All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH 0 of 5] amd iommu: Add ATS support (v3)
@ 2011-11-03 10:13 Wei Wang
  2011-11-03 10:13 ` [PATCH 1 of 5] ats: Move some ats functions to a new directory Wei Wang
                   ` (4 more replies)
  0 siblings, 5 replies; 15+ messages in thread
From: Wei Wang @ 2011-11-03 10:13 UTC (permalink / raw)
  To: xen-devel; +Cc: JBeulich

This patch set enables ats devices on amd systems with following changes:
1) Make vendor independent ATS codes more public.
2) Add additional helper functions for ats.
3) Add amd specific enablement.

Jan, this version should have fixed all issues from my 2nd try. Please check it.

Thanks,
Wei

^ permalink raw reply	[flat|nested] 15+ messages in thread

* [PATCH 1 of 5] ats: Move some ats functions to a new directory
  2011-11-03 10:13 [PATCH 0 of 5] amd iommu: Add ATS support (v3) Wei Wang
@ 2011-11-03 10:13 ` Wei Wang
  2011-11-03 12:46   ` Jan Beulich
  2011-11-03 10:13 ` [PATCH 2 of 5] amd iommu: Fix iommu page size encoding when page order > 0 Wei Wang
                   ` (3 subsequent siblings)
  4 siblings, 1 reply; 15+ messages in thread
From: Wei Wang @ 2011-11-03 10:13 UTC (permalink / raw)
  To: xen-devel; +Cc: JBeulich

# HG changeset patch
# User Wei Wang <wei.wang2@amd.com>
# Date 1320314537 -3600
# Node ID d422e3cf7976c76c57fc2d455b784d0fcc24d06b
# Parent  119bccb1cc5eee1364bbbd3bd1a30f22e9db703a
ats: Move some ats functions to a new directory.
Remove VTD prefix from debug output.
passhrough/x86 holds vendor neutral codes for x86 architecture.

Signed-off-by: Wei Wang <wei.wang2@amd.com>

diff -r 119bccb1cc5e -r d422e3cf7976 xen/drivers/passthrough/Makefile
--- a/xen/drivers/passthrough/Makefile	Wed Nov 02 13:53:05 2011 +0100
+++ b/xen/drivers/passthrough/Makefile	Thu Nov 03 11:02:17 2011 +0100
@@ -1,6 +1,7 @@
 subdir-$(x86) += vtd
 subdir-$(ia64) += vtd
 subdir-$(x86) += amd
+subdir-$(x86) += x86
 
 obj-y += iommu.o
 obj-y += io.o
diff -r 119bccb1cc5e -r d422e3cf7976 xen/drivers/passthrough/ats.h
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/xen/drivers/passthrough/ats.h	Thu Nov 03 11:02:17 2011 +0100
@@ -0,0 +1,39 @@
+/*
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms and conditions of the GNU General Public License,
+ * version 2, as published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * this program; if not, write to the Free Software Foundation, Inc., 59 Temple
+ * Place - Suite 330, Boston, MA 02111-1307 USA.
+ */
+
+#ifndef _ATS_H_
+#define _ATS_H_
+
+#define ATS_REG_CAP    4
+#define ATS_REG_CTL    6
+#define ATS_QUEUE_DEPTH_MASK     0xF
+#define ATS_ENABLE               (1<<15)
+
+struct pci_ats_dev {
+    struct list_head list;
+    u16 seg;
+    u8 bus;
+    u8 devfn;
+    u16 ats_queue_depth;    /* ATS device invalidation queue depth */
+};
+
+extern struct list_head ats_devices;
+extern bool_t ats_enabled;
+
+int enable_ats_device(int seg, int bus, int devfn);
+void disable_ats_device(int seg, int bus, int devfn);
+
+#endif /* _ATS_H_ */
+
diff -r 119bccb1cc5e -r d422e3cf7976 xen/drivers/passthrough/vtd/extern.h
--- a/xen/drivers/passthrough/vtd/extern.h	Wed Nov 02 13:53:05 2011 +0100
+++ b/xen/drivers/passthrough/vtd/extern.h	Thu Nov 03 11:02:17 2011 +0100
@@ -57,13 +57,9 @@ struct acpi_drhd_unit * iommu_to_drhd(st
 struct acpi_rhsa_unit * drhd_to_rhsa(struct acpi_drhd_unit *drhd);
 
 #ifdef CONFIG_X86_64
-extern bool_t ats_enabled;
-
 struct acpi_drhd_unit * find_ats_dev_drhd(struct iommu *iommu);
 
 int ats_device(const struct pci_dev *, const struct acpi_drhd_unit *);
-int enable_ats_device(int seg, int bus, int devfn);
-void disable_ats_device(int seg, int bus, int devfn);
 
 int dev_invalidate_iotlb(struct iommu *iommu, u16 did,
                          u64 addr, unsigned int size_order, u64 type);
diff -r 119bccb1cc5e -r d422e3cf7976 xen/drivers/passthrough/vtd/iommu.c
--- a/xen/drivers/passthrough/vtd/iommu.c	Wed Nov 02 13:53:05 2011 +0100
+++ b/xen/drivers/passthrough/vtd/iommu.c	Thu Nov 03 11:02:17 2011 +0100
@@ -40,6 +40,7 @@
 #include "dmar.h"
 #include "extern.h"
 #include "vtd.h"
+#include "../ats.h"
 
 #ifdef __ia64__
 #define nr_ioapics              iosapic_get_nr_iosapics()
diff -r 119bccb1cc5e -r d422e3cf7976 xen/drivers/passthrough/vtd/x86/ats.c
--- a/xen/drivers/passthrough/vtd/x86/ats.c	Wed Nov 02 13:53:05 2011 +0100
+++ b/xen/drivers/passthrough/vtd/x86/ats.c	Thu Nov 03 11:02:17 2011 +0100
@@ -27,51 +27,10 @@
 #include "../dmar.h"
 #include "../vtd.h"
 #include "../extern.h"
+#include "../../ats.h"
 
 static LIST_HEAD(ats_dev_drhd_units);
 
-#define ATS_REG_CAP    4
-#define ATS_REG_CTL    6
-#define ATS_QUEUE_DEPTH_MASK     0xF
-#define ATS_ENABLE               (1<<15)
-
-struct pci_ats_dev {
-    struct list_head list;
-    u16 seg;
-    u8 bus;
-    u8 devfn;
-    u16 ats_queue_depth;    /* ATS device invalidation queue depth */
-};
-static LIST_HEAD(ats_devices);
-
-static void parse_ats_param(char *s);
-custom_param("ats", parse_ats_param);
-
-bool_t __read_mostly ats_enabled = 1;
-
-static void __init parse_ats_param(char *s)
-{
-    char *ss;
-
-    do {
-        ss = strchr(s, ',');
-        if ( ss )
-            *ss = '\0';
-
-        switch ( parse_bool(s) )
-        {
-        case 0:
-            ats_enabled = 0;
-            break;
-        case 1:
-            ats_enabled = 1;
-            break;
-        }
-
-        s = ss + 1;
-    } while ( ss );
-}
-
 struct acpi_drhd_unit * find_ats_dev_drhd(struct iommu *iommu)
 {
     struct acpi_drhd_unit *drhd;
@@ -113,97 +72,6 @@ int ats_device(const struct pci_dev *pde
     return pos;
 }
 
-int enable_ats_device(int seg, int bus, int devfn)
-{
-    struct pci_ats_dev *pdev = NULL;
-    u32 value;
-    int pos;
-
-    pos = pci_find_ext_capability(seg, bus, devfn, PCI_EXT_CAP_ID_ATS);
-    BUG_ON(!pos);
-
-    if ( iommu_verbose )
-        dprintk(XENLOG_INFO VTDPREFIX,
-                "%04x:%02x:%02x.%u: ATS capability found\n",
-                seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn));
-
-    value = pci_conf_read16(seg, bus, PCI_SLOT(devfn),
-                            PCI_FUNC(devfn), pos + ATS_REG_CTL);
-    if ( value & ATS_ENABLE )
-    {
-        list_for_each_entry ( pdev, &ats_devices, list )
-        {
-            if ( pdev->seg == seg && pdev->bus == bus && pdev->devfn == devfn )
-            {
-                pos = 0;
-                break;
-            }
-        }
-    }
-    if ( pos )
-        pdev = xmalloc(struct pci_ats_dev);
-    if ( !pdev )
-        return -ENOMEM;
-
-    if ( !(value & ATS_ENABLE) )
-    {
-        value |= ATS_ENABLE;
-        pci_conf_write16(seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn),
-                         pos + ATS_REG_CTL, value);
-    }
-
-    if ( pos )
-    {
-        pdev->seg = seg;
-        pdev->bus = bus;
-        pdev->devfn = devfn;
-        value = pci_conf_read16(seg, bus, PCI_SLOT(devfn),
-                                PCI_FUNC(devfn), pos + ATS_REG_CAP);
-        pdev->ats_queue_depth = value & ATS_QUEUE_DEPTH_MASK;
-        list_add(&pdev->list, &ats_devices);
-    }
-
-    if ( iommu_verbose )
-        dprintk(XENLOG_INFO VTDPREFIX,
-                "%04x:%02x:%02x.%u: ATS %s enabled\n",
-                seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn),
-                pos ? "is" : "was");
-
-    return pos;
-}
-
-void disable_ats_device(int seg, int bus, int devfn)
-{
-    struct pci_ats_dev *pdev;
-    u32 value;
-    int pos;
-
-    pos = pci_find_ext_capability(seg, bus, devfn, PCI_EXT_CAP_ID_ATS);
-    BUG_ON(!pos);
-
-    value = pci_conf_read16(seg, bus, PCI_SLOT(devfn),
-                            PCI_FUNC(devfn), pos + ATS_REG_CTL);
-    value &= ~ATS_ENABLE;
-    pci_conf_write16(seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn),
-                     pos + ATS_REG_CTL, value);
-
-    list_for_each_entry ( pdev, &ats_devices, list )
-    {
-        if ( pdev->seg == seg && pdev->bus == bus && pdev->devfn == devfn )
-        {
-            list_del(&pdev->list);
-            xfree(pdev);
-            break;
-        }
-    }
-
-    if ( iommu_verbose )
-        dprintk(XENLOG_INFO VTDPREFIX,
-                "%04x:%02x:%02x.%u: ATS is disabled\n",
-                seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn));
-}
-
-
 static int device_in_domain(struct iommu *iommu, struct pci_ats_dev *pdev, u16 did)
 {
     struct root_entry *root_entry = NULL;
diff -r 119bccb1cc5e -r d422e3cf7976 xen/drivers/passthrough/x86/Makefile
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/xen/drivers/passthrough/x86/Makefile	Thu Nov 03 11:02:17 2011 +0100
@@ -0,0 +1,1 @@
+obj-y += ats.o
\ No newline at end of file
diff -r 119bccb1cc5e -r d422e3cf7976 xen/drivers/passthrough/x86/ats.c
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/xen/drivers/passthrough/x86/ats.c	Thu Nov 03 11:02:17 2011 +0100
@@ -0,0 +1,139 @@
+/*
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms and conditions of the GNU General Public License,
+ * version 2, as published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * this program; if not, write to the Free Software Foundation, Inc., 59 Temple
+ * Place - Suite 330, Boston, MA 02111-1307 USA.
+ */
+
+#include <xen/sched.h>
+#include <xen/pci.h>
+#include <xen/pci_regs.h>
+#include "../ats.h"
+
+LIST_HEAD(ats_devices);
+
+static void parse_ats_param(char *s);
+custom_param("ats", parse_ats_param);
+
+bool_t __read_mostly ats_enabled = 1;
+
+static void __init parse_ats_param(char *s)
+{
+    char *ss;
+
+    do {
+        ss = strchr(s, ',');
+        if ( ss )
+            *ss = '\0';
+
+        switch ( parse_bool(s) )
+        {
+        case 0:
+            ats_enabled = 0;
+            break;
+        case 1:
+            ats_enabled = 1;
+            break;
+        }
+
+        s = ss + 1;
+    } while ( ss );
+}
+
+int enable_ats_device(int seg, int bus, int devfn)
+{
+    struct pci_ats_dev *pdev = NULL;
+    u32 value;
+    int pos;
+
+    pos = pci_find_ext_capability(seg, bus, devfn, PCI_EXT_CAP_ID_ATS);
+    BUG_ON(!pos);
+
+    if ( iommu_verbose )
+        dprintk(XENLOG_INFO,
+                "%04x:%02x:%02x.%u: ATS capability found\n",
+                seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn));
+
+    value = pci_conf_read16(seg, bus, PCI_SLOT(devfn),
+                            PCI_FUNC(devfn), pos + ATS_REG_CTL);
+    if ( value & ATS_ENABLE )
+    {
+        list_for_each_entry ( pdev, &ats_devices, list )
+        {
+            if ( pdev->seg == seg && pdev->bus == bus && pdev->devfn == devfn )
+            {
+                pos = 0;
+                break;
+            }
+        }
+    }
+    if ( pos )
+        pdev = xmalloc(struct pci_ats_dev);
+    if ( !pdev )
+        return -ENOMEM;
+
+    if ( !(value & ATS_ENABLE) )
+    {
+        value |= ATS_ENABLE;
+        pci_conf_write16(seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn),
+                         pos + ATS_REG_CTL, value);
+    }
+
+    if ( pos )
+    {
+        pdev->seg = seg;
+        pdev->bus = bus;
+        pdev->devfn = devfn;
+        value = pci_conf_read16(seg, bus, PCI_SLOT(devfn),
+                                PCI_FUNC(devfn), pos + ATS_REG_CAP);
+        pdev->ats_queue_depth = value & ATS_QUEUE_DEPTH_MASK;
+        list_add(&pdev->list, &ats_devices);
+    }
+
+    if ( iommu_verbose )
+        dprintk(XENLOG_INFO,
+                "%04x:%02x:%02x.%u: ATS %s enabled\n",
+                seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn),
+                pos ? "is" : "was");
+
+    return pos;
+}
+
+void disable_ats_device(int seg, int bus, int devfn)
+{
+    struct pci_ats_dev *pdev;
+    u32 value;
+    int pos;
+
+    pos = pci_find_ext_capability(seg, bus, devfn, PCI_EXT_CAP_ID_ATS);
+    BUG_ON(!pos);
+
+    value = pci_conf_read16(seg, bus, PCI_SLOT(devfn),
+                            PCI_FUNC(devfn), pos + ATS_REG_CTL);
+    value &= ~ATS_ENABLE;
+    pci_conf_write16(seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn),
+                     pos + ATS_REG_CTL, value);
+
+    list_for_each_entry ( pdev, &ats_devices, list )
+    {
+        if ( pdev->seg == seg && pdev->bus == bus && pdev->devfn == devfn )
+        {
+            list_del(&pdev->list);
+            xfree(pdev);
+            break;
+        }
+    }
+
+    if ( iommu_verbose )
+        dprintk(XENLOG_INFO,
+                "%04x:%02x:%02x.%u: ATS is disabled\n",
+                seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn));
+}

