-
-
Notifications
You must be signed in to change notification settings - Fork 52
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Add a patch for conditional IOMMU-less passthrough on PV domain
Look for qubes.enable_insecure_pv_passthrough on dom0 kernel cmdline. If it's present, allow creating PV domain with PCI devices even if IOMMU is not present/enabled. QubesOS/qubes-issues#5529
- Loading branch information
Showing
2 changed files
with
125 additions
and
0 deletions.
There are no files selected for viewing
124 changes: 124 additions & 0 deletions
124
patch-0001-libxl-conditionally-allow-PCI-passthrough-on-PV-with.patch
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,124 @@ | ||
From 8d87bae7af619eed2e1bc7a670391ca170702239 Mon Sep 17 00:00:00 2001 | ||
From: =?UTF-8?q?Marek=20Marczykowski-G=C3=B3recki?= | ||
<marmarek@invisiblethingslab.com> | ||
Date: Sat, 16 Jan 2021 05:06:18 +0100 | ||
Subject: [PATCH] libxl: conditionally allow PCI passthrough on PV without | ||
IOMMU | ||
MIME-Version: 1.0 | ||
Content-Type: text/plain; charset=UTF-8 | ||
Content-Transfer-Encoding: 8bit | ||
Organization: Invisible Things Lab | ||
Cc: Marek Marczykowski-Górecki <marmarek@invisiblethingslab.com> | ||
|
||
Without IOMMU, PCI passthrough cannot be used securely. But there are | ||
still various Qubes OS features that would be useful and improve overall | ||
system trustworthiness compared to monolithic system. | ||
This is also handy for development, to allow running Qubes OS nested | ||
withing KVM (on AMD, vIOMMU is unstable). | ||
|
||
Signed-off-by: Marek Marczykowski-Górecki <marmarek@invisiblethingslab.com> | ||
--- | ||
tools/libxl/libxl_create.c | 8 ++++++- | ||
tools/libxl/libxl_internal.h | 2 ++ | ||
tools/libxl/libxl_pci.c | 41 ++++++++++++++++++++++++++++++++++-- | ||
3 files changed, 48 insertions(+), 3 deletions(-) | ||
|
||
diff --git a/tools/libxl/libxl_create.c b/tools/libxl/libxl_create.c | ||
index 2814818e34d2..90aa0a35cdc8 100644 | ||
--- a/tools/libxl/libxl_create.c | ||
+++ b/tools/libxl/libxl_create.c | ||
@@ -1097,12 +1097,18 @@ int libxl__domain_config_setdefault(libxl__gc *gc, | ||
} | ||
|
||
bool need_pt = d_config->num_pcidevs || d_config->num_dtdevs; | ||
+ bool iommu_enabled = physinfo.cap_hvm_directio; | ||
+ if (need_pt && !iommu_enabled && | ||
+ c_info->type == LIBXL_DOMAIN_TYPE_PV && | ||
+ libxl__is_insecure_pv_passthrough_enabled(gc)) { | ||
+ /* allow insecure PV with IOMMU usage */ | ||
+ need_pt = false; | ||
+ } | ||
if (c_info->passthrough == LIBXL_PASSTHROUGH_DEFAULT) { | ||
c_info->passthrough = need_pt | ||
? LIBXL_PASSTHROUGH_ENABLED : LIBXL_PASSTHROUGH_DISABLED; | ||
} | ||
|
||
- bool iommu_enabled = physinfo.cap_hvm_directio; | ||
if (c_info->passthrough != LIBXL_PASSTHROUGH_DISABLED && !iommu_enabled) { | ||
LOGD(ERROR, domid, | ||
"passthrough not supported on this platform\n"); | ||
diff --git a/tools/libxl/libxl_internal.h b/tools/libxl/libxl_internal.h | ||
index 94a23179d30a..a5b3bbcdf094 100644 | ||
--- a/tools/libxl/libxl_internal.h | ||
+++ b/tools/libxl/libxl_internal.h | ||
@@ -4819,6 +4819,8 @@ static inline const char *libxl__qemu_qmp_path(libxl__gc *gc, int domid) | ||
return GCSPRINTF("%s/qmp-libxl-%d", libxl__run_dir_path(), domid); | ||
} | ||
|
||
+_hidden bool libxl__is_insecure_pv_passthrough_enabled(libxl__gc *gc); | ||
+ | ||
/* Send control commands over xenstore and wait for an Ack. */ | ||
_hidden int libxl__domain_pvcontrol(libxl__egc *egc, | ||
libxl__xswait_state *pvcontrol, | ||
diff --git a/tools/libxl/libxl_pci.c b/tools/libxl/libxl_pci.c | ||
index bc5843b13701..feac48b45ece 100644 | ||
--- a/tools/libxl/libxl_pci.c | ||
+++ b/tools/libxl/libxl_pci.c | ||
@@ -1432,8 +1432,10 @@ out_no_irq: | ||
r = xc_assign_device(ctx->xch, domid, pcidev_encode_bdf(pcidev), flag); | ||
if (r < 0 && (hvm || errno != ENOSYS)) { | ||
LOGED(ERROR, domainid, "xc_assign_device failed"); | ||
- rc = ERROR_FAIL; | ||
- goto out; | ||
+ if (hvm || errno != EOPNOTSUPP || libxl__is_insecure_pv_passthrough_enabled(gc)) { | ||
+ rc = ERROR_FAIL; | ||
+ goto out; | ||
+ } | ||
} | ||
} | ||
|
||
@@ -1483,6 +1485,41 @@ static int libxl__device_pci_reset(libxl__gc *gc, unsigned int domain, unsigned | ||
return -1; | ||
} | ||
|
||
+bool libxl__is_insecure_pv_passthrough_enabled(libxl__gc *gc) | ||
+{ | ||
+ FILE *f = fopen("/proc/cmdline", "r"); | ||
+ char cmdline[4096], *tok; | ||
+ size_t read_s; | ||
+ static int is_enabled = -1; | ||
+ | ||
+ if (is_enabled != -1) | ||
+ return is_enabled; | ||
+ | ||
+ if (!f) { | ||
+ LOG(WARN, "Failed to open /proc/cmdline: %d", errno); | ||
+ return false; | ||
+ } | ||
+ read_s = fread(cmdline, 1, sizeof(cmdline) - 1, f); | ||
+ if (!feof(f) || ferror(f)) { | ||
+ LOG(WARN, "Failed to read /proc/cmdline: %d", errno); | ||
+ fclose(f); | ||
+ return false; | ||
+ } | ||
+ cmdline[read_s] = 0; | ||
+ fclose(f); | ||
+ | ||
+ tok = strtok(cmdline, " \n"); | ||
+ while (tok) { | ||
+ if (strcmp(tok, "qubes.enable_insecure_pv_passthrough") == 0) { | ||
+ is_enabled = 1; | ||
+ return true; | ||
+ } | ||
+ tok = strtok(NULL, " \n"); | ||
+ } | ||
+ is_enabled = 0; | ||
+ return false; | ||
+} | ||
+ | ||
int libxl__device_pci_setdefault(libxl__gc *gc, uint32_t domid, | ||
libxl_device_pci *pci, bool hotplug) | ||
{ | ||
-- | ||
2.25.4 | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters