All of lore.kernel.org
 help / color / mirror / Atom feed
From: Sriram Nambakam <snambakam@linux.microsoft.com>
To: kvm@vger.kernel.org
Cc: linux-kernel@vger.kernel.org
Subject: [RFC PATCH v1 14/42] KVM: Add per-plane memory attribute support for cross-plane EPT protection
Date: Wed,  5 Aug 2026 04:02:56 -0700	[thread overview]
Message-ID: <20260805110324.25067-15-snambakam@linux.microsoft.com> (raw)
In-Reply-To: <20260805110324.25067-1-snambakam@linux.microsoft.com>

Extend the KVM memory attributes framework to support per-plane
R/W/X permission control, enabling a higher-privilege plane (e.g.,
plane-1 / secure kernel) to restrict a lower-privilege plane's
(e.g., plane-0) EPT permissions.

This is the KVM equivalent of the AMD SEV-SNP RMP (Reverse Map Table):
each plane has its own mem_attr_array, and attributes like NO_WRITE
and NO_EXEC are enforced by filtering pte_access bits during SPTE
creation.

Changes:
- include/uapi/linux/kvm.h: Add KVM_MEMORY_ATTRIBUTE_NO_WRITE (bit 4)
  and KVM_MEMORY_ATTRIBUTE_NO_EXEC (bit 5). Add struct
  kvm_plane_memory_attributes and KVM_SET_PLANE_MEMORY_ATTRIBUTES
  ioctl (0xd6) for targeting a specific plane's address space.

- virt/kvm/kvm_main.c: Extend kvm_supported_mem_attributes() to
  return NO_WRITE|NO_EXEC when CONFIG_KVM_MAX_NR_VCPU_PLANES is
  enabled. Add KVM_SET_PLANE_MEMORY_ATTRIBUTES ioctl handler that
  validates the target plane and delegates to the existing
  kvm_vm_ioctl_set_mem_attributes() infrastructure.

- arch/x86/kvm/mmu/spte.h: Add kvm_plane_filter_pte_access() helper
  that reads the plane's mem_attr_array for a GFN and strips W/X
  from pte_access when NO_WRITE/NO_EXEC are set.

- arch/x86/kvm/mmu/tdp_mmu.c, arch/x86/kvm/mmu/mmu.c: Wire
  kvm_plane_filter_pte_access() into both TDP and shadow MMU SPTE
  creation paths, filtering pte_access before calling make_spte().
---
 arch/x86/kvm/mmu/mmu.c     |  4 +++-
 arch/x86/kvm/mmu/spte.h    | 33 +++++++++++++++++++++++++++++++++
 arch/x86/kvm/mmu/tdp_mmu.c |  4 +++-
 include/uapi/linux/kvm.h   | 23 +++++++++++++++++++++++
 4 files changed, 62 insertions(+), 2 deletions(-)

diff --git a/arch/x86/kvm/mmu/mmu.c b/arch/x86/kvm/mmu/mmu.c
index a0d9a0a33c5f..3b861a42a712 100644
--- a/arch/x86/kvm/mmu/mmu.c
+++ b/arch/x86/kvm/mmu/mmu.c
@@ -3107,7 +3107,9 @@ static int mmu_set_spte(struct kvm_vcpu *vcpu, struct kvm_memory_slot *slot,
 		return RET_PF_EMULATE;
 	}
 