^ permalink raw reply	[flat|nested] 15+ messages in thread

* [PATCH 2 of 5] amd iommu: Fix iommu page size encoding when page order > 0
  2011-11-03 10:13 [PATCH 0 of 5] amd iommu: Add ATS support (v3) Wei Wang
  2011-11-03 10:13 ` [PATCH 1 of 5] ats: Move some ats functions to a new directory Wei Wang
@ 2011-11-03 10:13 ` Wei Wang
  2011-11-03 12:49   ` Jan Beulich
  2011-11-03 10:13 ` [PATCH 3 of 5] ats: Add new ATS helper functions Wei Wang
                   ` (2 subsequent siblings)
  4 siblings, 1 reply; 15+ messages in thread
From: Wei Wang @ 2011-11-03 10:13 UTC (permalink / raw)
  To: xen-devel; +Cc: JBeulich

# HG changeset patch
# User Wei Wang <wei.wang2@amd.com>
# Date 1320314617 -3600
# Node ID d0c38cb215cd96e01de27eadf5ec0a5e711de448
# Parent  d422e3cf7976c76c57fc2d455b784d0fcc24d06b
amd iommu: Fix iommu page size encoding when page order > 0

Signed-off-by: Wei Wang <wei.wang2@amd.com>

diff -r d422e3cf7976 -r d0c38cb215cd xen/drivers/passthrough/amd/iommu_map.c
--- a/xen/drivers/passthrough/amd/iommu_map.c	Thu Nov 03 11:02:17 2011 +0100
+++ b/xen/drivers/passthrough/amd/iommu_map.c	Thu Nov 03 11:03:37 2011 +0100
@@ -77,23 +77,24 @@ static void invalidate_iommu_pages(struc
 {
     u64 addr_lo, addr_hi;
     u32 cmd[4], entry;
-    u64 mask = 0;
     int sflag = 0, pde = 0;
 
+    ASSERT ( order == 0 || order == 9 || order == 18 );
+
+    /* All pages associated with the domainID are invalidated */
+    if ( order || (io_addr == INV_IOMMU_ALL_PAGES_ADDRESS ) )
+    {
+        sflag = 1;
+        pde = 1;
+    }
+
     /* If sflag == 1, the size of the invalidate command is determined
      by the first zero bit in the address starting from Address[12] */
-    if ( order == 9 || order == 18 )
+    if ( order )
     {
-        mask = ((1ULL << (order - 1)) - 1) << PAGE_SHIFT;
-        io_addr |= mask;
-        sflag = 1;
-    }
-
-    /* All pages associated with the domainID are invalidated */
-    else if ( io_addr == 0x7FFFFFFFFFFFF000ULL )
-    {
-        sflag = 1;
-        pde = 1;
+        u64 mask = 1ULL << (order - 1 + PAGE_SHIFT);
+        io_addr &= ~mask;
+        io_addr |= mask - 1;
     }
 
     addr_lo = io_addr & DMA_32BIT_MASK;
@@ -917,7 +918,7 @@ static void _amd_iommu_flush_pages(struc
 
 void amd_iommu_flush_all_pages(struct domain *d)
 {
-    _amd_iommu_flush_pages(d, 0x7FFFFFFFFFFFFULL, 0);
+    _amd_iommu_flush_pages(d, INV_IOMMU_ALL_PAGES_ADDRESS, 0);
 }
 
 void amd_iommu_flush_pages(struct domain *d,
diff -r d422e3cf7976 -r d0c38cb215cd xen/include/asm-x86/hvm/svm/amd-iommu-defs.h
--- a/xen/include/asm-x86/hvm/svm/amd-iommu-defs.h	Thu Nov 03 11:02:17 2011 +0100
+++ b/xen/include/asm-x86/hvm/svm/amd-iommu-defs.h	Thu Nov 03 11:03:37 2011 +0100
@@ -407,4 +407,6 @@
 #define INT_REMAP_ENTRY_VECTOR_MASK     0x00FF0000
 #define INT_REMAP_ENTRY_VECTOR_SHIFT    16
 
+#define INV_IOMMU_ALL_PAGES_ADDRESS      0x7FFFFFFFFFFFFFFFULL
+
 #endif /* _ASM_X86_64_AMD_IOMMU_DEFS_H */

^ permalink raw reply	[flat|nested] 15+ messages in thread

* [PATCH 3 of 5] ats: Add new ATS helper functions
  2011-11-03 10:13 [PATCH 0 of 5] amd iommu: Add ATS support (v3) Wei Wang
  2011-11-03 10:13 ` [PATCH 1 of 5] ats: Move some ats functions to a new directory Wei Wang
  2011-11-03 10:13 ` [PATCH 2 of 5] amd iommu: Fix iommu page size encoding when page order > 0 Wei Wang
@ 2011-11-03 10:13 ` Wei Wang
  2011-11-03 10:13 ` [PATCH 4 of 5] amd iommu: add iotlb invalidation command Wei Wang
  2011-11-03 10:13 ` [PATCH 5 of 5] amd iommu: enable ats devices Wei Wang
  4 siblings, 0 replies; 15+ messages in thread
From: Wei Wang @ 2011-11-03 10:13 UTC (permalink / raw)
  To: xen-devel; +Cc: JBeulich

# HG changeset patch
# User Wei Wang <wei.wang2@amd.com>
# Date 1320314663 -3600
# Node ID c839972486f86a0833595bebae0baa0cd2c0d15e
# Parent  d0c38cb215cd96e01de27eadf5ec0a5e711de448
ats: Add new ATS helper functions

Signed-off-by Wei Wang <wei.wang2@amd.com>

diff -r d0c38cb215cd -r c839972486f8 xen/drivers/passthrough/ats.h
--- a/xen/drivers/passthrough/ats.h	Thu Nov 03 11:03:37 2011 +0100
+++ b/xen/drivers/passthrough/ats.h	Thu Nov 03 11:04:23 2011 +0100
@@ -21,6 +21,8 @@
 #define ATS_QUEUE_DEPTH_MASK     0xF
 #define ATS_ENABLE               (1<<15)
 
+#include <xen/pci_regs.h>
+
 struct pci_ats_dev {
     struct list_head list;
     u16 seg;
@@ -34,6 +36,27 @@ extern bool_t ats_enabled;
 
 int enable_ats_device(int seg, int bus, int devfn);
 void disable_ats_device(int seg, int bus, int devfn);
+struct pci_ats_dev *get_ats_device(int seg, int bus, int devfn);
 
+static inline int pci_ats_enabled(int seg, int bus, int devfn)
+{
+    u32 value;
+    int pos;
+
+    pos = pci_find_ext_capability(seg, bus, devfn, PCI_EXT_CAP_ID_ATS);
+    BUG_ON(!pos);
+
+    value = pci_conf_read16(seg, bus, PCI_SLOT(devfn),
+                            PCI_FUNC(devfn), pos + ATS_REG_CTL);
+    return value & ATS_ENABLE;
+}
+
+static inline int pci_ats_device(int seg, int bus, int devfn)
+{
+    if ( !ats_enabled )
+        return 0;
+
+    return pci_find_ext_capability(seg, bus, devfn, PCI_EXT_CAP_ID_ATS);
+}
 #endif /* _ATS_H_ */
 
diff -r d0c38cb215cd -r c839972486f8 xen/drivers/passthrough/x86/ats.c
--- a/xen/drivers/passthrough/x86/ats.c	Thu Nov 03 11:03:37 2011 +0100
+++ b/xen/drivers/passthrough/x86/ats.c	Thu Nov 03 11:04:23 2011 +0100
@@ -137,3 +137,19 @@ void disable_ats_device(int seg, int bus
                 "%04x:%02x:%02x.%u: ATS is disabled\n",
                 seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn));
 }
+
+struct pci_ats_dev *get_ats_device(int seg, int bus, int devfn)
+{
+    struct pci_ats_dev *pdev;
+
+    if ( !pci_ats_device(seg, bus, devfn) )
+        return NULL;
+
+    list_for_each_entry ( pdev, &ats_devices, list )
+    {
+        if ( pdev->seg == seg && pdev->bus == bus && pdev->devfn == devfn )
+            return pdev;
+    }
+
+    return NULL;
+}

^ permalink raw reply	[flat|nested] 15+ messages in thread

* [PATCH 4 of 5] amd iommu: add iotlb invalidation command
  2011-11-03 10:13 [PATCH 0 of 5] amd iommu: Add ATS support (v3) Wei Wang
                   ` (2 preceding siblings ...)
  2011-11-03 10:13 ` [PATCH 3 of 5] ats: Add new ATS helper functions Wei Wang
@ 2011-11-03 10:13 ` Wei Wang
  2011-11-03 10:13 ` [PATCH 5 of 5] amd iommu: enable ats devices Wei Wang
  4 siblings, 0 replies; 15+ messages in thread
From: Wei Wang @ 2011-11-03 10:13 UTC (permalink / raw)
  To: xen-devel; +Cc: JBeulich

# HG changeset patch
# User Wei Wang <wei.wang2@amd.com>
# Date 1320314694 -3600
# Node ID c9dcbe6d80a355f1e50ff910d618660a78b40653
# Parent  c839972486f86a0833595bebae0baa0cd2c0d15e
amd iommu: add iotlb invalidation command

Signed-off-by: Wei Wang <wei.wang2@amd.com>

diff -r c839972486f8 -r c9dcbe6d80a3 xen/drivers/passthrough/amd/iommu_map.c
--- a/xen/drivers/passthrough/amd/iommu_map.c	Thu Nov 03 11:04:23 2011 +0100
+++ b/xen/drivers/passthrough/amd/iommu_map.c	Thu Nov 03 11:04:54 2011 +0100
@@ -23,6 +23,8 @@
 #include <xen/hvm/iommu.h>
 #include <asm/amd-iommu.h>
 #include <asm/hvm/svm/amd-iommu-proto.h>
