From: Alexander Graf <graf@amazon.com>
To: <linux-kernel@vger.kernel.org>,
Greg Kroah-Hartman <gregkh@linuxfoundation.org>,
Arnd Bergmann <arnd@arndb.de>
Cc: The AWS Nitro Enclaves Team <aws-nitro-enclaves-devel@amazon.com>,
"Shuah Khan" <skhan@linuxfoundation.org>,
Randy Dunlap <rdunlap@infradead.org>,
Marek Szyprowski <m.szyprowski@samsung.com>,
Robin Murphy <robin.murphy@arm.com>, <linux-doc@vger.kernel.org>,
<iommu@lists.linux.dev>,
Andrew Morton <akpm@linux-foundation.org>,
David Hildenbrand <david@kernel.org>,
Mike Rapoport <rppt@kernel.org>, <nh-open-source@amazon.com>,
<linux-mm@kvack.org>, Jonathan Corbet <corbet@lwn.net>
Subject: [PATCH 35/40] nitro_enclaves: Add NE_ENCLAVE_DIRECT_MODE
Date: Wed, 11 Nov 2026 22:59:39 +0000 [thread overview]
Message-ID: <af6ee68b7edf080cfac1552f3a31a8ffdf42cbf6.1794393491.git.graf@amazon.com> (raw)
In-Reply-To: <cover.1794300002.git.graf@amazon.com>
Nitro Sandboxes introduce a mode called direct mode, in which the parent
keeps access to most of the memory it donates to the sandbox. This mode
disables any attestation, but enables guest kernels that are not aware
of the Device Memory Buffer (DMB) to work. A DMB-aware guest kernel
places its virtqueues and buffers in memory the device provides, so the
parent needs access to that memory only.
Add NE_ENCLAVE_DIRECT_MODE, which asks the hypervisor for a direct-mode
slot. Remember the flags a slot was allocated with in
ne_enclave->launch_flags. Allow NE_ADD_MEMORY_REGION to use an
NE_MEMORY_SHARED allocation for a slot that carries this flag.
Signed-off-by: Alexander Graf <graf@amazon.com>
---
Documentation/virt/ne_overview.rst | 4 +++-
drivers/virt/nitro_enclaves/ne_misc_dev.c | 9 +++++++--
drivers/virt/nitro_enclaves/ne_misc_dev.h | 7 ++++++-
include/uapi/linux/nitro_enclaves.h | 19 +++++++++++++++++--
4 files changed, 33 insertions(+), 6 deletions(-)
diff --git a/Documentation/virt/ne_overview.rst b/Documentation/virt/ne_overview.rst
index 012fcb394a2ef..5984fd32ec07a 100644
--- a/Documentation/virt/ne_overview.rst
+++ b/Documentation/virt/ne_overview.rst
@@ -183,7 +183,9 @@ memory region per contiguous run it is made of, or fewer where runs turn out
to be physically adjacent. It also ends writing: the memory is the enclave's
from that point, so an image goes in first. It takes private allocations
only, since memory the parent can still reach is not memory the enclave has
-to itself.
+to itself. A slot allocated with NE_ENCLAVE_DIRECT_MODE asks for an enclave
+whose memory the parent keeps access to, and takes a shared allocation as a
+memory region.
An enclave's memory is laid out in the order its allocations are given to it,
and the offset NE_GET_IMAGE_LOAD_INFO returns is an offset into that layout.
diff --git a/drivers/virt/nitro_enclaves/ne_misc_dev.c b/drivers/virt/nitro_enclaves/ne_misc_dev.c
index 961b821d6038b..cccfceeb575cc 100644
--- a/drivers/virt/nitro_enclaves/ne_misc_dev.c
+++ b/drivers/virt/nitro_enclaves/ne_misc_dev.c
@@ -3447,6 +3447,8 @@ static int ne_create_vm_ioctl(struct ne_pci_dev *ne_pci_dev, u64 flags,
if (!ne_enclave)
return -ENOMEM;
+ ne_enclave->launch_flags = flags;
+
mutex_lock(&ne_cpu_pool.mutex);
ne_enclave->nr_parent_vm_cores = ne_cpu_pool.nr_parent_vm_cores;
@@ -4603,9 +4605,12 @@ static int ne_add_memory_region_ioctl(struct ne_enclave *ne_enclave,
/*
* The parent may map a shared allocation and keeps any mapping it has
* for as long as the allocation lives. Memory a region is made of is
- * the enclave's alone.
+ * the enclave's alone, unless the slot was allocated for an enclave
+ * whose memory the parent keeps access to, which is what
+ * NE_ENCLAVE_DIRECT_MODE asks for.
*/
- if (mem->shared) {
+ if (mem->shared &&
+ !(ne_enclave->launch_flags & NE_ENCLAVE_DIRECT_MODE)) {
dev_err_ratelimited(ne_misc_dev.this_device,
"The memory region allocation is shared\n");
diff --git a/drivers/virt/nitro_enclaves/ne_misc_dev.h b/drivers/virt/nitro_enclaves/ne_misc_dev.h
index b0d0438157260..1fd93bddf7766 100644
--- a/drivers/virt/nitro_enclaves/ne_misc_dev.h
+++ b/drivers/virt/nitro_enclaves/ne_misc_dev.h
@@ -22,7 +22,8 @@
/*
* NE_ENCLAVE_FLAG_VALID_MASK - Every launch flag this kernel passes on.
*/
-#define NE_ENCLAVE_FLAG_VALID_MASK (NE_ENCLAVE_PCIE_MODE | \
+#define NE_ENCLAVE_FLAG_VALID_MASK (NE_ENCLAVE_DIRECT_MODE | \
+ NE_ENCLAVE_PCIE_MODE | \
NE_ENCLAVE_PCIE_VSOCK_MODE | \
NE_ENCLAVE_PCIE_VIRTIO_MODE | \
NE_ENCLAVE_PCIE_NUMA_MODE)
@@ -203,6 +204,9 @@ struct ne_doorbell_binding {
* so that the device keeps the page after user space
* has closed the descriptor. NULL until
* %NE_SET_INFO_PAGE is called.
+ * @launch_flags: The launch flag word the slot was allocated with,
+ * as %NE_CREATE_VM2 received it. Read to answer a
+ * later call the way the slot was asked for.
* @notify_bindings: List of the notifications this enclave has bound
* an eventfd to.
* @devices: List of struct ne_device_wiring, one for each device
@@ -243,6 +247,7 @@ struct ne_enclave {
bool has_event;
u64 id;
struct file *info_file;
+ u64 launch_flags;
struct list_head notify_bindings;
struct list_head devices;
u64 max_mem_regions;
diff --git a/include/uapi/linux/nitro_enclaves.h b/include/uapi/linux/nitro_enclaves.h
index 67be5c383c54b..b346e0582c5fa 100644
--- a/include/uapi/linux/nitro_enclaves.h
+++ b/include/uapi/linux/nitro_enclaves.h
@@ -58,6 +58,17 @@
*/
#define NE_ENCLAVE_PCIE_MODE (1u << 6)
+/**
+ * NE_ENCLAVE_DIRECT_MODE - Allocate a slot whose memory the parent keeps
+ * access to. The enclave produces no attestation,
+ * since nothing separates its memory from the VM that
+ * launched it. An %NE_MEMORY_SHARED allocation can be
+ * given to such a slot as a memory region, which a
+ * slot without this flag refuses. Requires
+ * NE_ENCLAVE_PCIE_MODE.
+ */
+#define NE_ENCLAVE_DIRECT_MODE (1u << 1)
+
/**
* NE_ENCLAVE_PCIE_VSOCK_MODE - Allocate a slot whose PCIe bus holds one
* virtio-vsock device, attached before the enclave
@@ -440,7 +451,9 @@ struct ne_add_memory_region_args {
* enclave image goes in before this call. The allocation
* has to be %NE_MEMORY_PRIVATE, since memory the parent
* can still reach is not memory the enclave has to
- * itself.
+ * itself, unless the slot was allocated with
+ * %NE_ENCLAVE_DIRECT_MODE, which asks for an enclave
+ * whose memory the parent keeps access to.
* An enclave's memory is laid out in the order its
* allocations are given to it, and the offset from
* %NE_GET_IMAGE_LOAD_INFO is an offset into that layout,
@@ -461,7 +474,9 @@ struct ne_add_memory_region_args {
* * EINVAL - The argument is shorter than @flags, or @fd
* is not a descriptor from %NE_ALLOC_MEMORY, or
* the allocation was made for another enclave,
- * or the allocation is %NE_MEMORY_SHARED.
+ * or the allocation is %NE_MEMORY_SHARED
+ * and the slot was not allocated with
+ * %NE_ENCLAVE_DIRECT_MODE.
* * EIO - Current task mm is not the same as the one
* that created the enclave.
* * E2BIG - The argument is longer than this kernel knows
--
2.47.1
next prev parent reply other threads:[~2026-11-11 23:11 UTC|newest]
Thread overview: 41+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-11-11 22:41 [PATCH 00/40] nitro_enclaves: Add support for Nitro Sandboxes Alexander Graf
2026-11-11 22:41 ` [PATCH 01/40] nitro_enclaves: Allow the CPU pool to span NUMA nodes Alexander Graf
2026-11-11 22:41 ` [PATCH 02/40] nitro_enclaves: Add NE_ADD_ANY_VCPU Alexander Graf
2026-11-11 22:41 ` [PATCH 03/40] nitro_enclaves: Expose CPU pool state under sysfs Alexander Graf
2026-11-11 22:41 ` [PATCH 04/40] nitro_enclaves: Document multi-NUMA CPU pools Alexander Graf
2026-11-11 22:41 ` [PATCH 05/40] dma-contiguous: add dma_get_numa_cma_area() accessor Alexander Graf
2026-11-11 22:41 ` [PATCH 06/40] nitro_enclaves: Add NE_ALLOC_MEMORY ioctl Alexander Graf
2026-11-11 22:41 ` [PATCH 07/40] nitro_enclaves: Add NE_MEMORY_SHARED Alexander Graf
2026-11-11 22:41 ` [PATCH 08/40] nitro_enclaves: Add NE_ADD_MEMORY_REGION Alexander Graf
2026-11-11 22:41 ` [PATCH 09/40] nitro_enclaves: Document the memory pool Alexander Graf
2026-11-11 22:41 ` [PATCH 10/40] nitro_enclaves: Add NE_CREATE_VM2 with a launch flag word Alexander Graf
2026-11-11 22:41 ` [PATCH 11/40] nitro_enclaves: Add NE_ENCLAVE_PCIE_MODE launch flag Alexander Graf
2026-11-11 22:41 ` [PATCH 12/40] nitro_enclaves: Name the device's error codes in the UAPI header Alexander Graf
2026-11-11 22:41 ` [PATCH 13/40] nitro_enclaves: Log a reached device limit at info level Alexander Graf
2026-11-11 22:56 ` [PATCH 14/40] nitro_enclaves: Add NE_SET_INFO_PAGE Alexander Graf
2026-11-11 22:59 ` [PATCH 15/40] nitro_enclaves: Document the info page in the memory pool Alexander Graf
2026-11-11 22:59 ` [PATCH 16/40] nitro_enclaves: Turn the command reply into a per-command union Alexander Graf
2026-11-11 22:59 ` [PATCH 17/40] nitro_enclaves: Add the slot pool donation commands Alexander Graf
2026-11-11 22:59 ` [PATCH 18/40] nitro_enclaves: Donate memory for the slot pool Alexander Graf
2026-11-11 22:59 ` [PATCH 19/40] nitro_enclaves: Add the slot pool growth commands Alexander Graf
2026-11-11 22:59 ` [PATCH 20/40] nitro_enclaves: Add a helper to grow the slot pool Alexander Graf
2026-11-11 22:59 ` [PATCH 21/40] nitro_enclaves: Document " Alexander Graf
2026-11-11 22:59 ` [PATCH 22/40] nitro_enclaves: Expose slot pool state under sysfs Alexander Graf
2026-11-11 22:59 ` [PATCH 23/40] nitro_enclaves: Add the device add command Alexander Graf
2026-11-11 22:59 ` [PATCH 24/40] nitro_enclaves: Add NE_ADD_DEVICE Alexander Graf
2026-11-11 22:59 ` [PATCH 25/40] nitro_enclaves: Read the interrupt multiplexer geometry at probe Alexander Graf
2026-11-11 22:59 ` [PATCH 26/40] nitro_enclaves: Donate a bitmap page per multiplexed vector Alexander Graf
2026-11-11 22:59 ` [PATCH 27/40] nitro_enclaves: Dispatch multiplexed interrupts to per-queue bindings Alexander Graf
2026-11-11 22:59 ` [PATCH 28/40] nitro_enclaves: Add NE_SET_NOTIFY_EVENTFD Alexander Graf
2026-11-11 22:59 ` [PATCH 29/40] nitro_enclaves: Report the device's info notification Alexander Graf
2026-11-11 22:59 ` [PATCH 30/40] nitro_enclaves: Count multiplexed interrupts under debugfs Alexander Graf
2026-11-11 22:59 ` [PATCH 31/40] nitro_enclaves: Map the doorbell window at probe Alexander Graf
2026-11-11 22:59 ` [PATCH 32/40] nitro_enclaves: Add NE_SET_VRING_CALL Alexander Graf
2026-11-11 22:59 ` [PATCH 33/40] nitro_enclaves: Assert the layout of the ioctl argument structs Alexander Graf
2026-11-11 22:59 ` [PATCH 34/40] nitro_enclaves: Pass on the Nitro Sandbox launch flags Alexander Graf
2026-11-11 22:59 ` Alexander Graf [this message]
2026-11-11 22:59 ` [PATCH 36/40] nitro_enclaves: Add NE_ENCLAVE_PCIE_HOTPLUG_MODE Alexander Graf
2026-11-11 22:59 ` [PATCH 37/40] nitro_enclaves: Add NE_ENCLAVE_CPU_OVERCOMMIT_MODE Alexander Graf
2026-11-11 22:59 ` [PATCH 38/40] nitro_enclaves: Add NE_GET_CAPS Alexander Graf
2026-11-11 22:59 ` [PATCH 39/40] nitro_enclaves: Add NE_UPDATE_DEVICE_CONFIG Alexander Graf
2026-11-11 22:59 ` [PATCH 40/40] nitro_enclaves: Document the driver side of Nitro Sandboxes Alexander Graf
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=af6ee68b7edf080cfac1552f3a31a8ffdf42cbf6.1794393491.git.graf@amazon.com \
--to=graf@amazon.com \
--cc=akpm@linux-foundation.org \
--cc=arnd@arndb.de \
--cc=aws-nitro-enclaves-devel@amazon.com \
--cc=corbet@lwn.net \
--cc=david@kernel.org \
--cc=gregkh@linuxfoundation.org \
--cc=iommu@lists.linux.dev \
--cc=linux-doc@vger.kernel.org \
--cc=linux-kernel@vger.kernel.org \
--cc=linux-mm@kvack.org \
--cc=m.szyprowski@samsung.com \
--cc=nh-open-source@amazon.com \
--cc=rdunlap@infradead.org \
--cc=robin.murphy@arm.com \
--cc=rppt@kernel.org \
--cc=skhan@linuxfoundation.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 a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox
all inboxes | Powered by JetHome®