don't allow Dom0 access to IOMMUs' MMIO pages
authorJan Beulich <jbeulich@suse.com>
Mon, 6 Oct 2014 09:15:01 +0000 (11:15 +0200)
committerJan Beulich <jbeulich@suse.com>
Mon, 6 Oct 2014 09:15:01 +0000 (11:15 +0200)
Just like for LAPIC, IO-APIC, MSI, and HT we shouldn't be granting Dom0
access to these. This implicitly results in these pages also getting
marked reserved in the machine memory map Dom0 uses to determine the
ranges where PCI devices can have their MMIO ranges placed.

Signed-off-by: Jan Beulich <jbeulich@suse.com>
Reviewed-by: Andrew Cooper <andrew.cooper3@citrix.com>
Acked-by: Kevin Tian <kevin.tian@intel.com>
xen/drivers/passthrough/amd/pci_amd_iommu.c
xen/drivers/passthrough/vtd/iommu.c

index 0b301b3556b3865ab4b2f57e867c55342eb6358f..e83bb35e484c521fc150c9dfbf3f9ed855740317 100644 (file)
@@ -19,6 +19,7 @@
  */
 
 #include <xen/sched.h>
+#include <xen/iocap.h>
 #include <xen/pci.h>
 #include <xen/pci_regs.h>
 #include <xen/paging.h>
@@ -283,6 +284,7 @@ static int amd_iommu_domain_init(struct domain *d)
 static void __hwdom_init amd_iommu_hwdom_init(struct domain *d)
 {
     unsigned long i; 
+    const struct amd_iommu *iommu;
 
     if ( !iommu_passthrough && !need_iommu(d) )
     {
@@ -304,6 +306,12 @@ static void __hwdom_init amd_iommu_hwdom_init(struct domain *d)
         }
     }
 
+    for_each_amd_iommu ( iommu )
+        if ( iomem_deny_access(d, PFN_DOWN(iommu->mmio_base_phys),
+                               PFN_DOWN(iommu->mmio_base_phys +
+                                        IOMMU_MMIO_REGION_LENGTH - 1)) )
+            BUG();
+
     setup_hwdom_pci_devices(d, amd_iommu_setup_hwdom_device);
 }
 
index 63038d9394493b776642e609f2abc4393e6597f0..98fb2950c654fd3de2b0a317add1baccf738d42e 100644 (file)
@@ -23,6 +23,7 @@
 #include <xen/sched.h>
 #include <xen/xmalloc.h>
 #include <xen/domain_page.h>
+#include <xen/iocap.h>
 #include <xen/iommu.h>
 #include <asm/hvm/iommu.h>
 #include <xen/numa.h>
@@ -1258,6 +1259,9 @@ static void __hwdom_init intel_iommu_hwdom_init(struct domain *d)
 
     for_each_drhd_unit ( drhd )
     {
+        if ( iomem_deny_access(d, PFN_DOWN(drhd->address),
+                               PFN_DOWN(drhd->address)) )
+            BUG();
         iommu_enable_translation(drhd);
     }
 }