+#include "../ats.h"
+#include <xen/pci.h>
 
 static int queue_iommu_command(struct amd_iommu *iommu, u32 cmd[])
 {
@@ -128,6 +130,75 @@ static void invalidate_iommu_pages(struc
     send_iommu_command(iommu, cmd);
 }
 
+static void invalidate_iotlb_pages(struct amd_iommu *iommu,
+                                   u16 maxpend, u32 pasid, u16 queueid,
+                                   u64 io_addr, u16 dev_id, u16 order)
+{
+    u64 addr_lo, addr_hi;
+    u32 cmd[4], entry;
+    int sflag = 0;
+
+    ASSERT ( order == 0 || order == 9 || order == 18 );
+
+    if ( order || (io_addr == INV_IOMMU_ALL_PAGES_ADDRESS ) )
+        sflag = 1;
+
+    /* If sflag == 1, the size of the invalidate command is determined
+     by the first zero bit in the address starting from Address[12] */
+    if ( order )
+    {
+        u64 mask = 1ULL << (order - 1 + PAGE_SHIFT);
+        io_addr &= ~mask;
+        io_addr |= mask - 1;
+    }
+
+    addr_lo = io_addr & DMA_32BIT_MASK;
+    addr_hi = io_addr >> 32;
+
+    set_field_in_reg_u32(dev_id, 0,
+                         IOMMU_INV_IOTLB_PAGES_DEVICE_ID_MASK,
+                         IOMMU_INV_IOTLB_PAGES_DEVICE_ID_SHIFT, &entry);
+
+    set_field_in_reg_u32(maxpend, entry,
+                         IOMMU_INV_IOTLB_PAGES_MAXPEND_MASK,
+                         IOMMU_INV_IOTLB_PAGES_MAXPEND_SHIFT, &entry);
+
+    set_field_in_reg_u32(pasid & 0xff, entry,
+                         IOMMU_INV_IOTLB_PAGES_PASID1_MASK,
+                         IOMMU_INV_IOTLB_PAGES_PASID1_SHIFT, &entry);
+    cmd[0] = entry;
+
+    set_field_in_reg_u32(IOMMU_CMD_INVALIDATE_IOTLB_PAGES, 0,
+                         IOMMU_CMD_OPCODE_MASK, IOMMU_CMD_OPCODE_SHIFT,
+                         &entry);
+
+    set_field_in_reg_u32(pasid >> 8, entry,
+                         IOMMU_INV_IOTLB_PAGES_PASID2_MASK, 
+                         IOMMU_INV_IOTLB_PAGES_PASID2_SHIFT,
+                         &entry);
+
+    set_field_in_reg_u32(queueid, entry,
+                         IOMMU_INV_IOTLB_PAGES_QUEUEID_MASK, 
+                         IOMMU_INV_IOTLB_PAGES_QUEUEID_SHIFT,
+                         &entry);
+    cmd[1] = entry;
+
+    set_field_in_reg_u32(sflag, 0,
+                         IOMMU_INV_IOTLB_PAGES_S_FLAG_MASK,
+                         IOMMU_INV_IOTLB_PAGES_S_FLAG_MASK, &entry);
+
+    set_field_in_reg_u32((u32)addr_lo >> PAGE_SHIFT, entry,
+                         IOMMU_INV_IOTLB_PAGES_ADDR_LOW_MASK,
+                         IOMMU_INV_IOTLB_PAGES_ADDR_LOW_SHIFT, &entry);
+    cmd[2] = entry;
+
+    set_field_in_reg_u32((u32)addr_hi, 0,
+                         IOMMU_INV_IOTLB_PAGES_ADDR_HIGH_MASK,
+                         IOMMU_INV_IOTLB_PAGES_ADDR_HIGH_SHIFT, &entry);
+    cmd[3] = entry;
+
+    send_iommu_command(iommu, cmd);
+}
 void flush_command_buffer(struct amd_iommu *iommu)
 {
     u32 cmd[4], status;
@@ -896,6 +967,63 @@ int amd_iommu_reserve_domain_unity_map(s
     return 0;
 }
 
+void amd_iommu_flush_iotlb(struct pci_dev *pdev,
+                           uint64_t gaddr, unsigned int order)
+{
+    unsigned long flags;
+    struct amd_iommu *iommu;
+    unsigned int bdf, req_id, queueid, maxpend;
+    struct pci_ats_dev *ats_pdev;
+
+    if ( !ats_enabled )
+        return;
+
+    ats_pdev = get_ats_device(pdev->seg, pdev->bus, pdev->devfn);
+    if ( ats_pdev == NULL )
+        return;
+
+    if ( !pci_ats_enabled(ats_pdev->seg, 
+                          ats_pdev->bus, ats_pdev->devfn) )
+        return;
+
+    bdf = PCI_BDF2(ats_pdev->bus, ats_pdev->devfn);
+    iommu = find_iommu_for_device(ats_pdev->seg, bdf);
+
+    if ( !iommu )
+    {
+        AMD_IOMMU_DEBUG("%s: Fail to find iommu for device %04x:%02x:%02x.%u\n",
+                        __func__, ats_pdev->seg, ats_pdev->bus, 
+                        PCI_SLOT(ats_pdev->devfn),
+                        PCI_FUNC(ats_pdev->devfn));
+        return;
+    }
+
+    if ( !iommu->iotlb_support )
+        return;
+
+    req_id = get_dma_requestor_id(iommu->seg, bdf);
+    queueid = req_id;
+    maxpend = (ats_pdev->ats_queue_depth + 32) & 0xff;
+
+    /* send INVALIDATE_IOTLB_PAGES command */
+    spin_lock_irqsave(&iommu->lock, flags);
+    invalidate_iotlb_pages(iommu, maxpend, 0, queueid,
+                           gaddr, req_id, order);
+    flush_command_buffer(iommu);
+    spin_unlock_irqrestore(&iommu->lock, flags);
+}
+
+static void amd_iommu_flush_all_iotlbs(struct domain *d, 
+                                       uint64_t gaddr, unsigned int order)
+{
+    struct pci_dev *pdev;
+
+    if ( !ats_enabled )
+        return;
+
+    for_each_pdev( d, pdev )
+        amd_iommu_flush_iotlb(pdev, gaddr, order);
+}
 
 /* Flush iommu cache after p2m changes. */
 static void _amd_iommu_flush_pages(struct domain *d,
@@ -914,6 +1042,9 @@ static void _amd_iommu_flush_pages(struc
         flush_command_buffer(iommu);
         spin_unlock_irqrestore(&iommu->lock, flags);
     }
+
+    if ( ats_enabled )
+        amd_iommu_flush_all_iotlbs(d, gaddr, order);
 }
 
 void amd_iommu_flush_all_pages(struct domain *d)
diff -r c839972486f8 -r c9dcbe6d80a3 xen/include/asm-x86/hvm/svm/amd-iommu-defs.h
--- a/xen/include/asm-x86/hvm/svm/amd-iommu-defs.h	Thu Nov 03 11:04:23 2011 +0100
+++ b/xen/include/asm-x86/hvm/svm/amd-iommu-defs.h	Thu Nov 03 11:04:54 2011 +0100
@@ -233,6 +233,24 @@
 #define IOMMU_INV_INT_TABLE_DEVICE_ID_MASK   0x0000FFFF
 #define IOMMU_INV_INT_TABLE_DEVICE_ID_SHIFT  0
 
+/* INVALIDATE_IOTLB_PAGES command */
+#define IOMMU_INV_IOTLB_PAGES_MAXPEND_MASK          0xff000000
+#define IOMMU_INV_IOTLB_PAGES_MAXPEND_SHIFT         24
+#define IOMMU_INV_IOTLB_PAGES_PASID1_MASK           0x00ff0000
+#define IOMMU_INV_IOTLB_PAGES_PASID1_SHIFT          16
+#define IOMMU_INV_IOTLB_PAGES_PASID2_MASK           0x0fff0000
+#define IOMMU_INV_IOTLB_PAGES_PASID2_SHIFT          16
+#define IOMMU_INV_IOTLB_PAGES_QUEUEID_MASK          0x0000ffff
+#define IOMMU_INV_IOTLB_PAGES_QUEUEID_SHIFT         0
+#define IOMMU_INV_IOTLB_PAGES_DEVICE_ID_MASK        0x0000FFFF
+#define IOMMU_INV_IOTLB_PAGES_DEVICE_ID_SHIFT       0
+#define IOMMU_INV_IOTLB_PAGES_ADDR_LOW_MASK         0xFFFFF000
+#define IOMMU_INV_IOTLB_PAGES_ADDR_LOW_SHIFT        12
+#define IOMMU_INV_IOTLB_PAGES_ADDR_HIGH_MASK        0xFFFFFFFF
+#define IOMMU_INV_IOTLB_PAGES_ADDR_HIGH_SHIFT       0
+#define IOMMU_INV_IOTLB_PAGES_S_FLAG_MASK           0x00000001
+#define IOMMU_INV_IOTLB_PAGES_S_FLAG_SHIFT          0
+
 /* Event Log */
 #define IOMMU_EVENT_LOG_BASE_LOW_OFFSET		0x10
 #define IOMMU_EVENT_LOG_BASE_HIGH_OFFSET	0x14
diff -r c839972486f8 -r c9dcbe6d80a3 xen/include/asm-x86/hvm/svm/amd-iommu-proto.h
--- a/xen/include/asm-x86/hvm/svm/amd-iommu-proto.h	Thu Nov 03 11:04:23 2011 +0100
+++ b/xen/include/asm-x86/hvm/svm/amd-iommu-proto.h	Thu Nov 03 11:04:54 2011 +0100
@@ -55,6 +55,8 @@ int amd_iommu_unmap_page(struct domain *
 void amd_iommu_flush_pages(struct domain *d, unsigned long gfn,
                            unsigned int order);
 void amd_iommu_flush_all_pages(struct domain *d);
+void amd_iommu_flush_iotlb(struct pci_dev *pdev,
+                           uint64_t gaddr, unsigned int order);
 
 u64 amd_iommu_get_next_table_from_pte(u32 *entry);
 int amd_iommu_reserve_domain_unity_map(struct domain *domain,

^ permalink raw reply	[flat|nested] 15+ messages in thread

* [PATCH 5 of 5] amd iommu: enable ats devices
  2011-11-03 10:13 [PATCH 0 of 5] amd iommu: Add ATS support (v3) Wei Wang
                   ` (3 preceding siblings ...)
  2011-11-03 10:13 ` [PATCH 4 of 5] amd iommu: add iotlb invalidation command Wei Wang
@ 2011-11-03 10:13 ` Wei Wang
  4 siblings, 0 replies; 15+ messages in thread
From: Wei Wang @ 2011-11-03 10:13 UTC (permalink / raw)
  To: xen-devel; +Cc: JBeulich

# HG changeset patch
# User Wei Wang <wei.wang2@amd.com>
# Date 1320314731 -3600
# Node ID 7316595e8f47fcf5a106d897f99105a14d7e646c
# Parent  c9dcbe6d80a355f1e50ff910d618660a78b40653
amd iommu: enable ats devices

Signed-off-by: Wei Wang <wei.wang2@amd.com>

diff -r c9dcbe6d80a3 -r 7316595e8f47 xen/drivers/passthrough/amd/iommu_map.c
--- a/xen/drivers/passthrough/amd/iommu_map.c	Thu Nov 03 11:04:54 2011 +0100
+++ b/xen/drivers/passthrough/amd/iommu_map.c	Thu Nov 03 11:05:31 2011 +0100
@@ -370,6 +370,17 @@ void amd_iommu_set_root_page_table(
     dte[0] = entry;
 }
 
+void iommu_dte_set_iotlb(u32 *dte, u8 i)
+{
+    u32 entry;
+
+    entry = dte[3];
+    set_field_in_reg_u32(!!i, entry,
+                         IOMMU_DEV_TABLE_IOTLB_SUPPORT_MASK,
+                         IOMMU_DEV_TABLE_IOTLB_SUPPORT_SHIFT, &entry);
+    dte[3] = entry;
+}
+
 void __init amd_iommu_set_intremap_table(
     u32 *dte, u64 intremap_ptr, u8 int_valid)
 {
diff -r c9dcbe6d80a3 -r 7316595e8f47 xen/drivers/passthrough/amd/pci_amd_iommu.c
--- a/xen/drivers/passthrough/amd/pci_amd_iommu.c	Thu Nov 03 11:04:54 2011 +0100
+++ b/xen/drivers/passthrough/amd/pci_amd_iommu.c	Thu Nov 03 11:05:31 2011 +0100
@@ -25,6 +25,7 @@
 #include <asm/hvm/iommu.h>
 #include <asm/amd-iommu.h>
 #include <asm/hvm/svm/amd-iommu-proto.h>
+#include "../ats.h"
 
 struct amd_iommu *find_iommu_for_device(int seg, int bdf)
 {
@@ -86,6 +87,9 @@ static void amd_iommu_setup_domain_devic
     void *dte;
     unsigned long flags;
     int req_id, valid = 1;
+    int dte_i = 0;
+    u8 bus = PCI_BUS(bdf);
+    u8 devfn = PCI_DEVFN2(bdf);
 
     struct hvm_iommu *hd = domain_hvm_iommu(domain);
 
@@ -94,6 +98,9 @@ static void amd_iommu_setup_domain_devic
     if ( iommu_passthrough && (domain->domain_id == 0) )
         valid = 0;
 
+    if ( ats_enabled )
+        dte_i = 1;
+
     /* get device-table entry */
     req_id = get_dma_requestor_id(iommu->seg, bdf);
     dte = iommu->dev_table.buffer + (req_id * IOMMU_DEV_TABLE_ENTRY_SIZE);
@@ -107,6 +114,10 @@ static void amd_iommu_setup_domain_devic
             (u32 *)dte, page_to_maddr(hd->root_table), hd->domain_id,
             hd->paging_mode, valid);
 
+        if ( pci_ats_device(iommu->seg, bus, devfn) &&
+             iommu->iotlb_support )
+            iommu_dte_set_iotlb((u32 *)dte, dte_i);
+
         invalidate_dev_table_entry(iommu, req_id);
         flush_command_buffer(iommu);
 
@@ -118,11 +129,27 @@ static void amd_iommu_setup_domain_devic
     }
 
     spin_unlock_irqrestore(&iommu->lock, flags);
+
+    ASSERT(spin_is_locked(&pcidevs_lock));
+
+    if ( pci_ats_device(iommu->seg, bus, devfn) &&
+         !pci_ats_enabled(iommu->seg, bus, devfn) )
+    {
+        struct pci_dev *pdev;
+
+        enable_ats_device(iommu->seg, bus, devfn);
+
+        ASSERT(spin_is_locked(&pcidevs_lock));
+        pdev = pci_get_pdev(iommu->seg, bus, devfn);
+
+        ASSERT( pdev != NULL );
+        amd_iommu_flush_iotlb(pdev, INV_IOMMU_ALL_PAGES_ADDRESS, 0);
+    }
 }
 
 static void __init amd_iommu_setup_dom0_device(struct pci_dev *pdev)
 {
-    int bdf = (pdev->bus << 8) | pdev->devfn;
+    int bdf = PCI_BDF2(pdev->bus, pdev->devfn);
     struct amd_iommu *iommu = find_iommu_for_device(pdev->seg, bdf);
 
     if ( likely(iommu != NULL) )
@@ -261,12 +288,14 @@ static void __init amd_iommu_dom0_init(s
     setup_dom0_pci_devices(d, amd_iommu_setup_dom0_device);
 }
 
-static void amd_iommu_disable_domain_device(
-    struct domain *domain, struct amd_iommu *iommu, int bdf)
+void amd_iommu_disable_domain_device(struct domain *domain, 
+                                     struct amd_iommu *iommu, int bdf)
 {
     void *dte;
     unsigned long flags;
     int req_id;
+    u8 bus = PCI_BUS(bdf);
+    u8 devfn = PCI_DEVFN2(bdf);
 
     BUG_ON ( iommu->dev_table.buffer == NULL );
     req_id = get_dma_requestor_id(iommu->seg, bdf);
@@ -276,6 +305,11 @@ static void amd_iommu_disable_domain_dev
     if ( is_translation_valid((u32 *)dte) )
     {
         disable_translation((u32 *)dte);
+
+        if ( pci_ats_device(iommu->seg, bus, devfn) &&
+             iommu->iotlb_support )
+            iommu_dte_set_iotlb((u32 *)dte, 0);
+
         invalidate_dev_table_entry(iommu, req_id);
         flush_command_buffer(iommu);
         AMD_IOMMU_DEBUG("Disable: device id = 0x%04x, "
@@ -284,6 +318,12 @@ static void amd_iommu_disable_domain_dev
                         domain_hvm_iommu(domain)->paging_mode);
     }
     spin_unlock_irqrestore(&iommu->lock, flags);
+
+    ASSERT(spin_is_locked(&pcidevs_lock));
+
+    if ( pci_ats_device(iommu->seg, bus, devfn) && 
+         pci_ats_enabled(iommu->seg, bus, devfn) )
+       disable_ats_device(iommu->seg, bus, devfn); 
 }
 
 static int reassign_device( struct domain *source, struct domain *target,
@@ -299,7 +339,7 @@ static int reassign_device( struct domai
     if ( !pdev )
         return -ENODEV;
 
-    bdf = (bus << 8) | devfn;
+    bdf = PCI_BDF2(bus, devfn);
     iommu = find_iommu_for_device(seg, bdf);
     if ( !iommu )
     {
@@ -421,7 +461,7 @@ static int amd_iommu_add_device(struct p
     if ( !pdev->domain )
         return -EINVAL;
 
-    bdf = (pdev->bus << 8) | pdev->devfn;
+    bdf = PCI_BDF2(pdev->bus, pdev->devfn);
     iommu = find_iommu_for_device(pdev->seg, bdf);
     if ( !iommu )
     {
@@ -443,7 +483,7 @@ static int amd_iommu_remove_device(struc
     if ( !pdev->domain )
         return -EINVAL;
 
-    bdf = (pdev->bus << 8) | pdev->devfn;
+    bdf = PCI_BDF2(pdev->bus, pdev->devfn);
     iommu = find_iommu_for_device(pdev->seg, bdf);
     if ( !iommu )
     {
diff -r c9dcbe6d80a3 -r 7316595e8f47 xen/include/asm-x86/hvm/svm/amd-iommu-proto.h
--- a/xen/include/asm-x86/hvm/svm/amd-iommu-proto.h	Thu Nov 03 11:04:54 2011 +0100
+++ b/xen/include/asm-x86/hvm/svm/amd-iommu-proto.h	Thu Nov 03 11:05:31 2011 +0100
@@ -75,6 +75,7 @@ void amd_iommu_set_intremap_table(
     u32 *dte, u64 intremap_ptr, u8 int_valid);
 void amd_iommu_set_root_page_table(
     u32 *dte, u64 root_ptr, u16 domain_id, u8 paging_mode, u8 valid);
+void iommu_dte_set_iotlb(u32 *dte, u8 i);
 void invalidate_dev_table_entry(struct amd_iommu *iommu, u16 devic_id);
 
 /* send cmd to iommu */

^ permalink raw reply	[flat|nested] 15+ messages in thread

* Re: [PATCH 1 of 5] ats: Move some ats functions to a new directory
  2011-11-03 10:13 ` [PATCH 1 of 5] ats: Move some ats functions to a new directory Wei Wang
@ 2011-11-03 12:46   ` Jan Beulich
  0 siblings, 0 replies; 15+ messages in thread
From: Jan Beulich @ 2011-11-03 12:46 UTC (permalink / raw)
  To: Wei Wang; +Cc: xen-devel

>>> On 03.11.11 at 11:13, Wei Wang <wei.wang2@amd.com> wrote:
> # HG changeset patch
> # User Wei Wang <wei.wang2@amd.com>
> # Date 1320314537 -3600
> # Node ID d422e3cf7976c76c57fc2d455b784d0fcc24d06b
> # Parent  119bccb1cc5eee1364bbbd3bd1a30f22e9db703a
> ats: Move some ats functions to a new directory.
> Remove VTD prefix from debug output.
> passhrough/x86 holds vendor neutral codes for x86 architecture.
> 
> Signed-off-by: Wei Wang <wei.wang2@amd.com>
> 
> diff -r 119bccb1cc5e -r d422e3cf7976 xen/drivers/passthrough/Makefile
> --- a/xen/drivers/passthrough/Makefile	Wed Nov 02 13:53:05 2011 +0100
> +++ b/xen/drivers/passthrough/Makefile	Thu Nov 03 11:02:17 2011 +0100
> @@ -1,6 +1,7 @@
>  subdir-$(x86) += vtd
>  subdir-$(ia64) += vtd
>  subdir-$(x86) += amd
> +subdir-$(x86) += x86
>  
>  obj-y += iommu.o
>  obj-y += io.o
> diff -r 119bccb1cc5e -r d422e3cf7976 xen/drivers/passthrough/ats.h
> --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
> +++ b/xen/drivers/passthrough/ats.h	Thu Nov 03 11:02:17 2011 +0100
> @@ -0,0 +1,39 @@
> +/*
> + * This program is free software; you can redistribute it and/or modify it
> + * under the terms and conditions of the GNU General Public License,
> + * version 2, as published by the Free Software Foundation.
> + *
> + * This program is distributed in the hope it will be useful, but WITHOUT
> + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
> + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License 
> for
> + * more details.
> + *
> + * You should have received a copy of the GNU General Public License along 
> with
> + * this program; if not, write to the Free Software Foundation, Inc., 59 
> Temple
> + * Place - Suite 330, Boston, MA 02111-1307 USA.
> + */
> +
> +#ifndef _ATS_H_
> +#define _ATS_H_
> +
> +#define ATS_REG_CAP    4
> +#define ATS_REG_CTL    6
> +#define ATS_QUEUE_DEPTH_MASK     0xF
> +#define ATS_ENABLE               (1<<15)
> +
> +struct pci_ats_dev {
> +    struct list_head list;
> +    u16 seg;
> +    u8 bus;
> +    u8 devfn;
> +    u16 ats_queue_depth;    /* ATS device invalidation queue depth */
> +};
> +
> +extern struct list_head ats_devices;
> +extern bool_t ats_enabled;
> +
> +int enable_ats_device(int seg, int bus, int devfn);
> +void disable_ats_device(int seg, int bus, int devfn);
> +
> +#endif /* _ATS_H_ */
> +
> diff -r 119bccb1cc5e -r d422e3cf7976 xen/drivers/passthrough/vtd/extern.h
> --- a/xen/drivers/passthrough/vtd/extern.h	Wed Nov 02 13:53:05 2011 +0100
> +++ b/xen/drivers/passthrough/vtd/extern.h	Thu Nov 03 11:02:17 2011 +0100
> @@ -57,13 +57,9 @@ struct acpi_drhd_unit * iommu_to_drhd(st
>  struct acpi_rhsa_unit * drhd_to_rhsa(struct acpi_drhd_unit *drhd);
>  
>  #ifdef CONFIG_X86_64

Did you overlook this conditional? It and the respective inline functions
and #define-s must be added/moved to the new header too.

> -extern bool_t ats_enabled;
> -
>  struct acpi_drhd_unit * find_ats_dev_drhd(struct iommu *iommu);
>  
>  int ats_device(const struct pci_dev *, const struct acpi_drhd_unit *);
> -int enable_ats_device(int seg, int bus, int devfn);
> -void disable_ats_device(int seg, int bus, int devfn);
>  
>  int dev_invalidate_iotlb(struct iommu *iommu, u16 did,
>                           u64 addr, unsigned int size_order, u64 type);
> diff -r 119bccb1cc5e -r d422e3cf7976 xen/drivers/passthrough/vtd/iommu.c
> --- a/xen/drivers/passthrough/vtd/iommu.c	Wed Nov 02 13:53:05 2011 +0100
> +++ b/xen/drivers/passthrough/vtd/iommu.c	Thu Nov 03 11:02:17 2011 +0100
> @@ -40,6 +40,7 @@
>  #include "dmar.h"
>  #include "extern.h"
>  #include "vtd.h"
> +#include "../ats.h"
>  
>  #ifdef __ia64__
>  #define nr_ioapics              iosapic_get_nr_iosapics()
> diff -r 119bccb1cc5e -r d422e3cf7976 xen/drivers/passthrough/vtd/x86/ats.c
> --- a/xen/drivers/passthrough/vtd/x86/ats.c	Wed Nov 02 13:53:05 2011 +0100
> +++ b/xen/drivers/passthrough/vtd/x86/ats.c	Thu Nov 03 11:02:17 2011 +0100
> @@ -27,51 +27,10 @@
>  #include "../dmar.h"
>  #include "../vtd.h"
>  #include "../extern.h"
> +#include "../../ats.h"
>  
>  static LIST_HEAD(ats_dev_drhd_units);
>  
> -#define ATS_REG_CAP    4
> -#define ATS_REG_CTL    6
> -#define ATS_QUEUE_DEPTH_MASK     0xF
> -#define ATS_ENABLE               (1<<15)
> -
> -struct pci_ats_dev {
> -    struct list_head list;
> -    u16 seg;
> -    u8 bus;
> -    u8 devfn;
> -    u16 ats_queue_depth;    /* ATS device invalidation queue depth */
> -};
> -static LIST_HEAD(ats_devices);
> -
> -static void parse_ats_param(char *s);
> -custom_param("ats", parse_ats_param);
> -
> -bool_t __read_mostly ats_enabled = 1;
> -
> -static void __init parse_ats_param(char *s)
> -{
> -    char *ss;
> -
> -    do {
> -        ss = strchr(s, ',');
> -        if ( ss )
> -            *ss = '\0';
> -
> -        switch ( parse_bool(s) )
> -        {
> -        case 0:
> -            ats_enabled = 0;
> -            break;
> -        case 1:
> -            ats_enabled = 1;
> -            break;
> -        }
> -
> -        s = ss + 1;
> -    } while ( ss );
> -}
> -
>  struct acpi_drhd_unit * find_ats_dev_drhd(struct iommu *iommu)
>  {
>      struct acpi_drhd_unit *drhd;
> @@ -113,97 +72,6 @@ int ats_device(const struct pci_dev *pde
>      return pos;
>  }
>  
> -int enable_ats_device(int seg, int bus, int devfn)
> -{
> -    struct pci_ats_dev *pdev = NULL;
> -    u32 value;
> -    int pos;
> -
> -    pos = pci_find_ext_capability(seg, bus, devfn, PCI_EXT_CAP_ID_ATS);
> -    BUG_ON(!pos);
> -
> -    if ( iommu_verbose )
> -        dprintk(XENLOG_INFO VTDPREFIX,
> -                "%04x:%02x:%02x.%u: ATS capability found\n",
> -                seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn));
> -
> -    value = pci_conf_read16(seg, bus, PCI_SLOT(devfn),
> -                            PCI_FUNC(devfn), pos + ATS_REG_CTL);
> -    if ( value & ATS_ENABLE )
> -    {
> -        list_for_each_entry ( pdev, &ats_devices, list )
> -        {
> -            if ( pdev->seg == seg && pdev->bus == bus && pdev->devfn == devfn )
> -            {
> -                pos = 0;
> -                break;
> -            }
> -        }
> -    }
> -    if ( pos )
> -        pdev = xmalloc(struct pci_ats_dev);
> -    if ( !pdev )
> -        return -ENOMEM;
> -
> -    if ( !(value & ATS_ENABLE) )
> -    {
> -        value |= ATS_ENABLE;
> -        pci_conf_write16(seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn),
> -                         pos + ATS_REG_CTL, value);
> -    }
> -
> -    if ( pos )
> -    {
> -        pdev->seg = seg;
> -        pdev->bus = bus;
> -        pdev->devfn = devfn;
> -        value = pci_conf_read16(seg, bus, PCI_SLOT(devfn),
> -                                PCI_FUNC(devfn), pos + ATS_REG_CAP);
> -        pdev->ats_queue_depth = value & ATS_QUEUE_DEPTH_MASK;
> -        list_add(&pdev->list, &ats_devices);
> -    }
> -
> -    if ( iommu_verbose )
> -        dprintk(XENLOG_INFO VTDPREFIX,
> -                "%04x:%02x:%02x.%u: ATS %s enabled\n",
> -                seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn),
> -                pos ? "is" : "was");
> -
> -    return pos;
> -}
> -
> -void disable_ats_device(int seg, int bus, int devfn)
> -{
> -    struct pci_ats_dev *pdev;
> -    u32 value;
> -    int pos;
> -
> -    pos = pci_find_ext_capability(seg, bus, devfn, PCI_EXT_CAP_ID_ATS);
> -    BUG_ON(!pos);
> -
> -    value = pci_conf_read16(seg, bus, PCI_SLOT(devfn),
> -                            PCI_FUNC(devfn), pos + ATS_REG_CTL);
> -    value &= ~ATS_ENABLE;
> -    pci_conf_write16(seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn),
> -                     pos + ATS_REG_CTL, value);
> -
> -    list_for_each_entry ( pdev, &ats_devices, list )
> -    {
> -        if ( pdev->seg == seg && pdev->bus == bus && pdev->devfn == devfn )
> -        {
> -            list_del(&pdev->list);
> -            xfree(pdev);
> -            break;
> -        }
> -    }
> -
> -    if ( iommu_verbose )
> -        dprintk(XENLOG_INFO VTDPREFIX,
> -                "%04x:%02x:%02x.%u: ATS is disabled\n",
> -                seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn));
> -}
> -
> -
>  static int device_in_domain(struct iommu *iommu, struct pci_ats_dev *pdev, 
> u16 did)
>  {
>      struct root_entry *root_entry = NULL;
> diff -r 119bccb1cc5e -r d422e3cf7976 xen/drivers/passthrough/x86/Makefile
> --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
> +++ b/xen/drivers/passthrough/x86/Makefile	Thu Nov 03 11:02:17 2011 +0100
> @@ -0,0 +1,1 @@
> +obj-y += ats.o

obj-$(CONFIG_X86_64) += ats.o

The original file got built for 64-bit only, too.

> \ No newline at end of file

This is self-explanatory, isn't it?

> diff -r 119bccb1cc5e -r d422e3cf7976 xen/drivers/passthrough/x86/ats.c
> --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
> +++ b/xen/drivers/passthrough/x86/ats.c	Thu Nov 03 11:02:17 2011 +0100
> @@ -0,0 +1,139 @@
> +/*
> + * This program is free software; you can redistribute it and/or modify it
> + * under the terms and conditions of the GNU General Public License,
> + * version 2, as published by the Free Software Foundation.
> + *
> + * This program is distributed in the hope it will be useful, but WITHOUT
> + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
> + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License 
> for
> + * more details.
> + *
> + * You should have received a copy of the GNU General Public License along 
> with
> + * this program; if not, write to the Free Software Foundation, Inc., 59 
> Temple
> + * Place - Suite 330, Boston, MA 02111-1307 USA.
> + */
> +
> +#include <xen/sched.h>
> +#include <xen/pci.h>
> +#include <xen/pci_regs.h>
> +#include "../ats.h"
> +
> +LIST_HEAD(ats_devices);
> +
> +static void parse_ats_param(char *s);
> +custom_param("ats", parse_ats_param);
> +
> +bool_t __read_mostly ats_enabled = 1;
> +
> +static void __init parse_ats_param(char *s)
> +{
> +    char *ss;
> +
> +    do {
> +        ss = strchr(s, ',');
> +        if ( ss )
> +            *ss = '\0';
> +
> +        switch ( parse_bool(s) )
> +        {
> +        case 0:
> +            ats_enabled = 0;
> +            break;
> +        case 1:
> +            ats_enabled = 1;
> +            break;
> +        }
> +
> +        s = ss + 1;
> +    } while ( ss );
> +}
> +
> +int enable_ats_device(int seg, int bus, int devfn)
> +{
> +    struct pci_ats_dev *pdev = NULL;
> +    u32 value;
> +    int pos;
> +
> +    pos = pci_find_ext_capability(seg, bus, devfn, PCI_EXT_CAP_ID_ATS);
> +    BUG_ON(!pos);
> +
> +    if ( iommu_verbose )
> +        dprintk(XENLOG_INFO,
> +                "%04x:%02x:%02x.%u: ATS capability found\n",

Here and below, the two lines can be folded (together they don't
exceed 80 chars per line) now that the VT-d prefix is gone.

Jan

> +                seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn));
> +
> +    value = pci_conf_read16(seg, bus, PCI_SLOT(devfn),
> +                            PCI_FUNC(devfn), pos + ATS_REG_CTL);
> +    if ( value & ATS_ENABLE )
> +    {
> +        list_for_each_entry ( pdev, &ats_devices, list )
> +        {
> +            if ( pdev->seg == seg && pdev->bus == bus && pdev->devfn == devfn )
> +            {
> +                pos = 0;
> +                break;
> +            }
> +        }
> +    }
> +    if ( pos )
> +        pdev = xmalloc(struct pci_ats_dev);
> +    if ( !pdev )
> +        return -ENOMEM;
> +
> +    if ( !(value & ATS_ENABLE) )
> +    {
> +        value |= ATS_ENABLE;
> +        pci_conf_write16(seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn),
> +                         pos + ATS_REG_CTL, value);
> +    }
> +
> +    if ( pos )
> +    {
> +        pdev->seg = seg;
> +        pdev->bus = bus;
> +        pdev->devfn = devfn;
> +        value = pci_conf_read16(seg, bus, PCI_SLOT(devfn),
> +                                PCI_FUNC(devfn), pos + ATS_REG_CAP);
> +        pdev->ats_queue_depth = value & ATS_QUEUE_DEPTH_MASK;
> +        list_add(&pdev->list, &ats_devices);
> +    }
> +
> +    if ( iommu_verbose )
> +        dprintk(XENLOG_INFO,
> +                "%04x:%02x:%02x.%u: ATS %s enabled\n",
> +                seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn),
> +                pos ? "is" : "was");
> +
> +    return pos;
> +}
> +
> +void disable_ats_device(int seg, int bus, int devfn)
> +{
> +    struct pci_ats_dev *pdev;
> +    u32 value;
> +    int pos;
> +
> +    pos = pci_find_ext_capability(seg, bus, devfn, PCI_EXT_CAP_ID_ATS);
> +    BUG_ON(!pos);
> +
> +    value = pci_conf_read16(seg, bus, PCI_SLOT(devfn),
> +                            PCI_FUNC(devfn), pos + ATS_REG_CTL);
> +    value &= ~ATS_ENABLE;
> +    pci_conf_write16(seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn),
> +                     pos + ATS_REG_CTL, value);
> +
> +    list_for_each_entry ( pdev, &ats_devices, list )
> +    {
> +        if ( pdev->seg == seg && pdev->bus == bus && pdev->devfn == devfn )
> +        {
> +            list_del(&pdev->list);
> +            xfree(pdev);
> +            break;
> +        }
> +    }
> +
> +    if ( iommu_verbose )
> +        dprintk(XENLOG_INFO,
> +                "%04x:%02x:%02x.%u: ATS is disabled\n",
> +                seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn));
> +}

^ permalink raw reply	[flat|nested] 15+ messages in thread

* Re: [PATCH 2 of 5] amd iommu: Fix iommu page size encoding when page order > 0
  2011-11-03 10:13 ` [PATCH 2 of 5] amd iommu: Fix iommu page size encoding when page order > 0 Wei Wang
@ 2011-11-03 12:49   ` Jan Beulich
  2011-11-03 12:52     ` Jan Beulich
  2011-11-03 13:26     ` Wei Wang2
  0 siblings, 2 replies; 15+ messages in thread
From: Jan Beulich @ 2011-11-03 12:49 UTC (permalink / raw)
  To: Wei Wang; +Cc: xen-devel

>>> On 03.11.11 at 11:13, Wei Wang <wei.wang2@amd.com> wrote:
> # HG changeset patch
> # User Wei Wang <wei.wang2@amd.com>
> # Date 1320314617 -3600
> # Node ID d0c38cb215cd96e01de27eadf5ec0a5e711de448
> # Parent  d422e3cf7976c76c57fc2d455b784d0fcc24d06b
> amd iommu: Fix iommu page size encoding when page order > 0
> 
> Signed-off-by: Wei Wang <wei.wang2@amd.com>
> 
> diff -r d422e3cf7976 -r d0c38cb215cd xen/drivers/passthrough/amd/iommu_map.c
> --- a/xen/drivers/passthrough/amd/iommu_map.c	Thu Nov 03 11:02:17 2011 +0100
> +++ b/xen/drivers/passthrough/amd/iommu_map.c	Thu Nov 03 11:03:37 2011 +0100
> @@ -77,23 +77,24 @@ static void invalidate_iommu_pages(struc
>  {
>      u64 addr_lo, addr_hi;
>      u32 cmd[4], entry;
> -    u64 mask = 0;
>      int sflag = 0, pde = 0;
>  
> +    ASSERT ( order == 0 || order == 9 || order == 18 );
> +
> +    /* All pages associated with the domainID are invalidated */
> +    if ( order || (io_addr == INV_IOMMU_ALL_PAGES_ADDRESS ) )
> +    {
> +        sflag = 1;
> +        pde = 1;
> +    }
> +
>      /* If sflag == 1, the size of the invalidate command is determined
>       by the first zero bit in the address starting from Address[12] */
> -    if ( order == 9 || order == 18 )
> +    if ( order )
>      {
> -        mask = ((1ULL << (order - 1)) - 1) << PAGE_SHIFT;
> -        io_addr |= mask;
> -        sflag = 1;
> -    }
> -
> -    /* All pages associated with the domainID are invalidated */
> -    else if ( io_addr == 0x7FFFFFFFFFFFF000ULL )

Note the difference between this and your adjusted definition
of INV_IOMMU_ALL_PAGES_ADDRESS. I don't think this is
correct (or else your patch description should say why).

> -    {
> -        sflag = 1;
> -        pde = 1;
> +        u64 mask = 1ULL << (order - 1 + PAGE_SHIFT);
> +        io_addr &= ~mask;
> +        io_addr |= mask - 1;
>      }
>  
>      addr_lo = io_addr & DMA_32BIT_MASK;
> @@ -917,7 +918,7 @@ static void _amd_iommu_flush_pages(struc
>  
>  void amd_iommu_flush_all_pages(struct domain *d)
>  {
> -    _amd_iommu_flush_pages(d, 0x7FFFFFFFFFFFFULL, 0);
> +    _amd_iommu_flush_pages(d, INV_IOMMU_ALL_PAGES_ADDRESS, 0);

Same here, for a slightly different reason.

Jan

>  }
>  
>  void amd_iommu_flush_pages(struct domain *d,
> diff -r d422e3cf7976 -r d0c38cb215cd xen/include/asm-x86/hvm/svm/amd-iommu-defs.h
> --- a/xen/include/asm-x86/hvm/svm/amd-iommu-defs.h	Thu Nov 03 11:02:17 2011 +0100
> +++ b/xen/include/asm-x86/hvm/svm/amd-iommu-defs.h	Thu Nov 03 11:03:37 2011 
> +0100
> @@ -407,4 +407,6 @@
>  #define INT_REMAP_ENTRY_VECTOR_MASK     0x00FF0000
>  #define INT_REMAP_ENTRY_VECTOR_SHIFT    16
>  
> +#define INV_IOMMU_ALL_PAGES_ADDRESS      0x7FFFFFFFFFFFFFFFULL
> +
>  #endif /* _ASM_X86_64_AMD_IOMMU_DEFS_H */

^ permalink raw reply	[flat|nested] 15+ messages in thread

* Re: [PATCH 2 of 5] amd iommu: Fix iommu page size encoding when page order > 0
  2011-11-03 12:49   ` Jan Beulich
@ 2011-11-03 12:52     ` Jan Beulich
  2011-11-03 13:29       ` Wei Wang2
  2011-11-03 13:26     ` Wei Wang2
  1 sibling, 1 reply; 15+ messages in thread
From: Jan Beulich @ 2011-11-03 12:52 UTC (permalink / raw)
  To: Wei Wang; +Cc: xen-devel

>>> On 03.11.11 at 13:49, "Jan Beulich" <JBeulich@suse.com> wrote:
>>>> On 03.11.11 at 11:13, Wei Wang <wei.wang2@amd.com> wrote:
>> # HG changeset patch
>> # User Wei Wang <wei.wang2@amd.com>
>> # Date 1320314617 -3600
>> # Node ID d0c38cb215cd96e01de27eadf5ec0a5e711de448
>> # Parent  d422e3cf7976c76c57fc2d455b784d0fcc24d06b
>> amd iommu: Fix iommu page size encoding when page order > 0
>> 
>> Signed-off-by: Wei Wang <wei.wang2@amd.com>
>> 
>> diff -r d422e3cf7976 -r d0c38cb215cd xen/drivers/passthrough/amd/iommu_map.c
>> --- a/xen/drivers/passthrough/amd/iommu_map.c	Thu Nov 03 11:02:17 2011 +0100
>> +++ b/xen/drivers/passthrough/amd/iommu_map.c	Thu Nov 03 11:03:37 2011 +0100
>> @@ -77,23 +77,24 @@ static void invalidate_iommu_pages(struc
>>  {
>>      u64 addr_lo, addr_hi;
>>      u32 cmd[4], entry;
>> -    u64 mask = 0;
>>      int sflag = 0, pde = 0;
>>  
>> +    ASSERT ( order == 0 || order == 9 || order == 18 );
>> +
>> +    /* All pages associated with the domainID are invalidated */
>> +    if ( order || (io_addr == INV_IOMMU_ALL_PAGES_ADDRESS ) )
>> +    {
>> +        sflag = 1;
>> +        pde = 1;
>> +    }
>> +
>>      /* If sflag == 1, the size of the invalidate command is determined
>>       by the first zero bit in the address starting from Address[12] */
>> -    if ( order == 9 || order == 18 )
>> +    if ( order )
>>      {
>> -        mask = ((1ULL << (order - 1)) - 1) << PAGE_SHIFT;
>> -        io_addr |= mask;
>> -        sflag = 1;
>> -    }
>> -
>> -    /* All pages associated with the domainID are invalidated */
>> -    else if ( io_addr == 0x7FFFFFFFFFFFF000ULL )
> 
> Note the difference between this and your adjusted definition
> of INV_IOMMU_ALL_PAGES_ADDRESS. I don't think this is
> correct (or else your patch description should say why).
> 
>> -    {
>> -        sflag = 1;
>> -        pde = 1;
>> +        u64 mask = 1ULL << (order - 1 + PAGE_SHIFT);
>> +        io_addr &= ~mask;
>> +        io_addr |= mask - 1;
>>      }
>>  
>>      addr_lo = io_addr & DMA_32BIT_MASK;
>> @@ -917,7 +918,7 @@ static void _amd_iommu_flush_pages(struc
>>  
>>  void amd_iommu_flush_all_pages(struct domain *d)
>>  {
>> -    _amd_iommu_flush_pages(d, 0x7FFFFFFFFFFFFULL, 0);
>> +    _amd_iommu_flush_pages(d, INV_IOMMU_ALL_PAGES_ADDRESS, 0);
> 
> Same here, for a slightly different reason.
> 
> Jan
> 
>>  }
>>  
>>  void amd_iommu_flush_pages(struct domain *d,
>> diff -r d422e3cf7976 -r d0c38cb215cd xen/include/asm-x86/hvm/svm/amd-iommu-defs.h
>> --- a/xen/include/asm-x86/hvm/svm/amd-iommu-defs.h	Thu Nov 03 11:02:17 2011 +0100
>> +++ b/xen/include/asm-x86/hvm/svm/amd-iommu-defs.h	Thu Nov 03 11:03:37 2011 
>> +0100
>> @@ -407,4 +407,6 @@
>>  #define INT_REMAP_ENTRY_VECTOR_MASK     0x00FF0000
>>  #define INT_REMAP_ENTRY_VECTOR_SHIFT    16
>>  
>> +#define INV_IOMMU_ALL_PAGES_ADDRESS      0x7FFFFFFFFFFFFFFFULL
>> +

Oh, additionally, this still isn't being expressed by a shift expression,
which makes it still badly readable (one has to count F-s in order to
know what this actually represents).

Jan

>>  #endif /* _ASM_X86_64_AMD_IOMMU_DEFS_H */
> 
> 
> 
> 
> _______________________________________________
> Xen-devel mailing list
> Xen-devel@lists.xensource.com 
> http://lists.xensource.com/xen-devel 

^ permalink raw reply	[flat|nested] 15+ messages in thread

* Re: [PATCH 2 of 5] amd iommu: Fix iommu page size encoding  when page order > 0
  2011-11-03 12:49   ` Jan Beulich
  2011-11-03 12:52     ` Jan Beulich
@ 2011-11-03 13:26     ` Wei Wang2
  2011-11-03 13:28       ` [PATCH 2 of 5] amd iommu: Fix iommu page size encoding when page order> 0 Jan Beulich
  1 sibling, 1 reply; 15+ messages in thread
From: Wei Wang2 @ 2011-11-03 13:26 UTC (permalink / raw)
  To: Jan Beulich; +Cc: xen-devel

On Thursday 03 November 2011 13:49:39 Jan Beulich wrote:
> >>> On 03.11.11 at 11:13, Wei Wang <wei.wang2@amd.com> wrote:
> >
> > # HG changeset patch
> > # User Wei Wang <wei.wang2@amd.com>
> > # Date 1320314617 -3600
> > # Node ID d0c38cb215cd96e01de27eadf5ec0a5e711de448
> > # Parent  d422e3cf7976c76c57fc2d455b784d0fcc24d06b
> > amd iommu: Fix iommu page size encoding when page order > 0
> >
> > Signed-off-by: Wei Wang <wei.wang2@amd.com>
> >
> > diff -r d422e3cf7976 -r d0c38cb215cd
> > xen/drivers/passthrough/amd/iommu_map.c ---
> > a/xen/drivers/passthrough/amd/iommu_map.c	Thu Nov 03 11:02:17 2011 +0100
> > +++ b/xen/drivers/passthrough/amd/iommu_map.c	Thu Nov 03 11:03:37 2011
> > +0100 @@ -77,23 +77,24 @@ static void invalidate_iommu_pages(struc
> >  {
> >      u64 addr_lo, addr_hi;
> >      u32 cmd[4], entry;
> > -    u64 mask = 0;
> >      int sflag = 0, pde = 0;
> >
> > +    ASSERT ( order == 0 || order == 9 || order == 18 );
> > +
> > +    /* All pages associated with the domainID are invalidated */
> > +    if ( order || (io_addr == INV_IOMMU_ALL_PAGES_ADDRESS ) )
> > +    {
> > +        sflag = 1;
> > +        pde = 1;
> > +    }
> > +
> >      /* If sflag == 1, the size of the invalidate command is determined
> >       by the first zero bit in the address starting from Address[12] */
> > -    if ( order == 9 || order == 18 )
> > +    if ( order )
> >      {
> > -        mask = ((1ULL << (order - 1)) - 1) << PAGE_SHIFT;
> > -        io_addr |= mask;
> > -        sflag = 1;
> > -    }
> > -
> > -    /* All pages associated with the domainID are invalidated */
> > -    else if ( io_addr == 0x7FFFFFFFFFFFF000ULL )
>
> Note the difference between this and your adjusted definition
> of INV_IOMMU_ALL_PAGES_ADDRESS. I don't think this is
> correct (or else your patch description should say why).
>
> > -    {
> > -        sflag = 1;
> > -        pde = 1;
> > +        u64 mask = 1ULL << (order - 1 + PAGE_SHIFT);
> > +        io_addr &= ~mask;
> > +        io_addr |= mask - 1;
> >      }
> >
> >      addr_lo = io_addr & DMA_32BIT_MASK;
> > @@ -917,7 +918,7 @@ static void _amd_iommu_flush_pages(struc
> >
> >  void amd_iommu_flush_all_pages(struct domain *d)
> >  {
> > -    _amd_iommu_flush_pages(d, 0x7FFFFFFFFFFFFULL, 0);
> > +    _amd_iommu_flush_pages(d, INV_IOMMU_ALL_PAGES_ADDRESS, 0);
>
> Same here, for a slightly different reason.

The old code is wrong, here should be 0x7FFFFFFFFFFFF000ULL (or 
0x7FFFFFFFFFFFFULL << PAGE_SHIFT)
iommu does not care about the last 12 bits. So in this patch  I just use
INV_IOMMU_ALL_PAGES_ADDRESS = 0x7FFFFFFFFFFFFFFFULL 

Wei 

> Jan
>
> >  }
> >
> >  void amd_iommu_flush_pages(struct domain *d,
> > diff -r d422e3cf7976 -r d0c38cb215cd
> > xen/include/asm-x86/hvm/svm/amd-iommu-defs.h ---
> > a/xen/include/asm-x86/hvm/svm/amd-iommu-defs.h	Thu Nov 03 11:02:17 2011
> > +0100 +++ b/xen/include/asm-x86/hvm/svm/amd-iommu-defs.h	Thu Nov 03
> > 11:03:37 2011 +0100
> > @@ -407,4 +407,6 @@
> >  #define INT_REMAP_ENTRY_VECTOR_MASK     0x00FF0000
> >  #define INT_REMAP_ENTRY_VECTOR_SHIFT    16
> >
> > +#define INV_IOMMU_ALL_PAGES_ADDRESS      0x7FFFFFFFFFFFFFFFULL
> > +
> >  #endif /* _ASM_X86_64_AMD_IOMMU_DEFS_H */

^ permalink raw reply	[flat|nested] 15+ messages in thread

* Re: [PATCH 2 of 5] amd iommu: Fix iommu page size encoding when page order> 0
  2011-11-03 13:26     ` Wei Wang2
@ 2011-11-03 13:28       ` Jan Beulich
  0 siblings, 0 replies; 15+ messages in thread
From: Jan Beulich @ 2011-11-03 13:28 UTC (permalink / raw)
  To: Wei Wang2; +Cc: xen-devel

>>> On 03.11.11 at 14:26, Wei Wang2 <wei.wang2@amd.com> wrote:
> On Thursday 03 November 2011 13:49:39 Jan Beulich wrote:
>> >>> On 03.11.11 at 11:13, Wei Wang <wei.wang2@amd.com> wrote:
>> >
>> > # HG changeset patch
>> > # User Wei Wang <wei.wang2@amd.com>
>> > # Date 1320314617 -3600
>> > # Node ID d0c38cb215cd96e01de27eadf5ec0a5e711de448
>> > # Parent  d422e3cf7976c76c57fc2d455b784d0fcc24d06b
>> > amd iommu: Fix iommu page size encoding when page order > 0
>> >
>> > Signed-off-by: Wei Wang <wei.wang2@amd.com>
>> >
>> > diff -r d422e3cf7976 -r d0c38cb215cd
>> > xen/drivers/passthrough/amd/iommu_map.c ---
>> > a/xen/drivers/passthrough/amd/iommu_map.c	Thu Nov 03 11:02:17 2011 +0100
>> > +++ b/xen/drivers/passthrough/amd/iommu_map.c	Thu Nov 03 11:03:37 2011
>> > +0100 @@ -77,23 +77,24 @@ static void invalidate_iommu_pages(struc
>> >  {
>> >      u64 addr_lo, addr_hi;
>> >      u32 cmd[4], entry;
>> > -    u64 mask = 0;
>> >      int sflag = 0, pde = 0;
>> >
>> > +    ASSERT ( order == 0 || order == 9 || order == 18 );
>> > +
>> > +    /* All pages associated with the domainID are invalidated */
>> > +    if ( order || (io_addr == INV_IOMMU_ALL_PAGES_ADDRESS ) )
>> > +    {
>> > +        sflag = 1;
>> > +        pde = 1;
>> > +    }
>> > +
>> >      /* If sflag == 1, the size of the invalidate command is determined
>> >       by the first zero bit in the address starting from Address[12] */
>> > -    if ( order == 9 || order == 18 )
>> > +    if ( order )
>> >      {
>> > -        mask = ((1ULL << (order - 1)) - 1) << PAGE_SHIFT;
>> > -        io_addr |= mask;
>> > -        sflag = 1;
>> > -    }
>> > -
>> > -    /* All pages associated with the domainID are invalidated */
>> > -    else if ( io_addr == 0x7FFFFFFFFFFFF000ULL )
>>
>> Note the difference between this and your adjusted definition
>> of INV_IOMMU_ALL_PAGES_ADDRESS. I don't think this is
>> correct (or else your patch description should say why).
>>
>> > -    {
>> > -        sflag = 1;
>> > -        pde = 1;
>> > +        u64 mask = 1ULL << (order - 1 + PAGE_SHIFT);
>> > +        io_addr &= ~mask;
>> > +        io_addr |= mask - 1;
>> >      }
>> >
>> >      addr_lo = io_addr & DMA_32BIT_MASK;
>> > @@ -917,7 +918,7 @@ static void _amd_iommu_flush_pages(struc
>> >
>> >  void amd_iommu_flush_all_pages(struct domain *d)
>> >  {
>> > -    _amd_iommu_flush_pages(d, 0x7FFFFFFFFFFFFULL, 0);
>> > +    _amd_iommu_flush_pages(d, INV_IOMMU_ALL_PAGES_ADDRESS, 0);
>>
>> Same here, for a slightly different reason.
> 
> The old code is wrong, here should be 0x7FFFFFFFFFFFF000ULL (or 
> 0x7FFFFFFFFFFFFULL << PAGE_SHIFT)
> iommu does not care about the last 12 bits. So in this patch  I just use
> INV_IOMMU_ALL_PAGES_ADDRESS = 0x7FFFFFFFFFFFFFFFULL 

Okay, in this case please state so in the patch description.

Jan

^ permalink raw reply	[flat|nested] 15+ messages in thread

* Re: Re: [PATCH 2 of 5] amd iommu: Fix iommu page size encoding when page order > 0
  2011-11-03 12:52     ` Jan Beulich
@ 2011-11-03 13:29       ` Wei Wang2
  2011-11-03 13:35         ` Jan Beulich
  0 siblings, 1 reply; 15+ messages in thread
From: Wei Wang2 @ 2011-11-03 13:29 UTC (permalink / raw)
  To: Jan Beulich; +Cc: xen-devel

On Thursday 03 November 2011 13:52:18 Jan Beulich wrote:
> >>> On 03.11.11 at 13:49, "Jan Beulich" <JBeulich@suse.com> wrote:
> >>>> On 03.11.11 at 11:13, Wei Wang <wei.wang2@amd.com> wrote:
> >>
> >> # HG changeset patch
> >> # User Wei Wang <wei.wang2@amd.com>
> >> # Date 1320314617 -3600
> >> # Node ID d0c38cb215cd96e01de27eadf5ec0a5e711de448
> >> # Parent  d422e3cf7976c76c57fc2d455b784d0fcc24d06b
> >> amd iommu: Fix iommu page size encoding when page order > 0
> >>
> >> Signed-off-by: Wei Wang <wei.wang2@amd.com>
> >>
> >> diff -r d422e3cf7976 -r d0c38cb215cd
> >> xen/drivers/passthrough/amd/iommu_map.c ---
> >> a/xen/drivers/passthrough/amd/iommu_map.c	Thu Nov 03 11:02:17 2011 +0100
> >> +++ b/xen/drivers/passthrough/amd/iommu_map.c	Thu Nov 03 11:03:37 2011
> >> +0100 @@ -77,23 +77,24 @@ static void invalidate_iommu_pages(struc
> >>  {
> >>      u64 addr_lo, addr_hi;
> >>      u32 cmd[4], entry;
> >> -    u64 mask = 0;
> >>      int sflag = 0, pde = 0;
> >>
> >> +    ASSERT ( order == 0 || order == 9 || order == 18 );
> >> +
> >> +    /* All pages associated with the domainID are invalidated */
> >> +    if ( order || (io_addr == INV_IOMMU_ALL_PAGES_ADDRESS ) )
> >> +    {
> >> +        sflag = 1;
> >> +        pde = 1;
> >> +    }
> >> +
> >>      /* If sflag == 1, the size of the invalidate command is determined
> >>       by the first zero bit in the address starting from Address[12] */
> >> -    if ( order == 9 || order == 18 )
> >> +    if ( order )
> >>      {
> >> -        mask = ((1ULL << (order - 1)) - 1) << PAGE_SHIFT;
> >> -        io_addr |= mask;
> >> -        sflag = 1;
> >> -    }
> >> -
> >> -    /* All pages associated with the domainID are invalidated */
> >> -    else if ( io_addr == 0x7FFFFFFFFFFFF000ULL )
> >
> > Note the difference between this and your adjusted definition
> > of INV_IOMMU_ALL_PAGES_ADDRESS. I don't think this is
> > correct (or else your patch description should say why).
> >
> >> -    {
> >> -        sflag = 1;
> >> -        pde = 1;
> >> +        u64 mask = 1ULL << (order - 1 + PAGE_SHIFT);
> >> +        io_addr &= ~mask;
> >> +        io_addr |= mask - 1;
> >>      }
> >>
> >>      addr_lo = io_addr & DMA_32BIT_MASK;
> >> @@ -917,7 +918,7 @@ static void _amd_iommu_flush_pages(struc
> >>
> >>  void amd_iommu_flush_all_pages(struct domain *d)
> >>  {
> >> -    _amd_iommu_flush_pages(d, 0x7FFFFFFFFFFFFULL, 0);
> >> +    _amd_iommu_flush_pages(d, INV_IOMMU_ALL_PAGES_ADDRESS, 0);
> >
> > Same here, for a slightly different reason.
> >
> > Jan
> >
> >>  }
> >>
> >>  void amd_iommu_flush_pages(struct domain *d,
> >> diff -r d422e3cf7976 -r d0c38cb215cd
> >> xen/include/asm-x86/hvm/svm/amd-iommu-defs.h ---
> >> a/xen/include/asm-x86/hvm/svm/amd-iommu-defs.h	Thu Nov 03 11:02:17 2011
> >> +0100 +++ b/xen/include/asm-x86/hvm/svm/amd-iommu-defs.h	Thu Nov 03
> >> 11:03:37 2011 +0100
> >> @@ -407,4 +407,6 @@
> >>  #define INT_REMAP_ENTRY_VECTOR_MASK     0x00FF0000
> >>  #define INT_REMAP_ENTRY_VECTOR_SHIFT    16
> >>
> >> +#define INV_IOMMU_ALL_PAGES_ADDRESS      0x7FFFFFFFFFFFFFFFULL
> >> +
>
> Oh, additionally, this still isn't being expressed by a shift expression,
> which makes it still badly readable (one has to count F-s in order to
> know what this actually represents).
Well, this is a copy from the spec.. How about using  (1<<63) -1?
Thanks,
Wei

> Jan
>
> >>  #endif /* _ASM_X86_64_AMD_IOMMU_DEFS_H */
> >
> > _______________________________________________
> > Xen-devel mailing list
> > Xen-devel@lists.xensource.com
> > http://lists.xensource.com/xen-devel

^ permalink raw reply	[flat|nested] 15+ messages in thread

* Re: Re: [PATCH 2 of 5] amd iommu: Fix iommu page size encoding when page order > 0
  2011-11-03 13:29       ` Wei Wang2
@ 2011-11-03 13:35         ` Jan Beulich
  0 siblings, 0 replies; 15+ messages in thread
From: Jan Beulich @ 2011-11-03 13:35 UTC (permalink / raw)
  To: Wei Wang2; +Cc: xen-devel

>>> On 03.11.11 at 14:29, Wei Wang2 <wei.wang2@amd.com> wrote:
> On Thursday 03 November 2011 13:52:18 Jan Beulich wrote:
>> >>> On 03.11.11 at 13:49, "Jan Beulich" <JBeulich@suse.com> wrote:
>> >>>> On 03.11.11 at 11:13, Wei Wang <wei.wang2@amd.com> wrote:
>> >> diff -r d422e3cf7976 -r d0c38cb215cd
>> >> xen/include/asm-x86/hvm/svm/amd-iommu-defs.h ---
>> >> a/xen/include/asm-x86/hvm/svm/amd-iommu-defs.h	Thu Nov 03 11:02:17 2011
>> >> +0100 +++ b/xen/include/asm-x86/hvm/svm/amd-iommu-defs.h	Thu Nov 03
>> >> 11:03:37 2011 +0100
>> >> @@ -407,4 +407,6 @@
>> >>  #define INT_REMAP_ENTRY_VECTOR_MASK     0x00FF0000
>> >>  #define INT_REMAP_ENTRY_VECTOR_SHIFT    16
>> >>
>> >> +#define INV_IOMMU_ALL_PAGES_ADDRESS      0x7FFFFFFFFFFFFFFFULL
>> >> +
>>
>> Oh, additionally, this still isn't being expressed by a shift expression,
>> which makes it still badly readable (one has to count F-s in order to
>> know what this actually represents).
> Well, this is a copy from the spec.. How about using  (1<<63) -1?

Yes, that's what I asked for. Ideally with 63 also given a meaningful
#define (matchable to the spec).

Jan

^ permalink raw reply	[flat|nested] 15+ messages in thread

* Re: [PATCH 1 of 5] ats: Move some ats functions to a new directory
  2011-11-03 15:48 ` [PATCH 1 of 5] ats: Move some ats functions to a new directory Wei Wang
@ 2011-11-03 16:21   ` Jan Beulich
  0 siblings, 0 replies; 15+ messages in thread
From: Jan Beulich @ 2011-11-03 16:21 UTC (permalink / raw)
  To: Wei Wang; +Cc: xen-devel

>>> On 03.11.11 at 16:48, Wei Wang <wei.wang2@amd.com> wrote:
> # HG changeset patch
> # User Wei Wang <wei.wang2@amd.com>
> # Date 1320334551 -3600
> # Node ID ef46c471a11f83d07e256ad2e0b868828f45ef63
> # Parent  119bccb1cc5eee1364bbbd3bd1a30f22e9db703a
> ats: Move some ats functions to a new directory.
> Remove VTD prefix from debug output.
> passhrough/x86 holds vendor neutral codes for x86 architecture.
> 
> Signed-off-by: Wei Wang <wei.wang2@amd.com>

Acked-by: Jan Beulich <jbeulich@suse.com>

> 
> diff -r 119bccb1cc5e -r ef46c471a11f xen/drivers/passthrough/Makefile
> --- a/xen/drivers/passthrough/Makefile	Wed Nov 02 13:53:05 2011 +0100
> +++ b/xen/drivers/passthrough/Makefile	Thu Nov 03 16:35:51 2011 +0100
> @@ -1,6 +1,7 @@
>  subdir-$(x86) += vtd
>  subdir-$(ia64) += vtd
>  subdir-$(x86) += amd
> +subdir-$(x86_64) += x86
>  
>  obj-y += iommu.o
>  obj-y += io.o
> diff -r 119bccb1cc5e -r ef46c471a11f xen/drivers/passthrough/ats.h
> --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
> +++ b/xen/drivers/passthrough/ats.h	Thu Nov 03 16:35:51 2011 +0100
> @@ -0,0 +1,56 @@
> +/*
> + * This program is free software; you can redistribute it and/or modify it
> + * under the terms and conditions of the GNU General Public License,
> + * version 2, as published by the Free Software Foundation.
> + *
> + * This program is distributed in the hope it will be useful, but WITHOUT
> + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
> + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License 
> for
> + * more details.
> + *
> + * You should have received a copy of the GNU General Public License along 
> with
> + * this program; if not, write to the Free Software Foundation, Inc., 59 
> Temple
> + * Place - Suite 330, Boston, MA 02111-1307 USA.
> + */
> +
> +#ifndef _ATS_H_
> +#define _ATS_H_
> +
> +struct pci_ats_dev {
> +    struct list_head list;
> +    u16 seg;
> +    u8 bus;
> +    u8 devfn;
> +    u16 ats_queue_depth;    /* ATS device invalidation queue depth */
> +};
> +
> +#ifdef CONFIG_X86_64
> +
> +#define ATS_REG_CAP    4
> +#define ATS_REG_CTL    6
> +#define ATS_QUEUE_DEPTH_MASK     0xF
> +#define ATS_ENABLE               (1<<15)
> +
> +extern struct list_head ats_devices;
> +extern bool_t ats_enabled;
> +
> +int enable_ats_device(int seg, int bus, int devfn);
> +void disable_ats_device(int seg, int bus, int devfn);
> +
> +#else
> +
> +#define ats_enabled 0
> +static inline int enable_ats_device(int seg, int bus, int devfn)
> +{
> +    BUG();
> +    return -ENOSYS;
> +}
> +
> +static inline void disable_ats_device(int seg, int bus, int devfn)
> +{
> +    BUG();
> +}
> +#endif
> +
> +#endif /* _ATS_H_ */
> +
> diff -r 119bccb1cc5e -r ef46c471a11f xen/drivers/passthrough/vtd/extern.h
> --- a/xen/drivers/passthrough/vtd/extern.h	Wed Nov 02 13:53:05 2011 +0100
> +++ b/xen/drivers/passthrough/vtd/extern.h	Thu Nov 03 16:35:51 2011 +0100
> @@ -57,18 +57,13 @@ struct acpi_drhd_unit * iommu_to_drhd(st
>  struct acpi_rhsa_unit * drhd_to_rhsa(struct acpi_drhd_unit *drhd);
>  
>  #ifdef CONFIG_X86_64
> -extern bool_t ats_enabled;
> -
>  struct acpi_drhd_unit * find_ats_dev_drhd(struct iommu *iommu);
>  
>  int ats_device(const struct pci_dev *, const struct acpi_drhd_unit *);
> -int enable_ats_device(int seg, int bus, int devfn);
> -void disable_ats_device(int seg, int bus, int devfn);
>  
>  int dev_invalidate_iotlb(struct iommu *iommu, u16 did,
>                           u64 addr, unsigned int size_order, u64 type);
>  #else
> -#define ats_enabled 0
>  
>  static inline struct acpi_drhd_unit *find_ats_dev_drhd(struct iommu *iommu)
>  {
> @@ -80,15 +75,6 @@ static inline int ats_device(const struc
>  {
>      return 0;
>  }
> -static inline int enable_ats_device(int seg, int bus, int devfn)
> -{
> -    BUG();
> -    return -ENOSYS;
> -}
> -static inline void disable_ats_device(int seg, int bus, int devfn)
> -{
> -    BUG();
> -}
>  
>  static inline int dev_invalidate_iotlb(struct iommu *iommu, u16 did, u64 
> addr,
>                                         unsigned int size_order, u64 type)
> diff -r 119bccb1cc5e -r ef46c471a11f xen/drivers/passthrough/vtd/iommu.c
> --- a/xen/drivers/passthrough/vtd/iommu.c	Wed Nov 02 13:53:05 2011 +0100
> +++ b/xen/drivers/passthrough/vtd/iommu.c	Thu Nov 03 16:35:51 2011 +0100
> @@ -40,6 +40,7 @@
>  #include "dmar.h"
>  #include "extern.h"
>  #include "vtd.h"
> +#include "../ats.h"
>  
>  #ifdef __ia64__
>  #define nr_ioapics              iosapic_get_nr_iosapics()
> diff -r 119bccb1cc5e -r ef46c471a11f xen/drivers/passthrough/vtd/x86/ats.c
> --- a/xen/drivers/passthrough/vtd/x86/ats.c	Wed Nov 02 13:53:05 2011 +0100
> +++ b/xen/drivers/passthrough/vtd/x86/ats.c	Thu Nov 03 16:35:51 2011 +0100
> @@ -27,51 +27,10 @@
>  #include "../dmar.h"
>  #include "../vtd.h"
>  #include "../extern.h"
> +#include "../../ats.h"
>  
>  static LIST_HEAD(ats_dev_drhd_units);
>  
> -#define ATS_REG_CAP    4
> -#define ATS_REG_CTL    6
> -#define ATS_QUEUE_DEPTH_MASK     0xF
> -#define ATS_ENABLE               (1<<15)
> -
> -struct pci_ats_dev {
> -    struct list_head list;
> -    u16 seg;
> -    u8 bus;
> -    u8 devfn;
> -    u16 ats_queue_depth;    /* ATS device invalidation queue depth */
> -};
> -static LIST_HEAD(ats_devices);
> -
> -static void parse_ats_param(char *s);
> -custom_param("ats", parse_ats_param);
> -
> -bool_t __read_mostly ats_enabled = 1;
> -
> -static void __init parse_ats_param(char *s)
> -{
> -    char *ss;
> -
> -    do {
> -        ss = strchr(s, ',');
> -        if ( ss )
> -            *ss = '\0';
> -
> -        switch ( parse_bool(s) )
> -        {
> -        case 0:
> -            ats_enabled = 0;
> -            break;
> -        case 1:
> -            ats_enabled = 1;
> -            break;
> -        }
> -
> -        s = ss + 1;
> -    } while ( ss );
> -}
> -
>  struct acpi_drhd_unit * find_ats_dev_drhd(struct iommu *iommu)
>  {
>      struct acpi_drhd_unit *drhd;
> @@ -113,97 +72,6 @@ int ats_device(const struct pci_dev *pde
>      return pos;
>  }
>  
> -int enable_ats_device(int seg, int bus, int devfn)
> -{
> -    struct pci_ats_dev *pdev = NULL;
> -    u32 value;
> -    int pos;
> -
> -    pos = pci_find_ext_capability(seg, bus, devfn, PCI_EXT_CAP_ID_ATS);
> -    BUG_ON(!pos);
> -
> -    if ( iommu_verbose )
> -        dprintk(XENLOG_INFO VTDPREFIX,
> -                "%04x:%02x:%02x.%u: ATS capability found\n",
> -                seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn));
> -
> -    value = pci_conf_read16(seg, bus, PCI_SLOT(devfn),
> -                            PCI_FUNC(devfn), pos + ATS_REG_CTL);
> -    if ( value & ATS_ENABLE )
> -    {
> -        list_for_each_entry ( pdev, &ats_devices, list )
> -        {
> -            if ( pdev->seg == seg && pdev->bus == bus && pdev->devfn == devfn )
> -            {
> -                pos = 0;
> -                break;
> -            }
> -        }
> -    }
> -    if ( pos )
> -        pdev = xmalloc(struct pci_ats_dev);
> -    if ( !pdev )
> -        return -ENOMEM;
> -
> -    if ( !(value & ATS_ENABLE) )
> -    {
> -        value |= ATS_ENABLE;
> -        pci_conf_write16(seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn),
> -                         pos + ATS_REG_CTL, value);
> -    }
> -
> -    if ( pos )
> -    {
> -        pdev->seg = seg;
> -        pdev->bus = bus;
> -        pdev->devfn = devfn;
> -        value = pci_conf_read16(seg, bus, PCI_SLOT(devfn),
> -                                PCI_FUNC(devfn), pos + ATS_REG_CAP);
> -        pdev->ats_queue_depth = value & ATS_QUEUE_DEPTH_MASK;
> -        list_add(&pdev->list, &ats_devices);
> -    }
> -
> -    if ( iommu_verbose )
> -        dprintk(XENLOG_INFO VTDPREFIX,
> -                "%04x:%02x:%02x.%u: ATS %s enabled\n",
> -                seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn),
> -                pos ? "is" : "was");
> -
> -    return pos;
> -}
> -
> -void disable_ats_device(int seg, int bus, int devfn)
> -{
> -    struct pci_ats_dev *pdev;
> -    u32 value;
> -    int pos;
> -
> -    pos = pci_find_ext_capability(seg, bus, devfn, PCI_EXT_CAP_ID_ATS);
> -    BUG_ON(!pos);
> -
> -    value = pci_conf_read16(seg, bus, PCI_SLOT(devfn),
> -                            PCI_FUNC(devfn), pos + ATS_REG_CTL);
> -    value &= ~ATS_ENABLE;
> -    pci_conf_write16(seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn),
> -                     pos + ATS_REG_CTL, value);
> -
> -    list_for_each_entry ( pdev, &ats_devices, list )
> -    {
> -        if ( pdev->seg == seg && pdev->bus == bus && pdev->devfn == devfn )
> -        {
> -            list_del(&pdev->list);
> -            xfree(pdev);
> -            break;
> -        }
> -    }
> -
> -    if ( iommu_verbose )
> -        dprintk(XENLOG_INFO VTDPREFIX,
> -                "%04x:%02x:%02x.%u: ATS is disabled\n",
> -                seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn));
> -}
> -
> -
>  static int device_in_domain(struct iommu *iommu, struct pci_ats_dev *pdev, 
> u16 did)
>  {
>      struct root_entry *root_entry = NULL;
> diff -r 119bccb1cc5e -r ef46c471a11f xen/drivers/passthrough/x86/Makefile
> --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
> +++ b/xen/drivers/passthrough/x86/Makefile	Thu Nov 03 16:35:51 2011 +0100
> @@ -0,0 +1,1 @@
> +obj-$(CONFIG_X86_64) += ats.o
> diff -r 119bccb1cc5e -r ef46c471a11f xen/drivers/passthrough/x86/ats.c
> --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
> +++ b/xen/drivers/passthrough/x86/ats.c	Thu Nov 03 16:35:51 2011 +0100
> @@ -0,0 +1,136 @@
> +/*
> + * This program is free software; you can redistribute it and/or modify it
> + * under the terms and conditions of the GNU General Public License,
> + * version 2, as published by the Free Software Foundation.
> + *
> + * This program is distributed in the hope it will be useful, but WITHOUT
> + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
> + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License 
> for
> + * more details.
> + *
> + * You should have received a copy of the GNU General Public License along 
> with
> + * this program; if not, write to the Free Software Foundation, Inc., 59 
> Temple
> + * Place - Suite 330, Boston, MA 02111-1307 USA.
> + */
> +
> +#include <xen/sched.h>
> +#include <xen/pci.h>
> +#include <xen/pci_regs.h>
> +#include "../ats.h"
> +
> +LIST_HEAD(ats_devices);
> +
> +static void parse_ats_param(char *s);
> +custom_param("ats", parse_ats_param);
> +
> +bool_t __read_mostly ats_enabled = 1;
> +
> +static void __init parse_ats_param(char *s)
> +{
> +    char *ss;
> +
> +    do {
> +        ss = strchr(s, ',');
> +        if ( ss )
> +            *ss = '\0';
> +
> +        switch ( parse_bool(s) )
> +        {
> +        case 0:
> +            ats_enabled = 0;
> +            break;
> +        case 1:
> +            ats_enabled = 1;
> +            break;
> +        }
> +
> +        s = ss + 1;
> +    } while ( ss );
> +}
> +
> +int enable_ats_device(int seg, int bus, int devfn)
> +{
> +    struct pci_ats_dev *pdev = NULL;
> +    u32 value;
> +    int pos;
> +
> +    pos = pci_find_ext_capability(seg, bus, devfn, PCI_EXT_CAP_ID_ATS);
> +    BUG_ON(!pos);
> +
> +    if ( iommu_verbose )
> +        dprintk(XENLOG_INFO, "%04x:%02x:%02x.%u: ATS capability found\n",
> +                seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn));
> +
> +    value = pci_conf_read16(seg, bus, PCI_SLOT(devfn),
> +                            PCI_FUNC(devfn), pos + ATS_REG_CTL);
> +    if ( value & ATS_ENABLE )
> +    {
> +        list_for_each_entry ( pdev, &ats_devices, list )
> +        {
> +            if ( pdev->seg == seg && pdev->bus == bus && pdev->devfn == devfn )
> +            {
> +                pos = 0;
> +                break;
> +            }
> +        }
> +    }
> +    if ( pos )
> +        pdev = xmalloc(struct pci_ats_dev);
> +    if ( !pdev )
> +        return -ENOMEM;
> +
> +    if ( !(value & ATS_ENABLE) )
> +    {
> +        value |= ATS_ENABLE;
> +        pci_conf_write16(seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn),
> +                         pos + ATS_REG_CTL, value);
> +    }
> +
> +    if ( pos )
> +    {
> +        pdev->seg = seg;
> +        pdev->bus = bus;
> +        pdev->devfn = devfn;
> +        value = pci_conf_read16(seg, bus, PCI_SLOT(devfn),
> +                                PCI_FUNC(devfn), pos + ATS_REG_CAP);
> +        pdev->ats_queue_depth = value & ATS_QUEUE_DEPTH_MASK;
> +        list_add(&pdev->list, &ats_devices);
> +    }
> +
> +    if ( iommu_verbose )
> +        dprintk(XENLOG_INFO, "%04x:%02x:%02x.%u: ATS %s enabled\n",
> +                seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn),
> +                pos ? "is" : "was");
> +
> +    return pos;
> +}
> +
> +void disable_ats_device(int seg, int bus, int devfn)
> +{
> +    struct pci_ats_dev *pdev;
> +    u32 value;
> +    int pos;
> +
> +    pos = pci_find_ext_capability(seg, bus, devfn, PCI_EXT_CAP_ID_ATS);
> +    BUG_ON(!pos);
> +
> +    value = pci_conf_read16(seg, bus, PCI_SLOT(devfn),
> +                            PCI_FUNC(devfn), pos + ATS_REG_CTL);
> +    value &= ~ATS_ENABLE;
> +    pci_conf_write16(seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn),
> +                     pos + ATS_REG_CTL, value);
> +
> +    list_for_each_entry ( pdev, &ats_devices, list )
> +    {
> +        if ( pdev->seg == seg && pdev->bus == bus && pdev->devfn == devfn )
> +        {
> +            list_del(&pdev->list);
> +            xfree(pdev);
> +            break;
> +        }
> +    }
> +
> +    if ( iommu_verbose )
> +        dprintk(XENLOG_INFO, "%04x:%02x:%02x.%u: ATS is disabled\n",
> +                seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn));
> +}
> 
> 
> _______________________________________________
> Xen-devel mailing list
> Xen-devel@lists.xensource.com 
> http://lists.xensource.com/xen-devel 

^ permalink raw reply	[flat|nested] 15+ messages in thread

* [PATCH 1 of 5] ats: Move some ats functions to a new directory
  2011-11-03 15:48 [PATCH 0 of 5] amd iommu: Add ATS support (v4) Wei Wang
@ 2011-11-03 15:48 ` Wei Wang
  2011-11-03 16:21   ` Jan Beulich
  0 siblings, 1 reply; 15+ messages in thread
From: Wei Wang @ 2011-11-03 15:48 UTC (permalink / raw)
  To: JanJBeulich; +Cc: xen-devel

# HG changeset patch
# User Wei Wang <wei.wang2@amd.com>
# Date 1320334551 -3600
# Node ID ef46c471a11f83d07e256ad2e0b868828f45ef63
# Parent  119bccb1cc5eee1364bbbd3bd1a30f22e9db703a
ats: Move some ats functions to a new directory.
Remove VTD prefix from debug output.
passhrough/x86 holds vendor neutral codes for x86 architecture.

Signed-off-by: Wei Wang <wei.wang2@amd.com>

diff -r 119bccb1cc5e -r ef46c471a11f xen/drivers/passthrough/Makefile
--- a/xen/drivers/passthrough/Makefile	Wed Nov 02 13:53:05 2011 +0100
+++ b/xen/drivers/passthrough/Makefile	Thu Nov 03 16:35:51 2011 +0100
@@ -1,6 +1,7 @@
 subdir-$(x86) += vtd
 subdir-$(ia64) += vtd
 subdir-$(x86) += amd
+subdir-$(x86_64) += x86
 
 obj-y += iommu.o
 obj-y += io.o
diff -r 119bccb1cc5e -r ef46c471a11f xen/drivers/passthrough/ats.h
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/xen/drivers/passthrough/ats.h	Thu Nov 03 16:35:51 2011 +0100
@@ -0,0 +1,56 @@
+/*
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms and conditions of the GNU General Public License,
+ * version 2, as published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * this program; if not, write to the Free Software Foundation, Inc., 59 Temple
+ * Place - Suite 330, Boston, MA 02111-1307 USA.
+ */
+
+#ifndef _ATS_H_
+#define _ATS_H_
+
+struct pci_ats_dev {
+    struct list_head list;
+    u16 seg;
+    u8 bus;
+    u8 devfn;
+    u16 ats_queue_depth;    /* ATS device invalidation queue depth */
+};
+
+#ifdef CONFIG_X86_64
+
+#define ATS_REG_CAP    4
+#define ATS_REG_CTL    6
+#define ATS_QUEUE_DEPTH_MASK     0xF
+#define ATS_ENABLE               (1<<15)
+
+extern struct list_head ats_devices;
+extern bool_t ats_enabled;
+
+int enable_ats_device(int seg, int bus, int devfn);
+void disable_ats_device(int seg, int bus, int devfn);
+
+#else
+
+#define ats_enabled 0
+static inline int enable_ats_device(int seg, int bus, int devfn)
+{
+    BUG();
+    return -ENOSYS;
+}
+
+static inline void disable_ats_device(int seg, int bus, int devfn)
+{
+    BUG();
+}
+#endif
+
+#endif /* _ATS_H_ */
+
diff -r 119bccb1cc5e -r ef46c471a11f xen/drivers/passthrough/vtd/extern.h
--- a/xen/drivers/passthrough/vtd/extern.h	Wed Nov 02 13:53:05 2011 +0100
+++ b/xen/drivers/passthrough/vtd/extern.h	Thu Nov 03 16:35:51 2011 +0100
@@ -57,18 +57,13 @@ struct acpi_drhd_unit * iommu_to_drhd(st
 struct acpi_rhsa_unit * drhd_to_rhsa(struct acpi_drhd_unit *drhd);
 
 #ifdef CONFIG_X86_64
-extern bool_t ats_enabled;
-
 struct acpi_drhd_unit * find_ats_dev_drhd(struct iommu *iommu);
 
 int ats_device(const struct pci_dev *, const struct acpi_drhd_unit *);
-int enable_ats_device(int seg, int bus, int devfn);
-void disable_ats_device(int seg, int bus, int devfn);
 
 int dev_invalidate_iotlb(struct iommu *iommu, u16 did,
                          u64 addr, unsigned int size_order, u64 type);
 #else
-#define ats_enabled 0
 
 static inline struct acpi_drhd_unit *find_ats_dev_drhd(struct iommu *iommu)
 {
@@ -80,15 +75,6 @@ static inline int ats_device(const struc
 {
     return 0;
 }
-static inline int enable_ats_device(int seg, int bus, int devfn)
-{
-    BUG();
-    return -ENOSYS;
-}
-static inline void disable_ats_device(int seg, int bus, int devfn)
-{
-    BUG();
-}
 
 static inline int dev_invalidate_iotlb(struct iommu *iommu, u16 did, u64 addr,
                                        unsigned int size_order, u64 type)
diff -r 119bccb1cc5e -r ef46c471a11f xen/drivers/passthrough/vtd/iommu.c
--- a/xen/drivers/passthrough/vtd/iommu.c	Wed Nov 02 13:53:05 2011 +0100
+++ b/xen/drivers/passthrough/vtd/iommu.c	Thu Nov 03 16:35:51 2011 +0100
@@ -40,6 +40,7 @@
 #include "dmar.h"
 #include "extern.h"
 #include "vtd.h"
+#include "../ats.h"
 
 #ifdef __ia64__
 #define nr_ioapics              iosapic_get_nr_iosapics()
diff -r 119bccb1cc5e -r ef46c471a11f xen/drivers/passthrough/vtd/x86/ats.c
--- a/xen/drivers/passthrough/vtd/x86/ats.c	Wed Nov 02 13:53:05 2011 +0100
+++ b/xen/drivers/passthrough/vtd/x86/ats.c	Thu Nov 03 16:35:51 2011 +0100
@@ -27,51 +27,10 @@
 #include "../dmar.h"
 #include "../vtd.h"
 #include "../extern.h"
+#include "../../ats.h"
 
 static LIST_HEAD(ats_dev_drhd_units);
 
-#define ATS_REG_CAP    4
-#define ATS_REG_CTL    6
-#define ATS_QUEUE_DEPTH_MASK     0xF
-#define ATS_ENABLE               (1<<15)
-
-struct pci_ats_dev {
-    struct list_head list;
-    u16 seg;
-    u8 bus;
-    u8 devfn;
-    u16 ats_queue_depth;    /* ATS device invalidation queue depth */
-};
-static LIST_HEAD(ats_devices);
-
-static void parse_ats_param(char *s);
-custom_param("ats", parse_ats_param);
-
-bool_t __read_mostly ats_enabled = 1;
-
-static void __init parse_ats_param(char *s)
-{
-    char *ss;
-
-    do {
-        ss = strchr(s, ',');
-        if ( ss )
-            *ss = '\0';
-
-        switch ( parse_bool(s) )
-        {
-        case 0:
-            ats_enabled = 0;
-            break;
-        case 1:
-            ats_enabled = 1;
-            break;
-        }
-
-        s = ss + 1;
-    } while ( ss );
-}
-
 struct acpi_drhd_unit * find_ats_dev_drhd(struct iommu *iommu)
 {
     struct acpi_drhd_unit *drhd;
@@ -113,97 +72,6 @@ int ats_device(const struct pci_dev *pde
     return pos;
 }
 
-int enable_ats_device(int seg, int bus, int devfn)
-{
-    struct pci_ats_dev *pdev = NULL;
-    u32 value;
-    int pos;
-
-    pos = pci_find_ext_capability(seg, bus, devfn, PCI_EXT_CAP_ID_ATS);
-    BUG_ON(!pos);
-
-    if ( iommu_verbose )
-        dprintk(XENLOG_INFO VTDPREFIX,
-                "%04x:%02x:%02x.%u: ATS capability found\n",
-                seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn));
-
-    value = pci_conf_read16(seg, bus, PCI_SLOT(devfn),
-                            PCI_FUNC(devfn), pos + ATS_REG_CTL);
-    if ( value & ATS_ENABLE )
-    {
-        list_for_each_entry ( pdev, &ats_devices, list )
-        {
-            if ( pdev->seg == seg && pdev->bus == bus && pdev->devfn == devfn )
-            {
-                pos = 0;
-                break;
-            }
-        }
-    }
-    if ( pos )
-        pdev = xmalloc(struct pci_ats_dev);
-    if ( !pdev )
-        return -ENOMEM;
-
-    if ( !(value & ATS_ENABLE) )
-    {
-        value |= ATS_ENABLE;
-        pci_conf_write16(seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn),
-                         pos + ATS_REG_CTL, value);
-    }
-
-    if ( pos )
-    {
-        pdev->seg = seg;
-        pdev->bus = bus;
-        pdev->devfn = devfn;
-        value = pci_conf_read16(seg, bus, PCI_SLOT(devfn),
-                                PCI_FUNC(devfn), pos + ATS_REG_CAP);
-        pdev->ats_queue_depth = value & ATS_QUEUE_DEPTH_MASK;
-        list_add(&pdev->list, &ats_devices);
-    }
-
-    if ( iommu_verbose )
-        dprintk(XENLOG_INFO VTDPREFIX,
-                "%04x:%02x:%02x.%u: ATS %s enabled\n",
-                seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn),
-                pos ? "is" : "was");
-
-    return pos;
-}
-
-void disable_ats_device(int seg, int bus, int devfn)
-{
-    struct pci_ats_dev *pdev;
-    u32 value;
-    int pos;
-
-    pos = pci_find_ext_capability(seg, bus, devfn, PCI_EXT_CAP_ID_ATS);
-    BUG_ON(!pos);
-
-    value = pci_conf_read16(seg, bus, PCI_SLOT(devfn),
-                            PCI_FUNC(devfn), pos + ATS_REG_CTL);
-    value &= ~ATS_ENABLE;
-    pci_conf_write16(seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn),
-                     pos + ATS_REG_CTL, value);
-
-    list_for_each_entry ( pdev, &ats_devices, list )
-    {
-        if ( pdev->seg == seg && pdev->bus == bus && pdev->devfn == devfn )
-        {
-            list_del(&pdev->list);
-            xfree(pdev);
-            break;
-        }
-    }
-
-    if ( iommu_verbose )
-        dprintk(XENLOG_INFO VTDPREFIX,
-                "%04x:%02x:%02x.%u: ATS is disabled\n",
-                seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn));
-}
-
-
 static int device_in_domain(struct iommu *iommu, struct pci_ats_dev *pdev, u16 did)
 {
     struct root_entry *root_entry = NULL;
diff -r 119bccb1cc5e -r ef46c471a11f xen/drivers/passthrough/x86/Makefile
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/xen/drivers/passthrough/x86/Makefile	Thu Nov 03 16:35:51 2011 +0100
@@ -0,0 +1,1 @@
+obj-$(CONFIG_X86_64) += ats.o
diff -r 119bccb1cc5e -r ef46c471a11f xen/drivers/passthrough/x86/ats.c
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/xen/drivers/passthrough/x86/ats.c	Thu Nov 03 16:35:51 2011 +0100
@@ -0,0 +1,136 @@
+/*
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms and conditions of the GNU General Public License,
+ * version 2, as published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * this program; if not, write to the Free Software Foundation, Inc., 59 Temple
+ * Place - Suite 330, Boston, MA 02111-1307 USA.
+ */
+
+#include <xen/sched.h>
+#include <xen/pci.h>
+#include <xen/pci_regs.h>
+#include "../ats.h"
+
+LIST_HEAD(ats_devices);
+
+static void parse_ats_param(char *s);
+custom_param("ats", parse_ats_param);
+
+bool_t __read_mostly ats_enabled = 1;
+
+static void __init parse_ats_param(char *s)
+{
+    char *ss;
+
+    do {
+        ss = strchr(s, ',');
+        if ( ss )
+            *ss = '\0';
+
+        switch ( parse_bool(s) )
+        {
+        case 0:
+            ats_enabled = 0;
+            break;
+        case 1:
+            ats_enabled = 1;
+            break;
+        }
+
+        s = ss + 1;
+    } while ( ss );
+}
+
+int enable_ats_device(int seg, int bus, int devfn)
+{
+    struct pci_ats_dev *pdev = NULL;
+    u32 value;
+    int pos;
+
+    pos = pci_find_ext_capability(seg, bus, devfn, PCI_EXT_CAP_ID_ATS);
+    BUG_ON(!pos);
+
+    if ( iommu_verbose )
+        dprintk(XENLOG_INFO, "%04x:%02x:%02x.%u: ATS capability found\n",
+                seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn));
+
+    value = pci_conf_read16(seg, bus, PCI_SLOT(devfn),
+                            PCI_FUNC(devfn), pos + ATS_REG_CTL);
+    if ( value & ATS_ENABLE )
+    {
+        list_for_each_entry ( pdev, &ats_devices, list )
+        {
+            if ( pdev->seg == seg && pdev->bus == bus && pdev->devfn == devfn )
+            {
+                pos = 0;
+                break;
+            }
+        }
+    }
+    if ( pos )
+        pdev = xmalloc(struct pci_ats_dev);
+    if ( !pdev )
+        return -ENOMEM;
+
+    if ( !(value & ATS_ENABLE) )
+    {
+        value |= ATS_ENABLE;
+        pci_conf_write16(seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn),
+                         pos + ATS_REG_CTL, value);
+    }
+
+    if ( pos )
+    {
+        pdev->seg = seg;
+        pdev->bus = bus;
+        pdev->devfn = devfn;
+        value = pci_conf_read16(seg, bus, PCI_SLOT(devfn),
+                                PCI_FUNC(devfn), pos + ATS_REG_CAP);
+        pdev->ats_queue_depth = value & ATS_QUEUE_DEPTH_MASK;
+        list_add(&pdev->list, &ats_devices);
+    }
+
+    if ( iommu_verbose )
+        dprintk(XENLOG_INFO, "%04x:%02x:%02x.%u: ATS %s enabled\n",
+                seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn),
+                pos ? "is" : "was");
+
+    return pos;
+}
+
+void disable_ats_device(int seg, int bus, int devfn)
+{
+    struct pci_ats_dev *pdev;
+    u32 value;
+    int pos;
+
+    pos = pci_find_ext_capability(seg, bus, devfn, PCI_EXT_CAP_ID_ATS);
+    BUG_ON(!pos);
+
+    value = pci_conf_read16(seg, bus, PCI_SLOT(devfn),
+                            PCI_FUNC(devfn), pos + ATS_REG_CTL);
+    value &= ~ATS_ENABLE;
+    pci_conf_write16(seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn),
+                     pos + ATS_REG_CTL, value);
+
+    list_for_each_entry ( pdev, &ats_devices, list )
+    {
+        if ( pdev->seg == seg && pdev->bus == bus && pdev->devfn == devfn )
+        {
+            list_del(&pdev->list);
+            xfree(pdev);
+            break;
+        }
+    }
+
+    if ( iommu_verbose )
+        dprintk(XENLOG_INFO, "%04x:%02x:%02x.%u: ATS is disabled\n",
+                seg, bus, PCI_SLOT(devfn), PCI_FUNC(devfn));
+}