-	wrprot = make_spte(vcpu, sp, slot, pte_access, gfn, pfn, *sptep, prefetch,
+	wrprot = make_spte(vcpu, sp, slot,
+			   kvm_plane_filter_pte_access(vcpu, gfn, pte_access),
+			   gfn, pfn, *sptep, prefetch,
 			   false, host_writable, &spte);
 
 	if (*sptep == spte) {
diff --git a/arch/x86/kvm/mmu/spte.h b/arch/x86/kvm/mmu/spte.h
index 13eea94dd212..421836fd3932 100644
--- a/arch/x86/kvm/mmu/spte.h
+++ b/arch/x86/kvm/mmu/spte.h
@@ -579,4 +579,37 @@ static inline u64 restore_acc_track_spte(u64 spte)
 void __init kvm_mmu_spte_module_init(void);
 void kvm_mmu_reset_all_pte_masks(void);
 
+/*
+ * Apply per-plane memory protection attributes to pte_access.
+ * If the plane's mem_attr_array has NO_WRITE or NO_EXEC set for a GFN,
+ * strip the corresponding access bits before building the SPTE.
+ */
+#ifdef CONFIG_KVM_GENERIC_MEMORY_ATTRIBUTES
+static inline unsigned int kvm_plane_filter_pte_access(struct kvm_vcpu *vcpu,
+						       gfn_t gfn,
+						       unsigned int pte_access)
+{
+	struct kvm_plane *plane = vcpu_to_plane(vcpu);
+	unsigned long attrs;
+
+	if (!plane)
+		return pte_access;
+
+	attrs = kvm_get_plane_memory_attributes(plane, gfn);
+	if (attrs & KVM_MEMORY_ATTRIBUTE_NO_WRITE)
+		pte_access &= ~ACC_WRITE_MASK;
+	if (attrs & KVM_MEMORY_ATTRIBUTE_NO_EXEC)
+		pte_access &= ~ACC_EXEC_MASK;
+
+	return pte_access;
+}
+#else
+static inline unsigned int kvm_plane_filter_pte_access(struct kvm_vcpu *vcpu,
+						       gfn_t gfn,
+						       unsigned int pte_access)
+{
+	return pte_access;
+}
+#endif
+
 #endif
diff --git a/arch/x86/kvm/mmu/tdp_mmu.c b/arch/x86/kvm/mmu/tdp_mmu.c
index 4503558211fd..0603445377aa 100644
--- a/arch/x86/kvm/mmu/tdp_mmu.c
+++ b/arch/x86/kvm/mmu/tdp_mmu.c
@@ -1140,7 +1140,9 @@ static int tdp_mmu_map_handle_target_level(struct kvm_vcpu *vcpu,
 	if (unlikely(!fault->slot))
 		new_spte = make_mmio_spte(vcpu, iter->gfn, sp->role.access);
 	else
-		wrprot = make_spte(vcpu, sp, fault->slot, sp->role.access, iter->gfn,
+		wrprot = make_spte(vcpu, sp, fault->slot,
+				   kvm_plane_filter_pte_access(vcpu, iter->gfn, sp->role.access),
+				   iter->gfn,
 				   fault->pfn, iter->old_spte, fault->prefetch,
 				   false, fault->map_writable, &new_spte);
 
diff --git a/include/uapi/linux/kvm.h b/include/uapi/linux/kvm.h
index de670bd836bf..82189353ef35 100644
--- a/include/uapi/linux/kvm.h
+++ b/include/uapi/linux/kvm.h
@@ -1687,6 +1687,29 @@ struct kvm_memory_attributes {
 
 #define KVM_MEMORY_ATTRIBUTE_PRIVATE           (1ULL << 3)
 
+/*
+ * Per-plane memory protection attributes (VM planes / VBS).
+ * These control EPT R/W/X permissions enforced by the hypervisor on
+ * behalf of a higher-privilege plane (e.g., plane-1 restricting plane-0).
+ */
+#define KVM_MEMORY_ATTRIBUTE_NO_WRITE          (1ULL << 4)
+#define KVM_MEMORY_ATTRIBUTE_NO_EXEC           (1ULL << 5)
+
+/*
+ * Set memory attributes on a specific plane's address space.
+ * Used by a higher-privilege plane to restrict a lower-privilege plane's
+ * EPT permissions (e.g., plane-1 making plane-0 kernel text read-only).
+ */
+struct kvm_plane_memory_attributes {
+	__u32 plane;        /* target plane index                        */
+	__u32 flags;        /* must be 0                                 */
+	__u64 address;      /* GPA (page-aligned)                        */
+	__u64 size;         /* size in bytes (page-aligned)              */
+	__u64 attributes;   /* KVM_MEMORY_ATTRIBUTE_NO_WRITE / NO_EXEC   */
+};
+
+#define KVM_SET_PLANE_MEMORY_ATTRIBUTES	_IOW(KVMIO, 0xd6, struct kvm_plane_memory_attributes)
+
 #define KVM_CREATE_GUEST_MEMFD	_IOWR(KVMIO,  0xd4, struct kvm_create_guest_memfd)
 #define GUEST_MEMFD_FLAG_MMAP		(1ULL << 0)
 #define GUEST_MEMFD_FLAG_INIT_SHARED	(1ULL << 1)
-- 
2.55.0


  parent reply	other threads:[~2026-08-05 11:03 UTC|newest]

Thread overview: 43+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2026-08-05 11:02 [RFC PATCH v1 00/42] VBS/VSM-on-KVM: VBS integration for KVM VM planes Sriram Nambakam
2026-08-05 11:02 ` [RFC PATCH v1 01/42] Fix merge issue - Remove duplicate definition for kvm_arch_has_irq_bypass Sriram Nambakam
2026-08-05 11:02 ` [RFC PATCH v1 02/42] Fix compilation Sriram Nambakam
2026-08-05 11:02 ` [RFC PATCH v1 03/42] Fix compile error Sriram Nambakam
2026-08-05 11:02 ` [RFC PATCH v1 04/42] Fix compile errors Sriram Nambakam
2026-08-05 11:02 ` [RFC PATCH v1 05/42] Initial support for VM Planes - Add kernel config for CONFIG_VM_PLANES - Parse vm plane config from initrd for plane configuration - Make hypercalls to allocate memory for the vm planes Sriram Nambakam
2026-08-05 11:02 ` [RFC PATCH v1 06/42] Use vcpu count from the plane configuration Sriram Nambakam
2026-08-05 11:02 ` [RFC PATCH v1 07/42] skip processing plane configuration for plane 0 - plane 0 is the boot plane Sriram Nambakam
2026-08-05 11:02 ` [RFC PATCH v1 08/42] Add plane config param to specify kernel image format Sriram Nambakam
2026-08-05 11:02 ` [RFC PATCH v1 09/42] Activate the VM Planes through the Hypervisor - Using KVM as the VMM Sriram Nambakam
2026-08-05 11:02 ` [RFC PATCH v1 10/42] allow the command line to be specified for kernels in other planes Sriram Nambakam
2026-08-05 11:02 ` [RFC PATCH v1 11/42] Various changes to support VM Planes Sriram Nambakam
2026-08-05 11:02 ` [RFC PATCH v1 12/42] Add a Virtualization Based Security (VBS) framework. - Add backends for AMD SEV-SNP, Intel TDX, Arm CCA and KVM Planes. - Support VTL on Hyper-V in addition to Planes on KVM Sriram Nambakam
2026-08-05 11:02 ` [RFC PATCH v1 13/42] Add a inter-plane communication mechanism through KVM. - model this to use a single page similar to SEV-SNP Sriram Nambakam
2026-08-05 11:02 ` Sriram Nambakam [this message]
2026-08-05 11:02 ` [RFC PATCH v1 15/42] KVM: x86: Add KVM_HC_VBS_VTL_CALL hypercall for VBS inter-plane calls Sriram Nambakam
2026-08-05 11:02 ` [RFC PATCH v1 16/42] vbs: Add HEKI kernel sealing and fix KVM plane memory attribute guards Sriram Nambakam
2026-08-05 11:02 ` [RFC PATCH v1 17/42] vbs: Add module authentication via VBS/HEKI Sriram Nambakam
2026-08-05 11:03 ` [RFC PATCH v1 18/42] vbs: Add kexec validation and make module auth non-fatal Sriram Nambakam
2026-08-05 11:03 ` [RFC PATCH v1 19/42] Merge branch 'master' into vm-planes Sriram Nambakam
2026-08-05 11:03 ` [RFC PATCH v1 20/42] kvm: x86: fix merged plane API/stat build regressions Sriram Nambakam
2026-08-05 11:03 ` [RFC PATCH v1 21/42] KVM: x86: exit VM planes and VBS hypercalls to userspace Sriram Nambakam
2026-08-05 11:03 ` [RFC PATCH v1 22/42] kexec: block legacy kexec_load when VBS is active Sriram Nambakam
2026-08-05 11:03 ` [RFC PATCH v1 23/42] kvm: x86: fix merged plane API/stat build regressions Sriram Nambakam
2026-08-05 11:03 ` [RFC PATCH v1 24/42] KVM: planes: expose memory-attribute setting to in-kernel callers Sriram Nambakam
2026-08-05 11:03 ` [RFC PATCH v1 25/42] vm_planes: drop unused per-plane vcpu_count Sriram Nambakam
2026-08-05 11:03 ` [RFC PATCH v1 26/42] drivers/virt: add VBS secure-plane park loop Sriram Nambakam
2026-08-05 11:03 ` [RFC PATCH v1 27/42] KVM: planes: add arch-neutral in-kernel plane switch helper Sriram Nambakam
2026-08-05 11:03 ` [RFC PATCH v1 28/42] KVM: x86: add VBS VTL call/return and cross-plane set-mem-attrs hypercalls Sriram Nambakam
2026-08-05 11:03 ` [RFC PATCH v1 29/42] init/vm_planes: set up planes from rootfs_initcall and load ELF payloads Sriram Nambakam
2026-08-05 11:03 ` [RFC PATCH v1 30/42] security/vbs: run backend probe and HEKI seal at rootfs_initcall Sriram Nambakam
2026-08-05 11:03 ` [RFC PATCH v1 31/42] security/vbs: pin the VTL call hypercall to CPU0 Sriram Nambakam
2026-08-05 11:03 ` [RFC PATCH v1 32/42] security/vbs: add secure-plane monitor backend Sriram Nambakam
2026-08-05 11:03 ` [RFC PATCH v1 33/42] drivers/virt: rename VBS park loop to secure_monitor Sriram Nambakam
2026-08-05 11:03 ` [RFC PATCH v1 34/42] x86/realmode: skip the sub-1M trampoline for the VBS secure plane Sriram Nambakam
2026-08-05 11:03 ` [RFC PATCH v1 35/42] KVM: x86: deny normal-plane access to secure-plane memory Sriram Nambakam
2026-08-05 11:03 ` [RFC PATCH v1 36/42] KVM: plane: handle KVM_CHECK_EXTENSION on the plane fd Sriram Nambakam
2026-08-05 11:03 ` [RFC PATCH v1 37/42] KVM: selftests: run plane tests with a split IRQ chip Sriram Nambakam
2026-08-05 11:03 ` [RFC PATCH v1 38/42] kvm: x86: drop obsolete kvm_cache_regs.h Sriram Nambakam
2026-08-05 11:03 ` [RFC PATCH v1 39/42] kvm: arch: finalize plane hooks and kvm_arch_vcpu_create signature Sriram Nambakam
2026-08-05 11:03 ` [RFC PATCH v1 40/42] kvm: x86: use kvm_vcpu scheduling-state accessors and struct stat fields Sriram Nambakam
2026-08-05 11:03 ` [RFC PATCH v1 41/42] kvm: x86: finalize per-plane APIC state and CPUID placement Sriram Nambakam
2026-08-05 11:03 ` [RFC PATCH v1 42/42] kvm: planes: reconcile core plane state, UAPI and hypercall exit Sriram Nambakam

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20260805110324.25067-15-snambakam@linux.microsoft.com \
    --to=snambakam@linux.microsoft.com \
    --cc=kvm@vger.kernel.org \
    --cc=linux-kernel@vger.kernel.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.