^ permalink raw reply	[flat|nested] 15+ messages in thread

end of thread, other threads:[~2011-11-03 16:21 UTC | newest]

Thread overview: 15+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2011-11-03 10:13 [PATCH 0 of 5] amd iommu: Add ATS support (v3) Wei Wang
2011-11-03 10:13 ` [PATCH 1 of 5] ats: Move some ats functions to a new directory Wei Wang
2011-11-03 12:46   ` Jan Beulich
2011-11-03 10:13 ` [PATCH 2 of 5] amd iommu: Fix iommu page size encoding when page order > 0 Wei Wang
2011-11-03 12:49   ` Jan Beulich
2011-11-03 12:52     ` Jan Beulich
2011-11-03 13:29       ` Wei Wang2
2011-11-03 13:35         ` Jan Beulich
2011-11-03 13:26     ` Wei Wang2
2011-11-03 13:28       ` [PATCH 2 of 5] amd iommu: Fix iommu page size encoding when page order> 0 Jan Beulich
2011-11-03 10:13 ` [PATCH 3 of 5] ats: Add new ATS helper functions Wei Wang
2011-11-03 10:13 ` [PATCH 4 of 5] amd iommu: add iotlb invalidation command Wei Wang
2011-11-03 10:13 ` [PATCH 5 of 5] amd iommu: enable ats devices Wei Wang
2011-11-03 15:48 [PATCH 0 of 5] amd iommu: Add ATS support (v4) Wei Wang
2011-11-03 15:48 ` [PATCH 1 of 5] ats: Move some ats functions to a new directory Wei Wang
2011-11-03 16:21   ` Jan Beulich

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.