All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH v10 0/5] iommu: add rmrr Xen command line option
@ 2015-07-13 18:17 elena.ufimtseva
  2015-07-13 18:17 ` [PATCH v10 1/5] dmar: device scope mem leak fix elena.ufimtseva
                   ` (5 more replies)
  0 siblings, 6 replies; 11+ messages in thread
From: elena.ufimtseva @ 2015-07-13 18:17 UTC (permalink / raw)
  To: xen-devel
  Cc: Elena Ufimtseva, kevin.tian, tim, jbeulich, yang.z.zhang,
	boris.ostrovsky

From: Elena Ufimtseva <elena.ufimtseva@oracle.com>

Add Xen command line option rmrr to specify RMRR                                
regions for devices that are not defined in ACPI thus                           
causing IO Page Fault while booting dom0 in PVH mode.                           
These additional regions will be added to the list of                           
RMRR regions parsed from ACPI.                                                  

Changes in v10:
 - incorporate patch 'dmar: device scope mem leak fix' as series requires it.
 - move patch 'pci: add PCI_SBDF and PCI_SEG macros' close to the last patch which uses it;
 
Changes in v9:                                                                  - skip to next RMRR region if current overlaps with any in acpi_rmrr_units;    - fix typos in commit messages;                                                
 - remove clean up chages introduced by mistake in v8;                          
                                                                                
Changes in v8:                                                                  
 - removed bogus debug in patch 1 with non-functional changes;                  
 - changed PRI_RMRRL macro for formatting to reflect the fact that two arguments
   are used, so make it PRI_RMRR(s,e) for formatting inclusive RMRR range;      
   'L' is also removed from macro name, which meant to server as a type of arguments (%lx);
 - added overlapping check with RMRRs from ACPI;                                
 - added check based on paddr_bits for pfn's in extra RMRR range (not sure if   
   its redundant with mfn_valid);                                               
 - addressed while loop exit condition in extra RMRRs parser;                   
                                                            
Elena Ufimtseva (5):
  dmar: device scope mem leak fix
  iommu VT-d: separate rmrr addition function
  pci: add wrapper for parse_pci
  pci: add PCI_SBDF and PCI_SEG macros
  iommu: add rmrr Xen command line option for extra rmrrs

 docs/misc/xen-command-line.markdown |  13 ++
 xen/drivers/passthrough/vtd/dmar.c  | 355 +++++++++++++++++++++++++++++-------
 xen/drivers/pci/pci.c               |  11 ++
 xen/include/xen/pci.h               |   5 +
 4 files changed, 322 insertions(+), 62 deletions(-)

-- 
2.1.3

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

* [PATCH v10 1/5] dmar: device scope mem leak fix
  2015-07-13 18:17 [PATCH v10 0/5] iommu: add rmrr Xen command line option elena.ufimtseva
@ 2015-07-13 18:17 ` elena.ufimtseva
  2015-07-13 18:17 ` [PATCH v10 2/5] iommu VT-d: separate rmrr addition function elena.ufimtseva
                   ` (4 subsequent siblings)
  5 siblings, 0 replies; 11+ messages in thread
From: elena.ufimtseva @ 2015-07-13 18:17 UTC (permalink / raw)
  To: xen-devel
  Cc: Elena Ufimtseva, kevin.tian, tim, jbeulich, yang.z.zhang,
	boris.ostrovsky

From: Elena Ufimtseva <elena.ufimtseva@oracle.com>

Release memory allocated for scope.devices dmar units on various
failure paths and when disabling dmar. Set device count after
sucessfull memory allocation, not before, in device scope parsing function.

Signed-off-by: Elena Ufimtseva <elena.ufimtseva@oracle.com>
---
Changes in v10:
 - mark patch v6 as v10 and include into the series of patches which add RMRR 
   comman line option for Xen;

Changes in v6:
 - eliminated unrelated code move;
 - fix introduces in v5 memory leak;

Changes in v5;
  - xencope_devices_free actually safe;

Changes in v4:
 - make scope_devices_free safe to call with NULL scope pointer;
 - since scope_devices_free is safe to call, use it in failure path
   in acpi_parse_one_drhd;

Changes in v3:
 - make freeing memory for scope devices and zeroing device counter
 as a function;
 - make sure parse_one_rmrr has memory leak fix in this patch;
 - make sure ret values are not lost acpi_parse_one_drhd;

Changes in v2:
 - release memory for devices scope on error paths in acpi_parse_one_drhd
 and acpi_parse_one_atsr and set the count to zero;

drivers/passthrough/vtd/dmar.c | 24 ++++++++++++++++++++++--
 1 file changed, 22 insertions(+), 2 deletions(-)

diff --git a/xen/drivers/passthrough/vtd/dmar.c b/xen/drivers/passthrough/vtd/dmar.c
index 2b07be9..8ed1e24 100644
--- a/xen/drivers/passthrough/vtd/dmar.c
+++ b/xen/drivers/passthrough/vtd/dmar.c
@@ -81,6 +81,15 @@ static int __init acpi_register_rmrr_unit(struct acpi_rmrr_unit *rmrr)
     return 0;
 }
 
+static void scope_devices_free(struct dmar_scope *scope)
+{
+    if ( !scope )
+        return;
+
+    scope->devices_cnt = 0;
+    xfree(scope->devices);
+}
+
 static void __init disable_all_dmar_units(void)
 {
     struct acpi_drhd_unit *drhd, *_drhd;
@@ -90,16 +99,19 @@ static void __init disable_all_dmar_units(void)
     list_for_each_entry_safe ( drhd, _drhd, &acpi_drhd_units, list )
     {
         list_del(&drhd->list);
+        scope_devices_free(&drhd->scope);
         xfree(drhd);
     }
     list_for_each_entry_safe ( rmrr, _rmrr, &acpi_rmrr_units, list )
     {
         list_del(&rmrr->list);
+        scope_devices_free(&rmrr->scope);
         xfree(rmrr);
     }
     list_for_each_entry_safe ( atsr, _atsr, &acpi_atsr_units, list )
     {
         list_del(&atsr->list);
+        scope_devices_free(&atsr->scope);
         xfree(atsr);
     }
 }
@@ -318,13 +330,13 @@ static int __init acpi_parse_dev_scope(
     if ( (cnt = scope_device_count(start, end)) < 0 )
         return cnt;
 
-    scope->devices_cnt = cnt;
     if ( cnt > 0 )
     {
         scope->devices = xzalloc_array(u16, cnt);
         if ( !scope->devices )
             return -ENOMEM;
     }
+    scope->devices_cnt = cnt;
 
     while ( start < end )
     {
@@ -427,7 +439,7 @@ static int __init acpi_parse_dev_scope(
 
  out:
     if ( ret )
-        xfree(scope->devices);
+        scope_devices_free(scope);
 
     return ret;
 }
@@ -542,6 +554,7 @@ acpi_parse_one_drhd(struct acpi_dmar_header *header)
                     "  Workaround BIOS bug: ignore the DRHD due to all "
                     "devices under its scope are not PCI discoverable!\n");
 
+                scope_devices_free(&dmaru->scope);
                 iommu_free(dmaru);
                 xfree(dmaru);
             }
@@ -562,9 +575,11 @@ acpi_parse_one_drhd(struct acpi_dmar_header *header)
 out:
     if ( ret )
     {
+        scope_devices_free(&dmaru->scope);
         iommu_free(dmaru);
         xfree(dmaru);
     }
+
     return ret;
 }
 
@@ -658,6 +673,7 @@ acpi_parse_one_rmrr(struct acpi_dmar_header *header)
                 "  Ignore the RMRR (%"PRIx64", %"PRIx64") due to "
                 "devices under its scope are not PCI discoverable!\n",
                 rmrru->base_address, rmrru->end_address);
+            scope_devices_free(&rmrru->scope);
             xfree(rmrru);
         }
         else if ( base_addr > end_addr )
@@ -665,6 +681,7 @@ acpi_parse_one_rmrr(struct acpi_dmar_header *header)
             dprintk(XENLOG_WARNING VTDPREFIX,
                 "  The RMRR (%"PRIx64", %"PRIx64") is incorrect!\n",
                 rmrru->base_address, rmrru->end_address);
+            scope_devices_free(&rmrru->scope);
             xfree(rmrru);
             ret = -EFAULT;
         }
@@ -727,7 +744,10 @@ acpi_parse_one_atsr(struct acpi_dmar_header *header)
     }
 
     if ( ret )
+    {
+        scope_devices_free(&atsru->scope);
         xfree(atsru);
+    }
     else
         acpi_register_atsr_unit(atsru);
     return ret;
-- 
2.1.3

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

* [PATCH v10 2/5] iommu VT-d: separate rmrr addition function
  2015-07-13 18:17 [PATCH v10 0/5] iommu: add rmrr Xen command line option elena.ufimtseva
  2015-07-13 18:17 ` [PATCH v10 1/5] dmar: device scope mem leak fix elena.ufimtseva
@ 2015-07-13 18:17 ` elena.ufimtseva
  2015-07-13 18:18 ` [PATCH v10 3/5] pci: add wrapper for parse_pci elena.ufimtseva
                   ` (3 subsequent siblings)
  5 siblings, 0 replies; 11+ messages in thread
From: elena.ufimtseva @ 2015-07-13 18:17 UTC (permalink / raw)
  To: xen-devel
  Cc: Elena Ufimtseva, kevin.tian, tim, jbeulich, yang.z.zhang,
	boris.ostrovsky

From: Elena Ufimtseva <elena.ufimtseva@oracle.com>

In preparation for auxiliary RMRR data provided on Xen
command line, make RMRR adding a separate function.
Also free memory for rmrr device scope in error path.

Signed-off-by: Elena Ufimtseva <elena.ufimtseva@oracle.com>
Reviewed-by: Konrad Rzeszutek Wilk <konrad.wilk@oracle.com>
---
 xen/drivers/passthrough/vtd/dmar.c | 126 +++++++++++++++++++------------------
 1 file changed, 65 insertions(+), 61 deletions(-)

diff --git a/xen/drivers/passthrough/vtd/dmar.c b/xen/drivers/passthrough/vtd/dmar.c
index 8ed1e24..93f10fd 100644
--- a/xen/drivers/passthrough/vtd/dmar.c
+++ b/xen/drivers/passthrough/vtd/dmar.c
@@ -583,6 +583,68 @@ out:
     return ret;
 }
 
+static int register_one_rmrr(struct acpi_rmrr_unit *rmrru)
+{
+    bool_t ignore = 0;
+    unsigned int i = 0;
+    int ret = 0;
+
+    /* Skip checking if segment is not accessible yet. */
+    if ( !pci_known_segment(rmrru->segment) )
+        i = UINT_MAX;
+
+    for ( ; i < rmrru->scope.devices_cnt; i++ )
+    {
+        u8 b = PCI_BUS(rmrru->scope.devices[i]);
+        u8 d = PCI_SLOT(rmrru->scope.devices[i]);
+        u8 f = PCI_FUNC(rmrru->scope.devices[i]);
+
+        if ( pci_device_detect(rmrru->segment, b, d, f) == 0 )
+        {
+            dprintk(XENLOG_WARNING VTDPREFIX,
+                    " Non-existent device (%04x:%02x:%02x.%u) is reported"
+                    " in RMRR (%"PRIx64", %"PRIx64")'s scope!\n",
+                    rmrru->segment, b, d, f,
+                    rmrru->base_address, rmrru->end_address);
+            ignore = 1;
+        }
+        else
+        {
+            ignore = 0;
+            break;
+        }
+    }
+
+    if ( ignore )
+    {
+        dprintk(XENLOG_WARNING VTDPREFIX,
+                "  Ignore the RMRR (%"PRIx64", %"PRIx64") due to "
+                "devices under its scope are not PCI discoverable!\n",
+            rmrru->base_address, rmrru->end_address);
+        scope_devices_free(&rmrru->scope);
+        xfree(rmrru);
+    }
+    else if ( rmrru->base_address > rmrru->end_address )
+    {
+        dprintk(XENLOG_WARNING VTDPREFIX,
+                "  The RMRR (%"PRIx64", %"PRIx64") is incorrect!\n",
+                rmrru->base_address, rmrru->end_address);
+        scope_devices_free(&rmrru->scope);
+        xfree(rmrru);
+        ret = -EFAULT;
+    }
+    else
+    {
+        if ( iommu_verbose )
+            dprintk(VTDPREFIX,
+                    "  RMRR region: base_addr %"PRIx64" end_address %"PRIx64"\n",
+                    rmrru->base_address, rmrru->end_address);
+        acpi_register_rmrr_unit(rmrru);
+    }
+
+    return ret;
+}
+
 static int __init
 acpi_parse_one_rmrr(struct acpi_dmar_header *header)
 {
@@ -633,68 +695,10 @@ acpi_parse_one_rmrr(struct acpi_dmar_header *header)
     ret = acpi_parse_dev_scope(dev_scope_start, dev_scope_end,
                                &rmrru->scope, RMRR_TYPE, rmrr->segment);
 
-    if ( ret || (rmrru->scope.devices_cnt == 0) )
-        xfree(rmrru);
+    if ( !ret && (rmrru->scope.devices_cnt != 0) )
+        register_one_rmrr(rmrru);
     else
-    {
-        u8 b, d, f;
-        bool_t ignore = 0;
-        unsigned int i = 0;
-
-        /* Skip checking if segment is not accessible yet. */
-        if ( !pci_known_segment(rmrr->segment) )
-            i = UINT_MAX;
-
-        for ( ; i < rmrru->scope.devices_cnt; i++ )
-        {
-            b = PCI_BUS(rmrru->scope.devices[i]);
-            d = PCI_SLOT(rmrru->scope.devices[i]);
-            f = PCI_FUNC(rmrru->scope.devices[i]);
-
-            if ( !pci_device_detect(rmrr->segment, b, d, f) )
-            {
-                dprintk(XENLOG_WARNING VTDPREFIX,
-                        " Non-existent device (%04x:%02x:%02x.%u) is reported"
-                        " in RMRR (%"PRIx64", %"PRIx64")'s scope!\n",
-                        rmrr->segment, b, d, f,
-                        rmrru->base_address, rmrru->end_address);
-                ignore = 1;
-            }
-            else
-            {
-                ignore = 0;
-                break;
-            }
-        }
-
-        if ( ignore )
-        {
-            dprintk(XENLOG_WARNING VTDPREFIX,
-                "  Ignore the RMRR (%"PRIx64", %"PRIx64") due to "
-                "devices under its scope are not PCI discoverable!\n",
-                rmrru->base_address, rmrru->end_address);
-            scope_devices_free(&rmrru->scope);
-            xfree(rmrru);
-        }
-        else if ( base_addr > end_addr )
-        {
-            dprintk(XENLOG_WARNING VTDPREFIX,
-                "  The RMRR (%"PRIx64", %"PRIx64") is incorrect!\n",
-                rmrru->base_address, rmrru->end_address);
-            scope_devices_free(&rmrru->scope);
-            xfree(rmrru);
-            ret = -EFAULT;
-        }
-        else
-        {
-            if ( iommu_verbose )
-                dprintk(VTDPREFIX,
-                        "  RMRR region: base_addr %"PRIx64
-                        " end_address %"PRIx64"\n",
-                        rmrru->base_address, rmrru->end_address);
-            acpi_register_rmrr_unit(rmrru);
-        }
-    }
+        xfree(rmrru);
 
     return ret;
 }
-- 
2.1.3

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

* [PATCH v10 3/5] pci: add wrapper for parse_pci
  2015-07-13 18:17 [PATCH v10 0/5] iommu: add rmrr Xen command line option elena.ufimtseva
  2015-07-13 18:17 ` [PATCH v10 1/5] dmar: device scope mem leak fix elena.ufimtseva
  2015-07-13 18:17 ` [PATCH v10 2/5] iommu VT-d: separate rmrr addition function elena.ufimtseva
@ 2015-07-13 18:18 ` elena.ufimtseva
  2015-07-13 18:18 ` [PATCH v10 4/5] pci: add PCI_SBDF and PCI_SEG macros elena.ufimtseva
                   ` (2 subsequent siblings)
  5 siblings, 0 replies; 11+ messages in thread
From: elena.ufimtseva @ 2015-07-13 18:18 UTC (permalink / raw)
  To: xen-devel
  Cc: Elena Ufimtseva, kevin.tian, tim, jbeulich, yang.z.zhang,
	boris.ostrovsky

From: Elena Ufimtseva <elena.ufimtseva@oracle.com>

For sbdf's parsing in RMRR command line add __parse_pci with additional
parameter def_seg. __parse_pci will help to identify if segment was
found in string being parsed or default segment was used.
Make a wrapper parse_pci so the rest of the callers are not affected.

Signed-off-by: Elena Ufimtseva <elena.ufimtseva@oracle.com>
Acked-by: Jan Beulich <jbeulich@suse.com>
---
 xen/drivers/pci/pci.c | 11 +++++++++++
 xen/include/xen/pci.h |  3 +++
 2 files changed, 14 insertions(+)

diff --git a/xen/drivers/pci/pci.c b/xen/drivers/pci/pci.c
index ca07ed0..788a356 100644
--- a/xen/drivers/pci/pci.c
+++ b/xen/drivers/pci/pci.c
@@ -119,11 +119,21 @@ const char *__init parse_pci(const char *s, unsigned int *seg_p,
                              unsigned int *bus_p, unsigned int *dev_p,
                              unsigned int *func_p)
 {
+    bool_t def_seg;
+
+    return __parse_pci(s, seg_p, bus_p, dev_p, func_p, &def_seg);
+}
+
+const char *__init __parse_pci(const char *s, unsigned int *seg_p,
+                             unsigned int *bus_p, unsigned int *dev_p,
+                             unsigned int *func_p, bool_t *def_seg)
+{
     unsigned long seg = simple_strtoul(s, &s, 16), bus, dev, func;
 
     if ( *s != ':' )
         return NULL;
     bus = simple_strtoul(s + 1, &s, 16);
+    *def_seg = 0;
     if ( *s == ':' )
         dev = simple_strtoul(s + 1, &s, 16);
     else
@@ -131,6 +141,7 @@ const char *__init parse_pci(const char *s, unsigned int *seg_p,
         dev = bus;
         bus = seg;
         seg = 0;
+        *def_seg = 1;
     }
     if ( func_p )
     {
diff --git a/xen/include/xen/pci.h b/xen/include/xen/pci.h
index 3908146..36e8cd3 100644
--- a/xen/include/xen/pci.h
+++ b/xen/include/xen/pci.h
@@ -148,6 +148,9 @@ int pci_find_ext_capability(int seg, int bus, int devfn, int cap);
 int pci_find_next_ext_capability(int seg, int bus, int devfn, int pos, int cap);
 const char *parse_pci(const char *, unsigned int *seg, unsigned int *bus,
                       unsigned int *dev, unsigned int *func);
+const char *__parse_pci(const char *, unsigned int *seg, unsigned int *bus,
+                      unsigned int *dev, unsigned int *func, bool_t *def_seg);
+
 
 bool_t pcie_aer_get_firmware_first(const struct pci_dev *);
 
-- 
2.1.3

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

* [PATCH v10 4/5] pci: add PCI_SBDF and PCI_SEG macros
  2015-07-13 18:17 [PATCH v10 0/5] iommu: add rmrr Xen command line option elena.ufimtseva
                   ` (2 preceding siblings ...)
  2015-07-13 18:18 ` [PATCH v10 3/5] pci: add wrapper for parse_pci elena.ufimtseva
@ 2015-07-13 18:18 ` elena.ufimtseva
  2015-07-13 18:18 ` [PATCH v10 5/5] iommu: add rmrr Xen command line option for extra rmrrs elena.ufimtseva
  2015-07-14 10:18 ` [PATCH v10 0/5] iommu: add rmrr Xen command line option Jan Beulich
  5 siblings, 0 replies; 11+ messages in thread
From: elena.ufimtseva @ 2015-07-13 18:18 UTC (permalink / raw)
  To: xen-devel
  Cc: Elena Ufimtseva, kevin.tian, tim, jbeulich, yang.z.zhang,
	boris.ostrovsky

From: Elena Ufimtseva <elena.ufimtseva@oracle.com>

In preperation for patch "iommu: add rmrr Xen command line option for
extra rmrrs" which will use it.

Signed-off-by: Elena Ufimtseva <elena.ufimtseva@oracle.com>
---
 xen/include/xen/pci.h | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/xen/include/xen/pci.h b/xen/include/xen/pci.h
index 36e8cd3..d66ecab 100644
--- a/xen/include/xen/pci.h
+++ b/xen/include/xen/pci.h
@@ -33,6 +33,8 @@
 #define PCI_DEVFN2(bdf) ((bdf) & 0xff)
 #define PCI_BDF(b,d,f)  ((((b) & 0xff) << 8) | PCI_DEVFN(d,f))
 #define PCI_BDF2(b,df)  ((((b) & 0xff) << 8) | ((df) & 0xff))
+#define PCI_SBDF(s,b,d,f) ((((s) & 0xffff) << 16) | PCI_BDF(b,d,f))
+#define PCI_SEG(sbdf) (((sbdf) >> 16) & 0xffff)
 
 struct pci_dev_info {
     bool_t is_extfn;
-- 
2.1.3

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

* [PATCH v10 5/5] iommu: add rmrr Xen command line option for extra rmrrs
  2015-07-13 18:17 [PATCH v10 0/5] iommu: add rmrr Xen command line option elena.ufimtseva
                   ` (3 preceding siblings ...)
  2015-07-13 18:18 ` [PATCH v10 4/5] pci: add PCI_SBDF and PCI_SEG macros elena.ufimtseva
@ 2015-07-13 18:18 ` elena.ufimtseva
  2015-07-14 10:43   ` Jan Beulich
  2015-07-14 10:18 ` [PATCH v10 0/5] iommu: add rmrr Xen command line option Jan Beulich
  5 siblings, 1 reply; 11+ messages in thread
From: elena.ufimtseva @ 2015-07-13 18:18 UTC (permalink / raw)
  To: xen-devel
  Cc: Elena Ufimtseva, kevin.tian, tim, jbeulich, yang.z.zhang,
	boris.ostrovsky

From: Elena Ufimtseva <elena.ufimtseva@oracle.com>

On some platforms RMRR regions may be not specified
in ACPI and thus will not be mapped 1:1 in dom0. This
causes IO Page Faults and prevents dom0 from booting
in PVH mode.
New Xen command line option rmrr allows to specify
such devices and memory regions. These regions are added
to the list of RMRR defined in ACPI if the device
is present in system. As a result, additional RMRRs will
be mapped 1:1 in dom0 with correct permissions.

Mentioned above problems were discovered during PVH work with
ThinkCentre M and Dell 5600T. No official documentation
was found so far in regards to what devices and why cause this.
Experiments show that ThinkCentre M USB devices with enabled
debug port generate DMA read transactions to the regions of
memory marked reserved in host e820 map.
For Dell 5600T the device and faulting addresses are not found yet.

For detailed history of the discussion please check following threads:
http://lists.Xen.org/archives/html/xen-devel/2015-02/msg01724.html
http://lists.Xen.org/archives/html/xen-devel/2015-01/msg02513.html

Format for rmrr Xen command line option:
rmrr=start<-end>=[s1]bdf1[,[s1]bdf2[,...]];start<-end>=[s2]bdf1[,[s2]bdf2[,...]]
If grub2 used and multiple ranges are specified, ';' should be
quoted/escaped, refer to grub2 manual for more information.

Signed-off-by: Elena Ufimtseva <elena.ufimtseva@oracle.com>
Reviewed-by: Konrad Rzeszutek Wilk <konrad.wilk@oracle.com>
---
 docs/misc/xen-command-line.markdown |  13 +++
 xen/drivers/passthrough/vtd/dmar.c  | 209 +++++++++++++++++++++++++++++++++++-
 2 files changed, 221 insertions(+), 1 deletion(-)

diff --git a/docs/misc/xen-command-line.markdown b/docs/misc/xen-command-line.markdown
index aa684c0..f307f3d 100644
--- a/docs/misc/xen-command-line.markdown
+++ b/docs/misc/xen-command-line.markdown
@@ -1197,6 +1197,19 @@ Specify the host reboot method.
 'efi' instructs Xen to reboot using the EFI reboot call (in EFI mode by
  default it will use that method first).
 
+### rmrr
+> '= start<-end>=[s1]bdf1[,[s1]bdf2[,...]];start<-end>=[s2]bdf1[,[s2]bdf2[,...]]
+
+Define RMRR units that are missing from ACPI table along with device they
+belong to and use them for 1:1 mapping. End addresses can be omitted and one
+page will be mapped. The ranges are inclusive when start and end are specified.
+If segment of the first device is not specified, segment zero will be used.
+If other segments are not specified, first device segment will be used.
+If a segment is specified for other than the first device and it does not match
+the one specified for the first one, an error will be reported.
+Note: grub2 requires to escape or use quotations if special characters are used,
+namely ';', refer to the grub2 documentation if multiple ranges are specified.
+
 ### ro-hpet
 > `= <boolean>`
 
diff --git a/xen/drivers/passthrough/vtd/dmar.c b/xen/drivers/passthrough/vtd/dmar.c
index 93f10fd..61e8f28 100644
--- a/xen/drivers/passthrough/vtd/dmar.c
+++ b/xen/drivers/passthrough/vtd/dmar.c
@@ -867,6 +867,145 @@ out:
     return ret;
 }
 
+#define MAX_EXTRA_RMRR_PAGES 16
+#define MAX_EXTRA_RMRR 10
+
+/* RMRR units derived from command line rmrr option. */
+#define MAX_EXTRA_RMRR_DEV 20
+struct extra_rmrr_unit {
+    struct list_head list;
+    unsigned long base_pfn, end_pfn;
+    unsigned int dev_count;
+    u32    sbdf[MAX_EXTRA_RMRR_DEV];
+};
+static __initdata unsigned int nr_rmrr;
+static struct __initdata extra_rmrr_unit extra_rmrr_units[MAX_EXTRA_RMRR];
+
+/* Macro for RMRR inclusive range formatting. */
+#define PRI_RMRR(s,e) "[%lx-%lx]"
+
+static void __init add_extra_rmrr(void)
+{
+    struct acpi_rmrr_unit *acpi_rmrr;
+    struct acpi_rmrr_unit *rmrru;
+    unsigned int dev, seg, i, j;
+    unsigned long pfn;
+    bool_t overlap;
+
+    for ( i = 0; i < nr_rmrr; i++ )
+    {
+        if ( extra_rmrr_units[i].base_pfn > extra_rmrr_units[i].end_pfn )
+        {
+            printk(XENLOG_ERR VTDPREFIX
+                   "Invalid RMRR Range "PRI_RMRR(s,e)"\n",
+                   extra_rmrr_units[i].base_pfn, extra_rmrr_units[i].end_pfn);
+            continue;
+        }
+
+        if ( extra_rmrr_units[i].end_pfn - extra_rmrr_units[i].base_pfn >=
+             MAX_EXTRA_RMRR_PAGES )
+        {
+            printk(XENLOG_ERR VTDPREFIX
+                   "RMRR range "PRI_RMRR(s,e)" exceeds "__stringify(MAX_EXTRA_RMRR_PAGES)" pages\n",
+                   extra_rmrr_units[i].base_pfn, extra_rmrr_units[i].end_pfn);
+            continue;
+        }
+
+        for ( j = 0; j < nr_rmrr; j++ )
+        {
+            if ( i != j &&
+                 extra_rmrr_units[i].base_pfn <= extra_rmrr_units[j].end_pfn &&
+                 extra_rmrr_units[j].base_pfn <= extra_rmrr_units[i].end_pfn )
+            {
+                printk(XENLOG_ERR VTDPREFIX
+                      "Overlapping RMRRs "PRI_RMRR(s,e)" and "PRI_RMRR(s,e)"\n",
+                      extra_rmrr_units[i].base_pfn, extra_rmrr_units[i].end_pfn,
+                      extra_rmrr_units[j].base_pfn, extra_rmrr_units[j].end_pfn);
+                break;
+            }
+        }
+        /* Broke out of the overlap loop check, continue with next rmrr. */
+        if ( j < nr_rmrr )
+            continue;
+        overlap = 0;
+        list_for_each_entry(rmrru, &acpi_rmrr_units, list)
+        {
+            if ( pfn_to_paddr(extra_rmrr_units[i].base_pfn <= rmrru->end_address) &&
+                 rmrru->base_address <= pfn_to_paddr(extra_rmrr_units[i].end_pfn) )
+            {
+                printk(XENLOG_ERR VTDPREFIX
+                       "Overlapping extra RMRRs "PRI_RMRR(s,e)" and ACPI RMRRs "PRI_RMRR(s,e)"\n",
+                       extra_rmrr_units[i].base_pfn,
+                       extra_rmrr_units[i].end_pfn,
+                       paddr_to_pfn(rmrru->base_address),
+                       paddr_to_pfn(rmrru->end_address));
+                overlap = 1;
+                break;
+            }
+        }
+        /* Continue to next RMRR is this one overlaps with one from ACPI. */
+        if ( overlap )
+            continue;
+
+        pfn = extra_rmrr_units[i].base_pfn;
+        do
+        {
+            if ( !mfn_valid(pfn) || (pfn >> (paddr_bits - PAGE_SHIFT)) )
+            {
+                printk(XENLOG_ERR VTDPREFIX
+                       "Invalid pfn in RMRR range "PRI_RMRR(s,e)"\n",
+                       extra_rmrr_units[i].base_pfn, extra_rmrr_units[i].end_pfn);
+                break;
+            }
+        } while ( pfn++ <= extra_rmrr_units[i].end_pfn );
+        /* The range had invalid pfn as the loop was broken out before reaching end_pfn. */
+        if ( pfn <= extra_rmrr_units[i].end_pfn )
+            continue;
+
+        acpi_rmrr = xzalloc(struct acpi_rmrr_unit);
+        if ( !acpi_rmrr )
+            return;
+
+        acpi_rmrr->scope.devices = xmalloc_array(u16,
+                                                 extra_rmrr_units[i].dev_count);
+        if ( !acpi_rmrr->scope.devices )
+        {
+            xfree(acpi_rmrr);
+            return;
+        }
+
+        seg = 0;
+        for ( dev = 0; dev < extra_rmrr_units[i].dev_count; dev++ )
+        {
+            acpi_rmrr->scope.devices[dev] = extra_rmrr_units[i].sbdf[dev];
+            seg = seg | PCI_SEG(extra_rmrr_units[i].sbdf[dev]);
+        }
+        if ( seg != PCI_SEG(extra_rmrr_units[i].sbdf[0]) )
+        {
+            printk(XENLOG_ERR VTDPREFIX
+                   "Segments are not equal for RMRR range "PRI_RMRR(s,e)"\n",
+                   extra_rmrr_units[i].base_pfn, extra_rmrr_units[i].end_pfn);
+            scope_devices_free(&acpi_rmrr->scope);
+            xfree(acpi_rmrr);
+            continue;
+        }
+
+        acpi_rmrr->segment = seg;
+        acpi_rmrr->base_address = pfn_to_paddr(extra_rmrr_units[i].base_pfn);
+        acpi_rmrr->end_address = pfn_to_paddr(extra_rmrr_units[i].end_pfn + 1);
+        acpi_rmrr->scope.devices_cnt = extra_rmrr_units[i].dev_count;
+
+        if ( register_one_rmrr(acpi_rmrr) )
+        {
+            printk(XENLOG_ERR VTDPREFIX
+                   "Could not register RMMR range "PRI_RMRR(s,e)"\n",
+                   extra_rmrr_units[i].base_pfn, extra_rmrr_units[i].end_pfn);
+            scope_devices_free(&acpi_rmrr->scope);
+            xfree(acpi_rmrr);
+        }
+    }
+}
+
 #include <asm/tboot.h>
 /* ACPI tables may not be DMA protected by tboot, so use DMAR copy */
 /* SINIT saved in SinitMleData in TXT heap (which is DMA protected) */
@@ -876,6 +1015,7 @@ int __init acpi_dmar_init(void)
 {
     acpi_physical_address dmar_addr;
     acpi_native_uint dmar_len;
+    int ret;
 
     if ( ACPI_SUCCESS(acpi_get_table_phys(ACPI_SIG_DMAR, 0,
                                           &dmar_addr, &dmar_len)) )
@@ -886,7 +1026,10 @@ int __init acpi_dmar_init(void)
         dmar_table = __va(dmar_addr);
     }
 
-    return parse_dmar_table(acpi_parse_dmar);
+    ret = parse_dmar_table(acpi_parse_dmar);
+    add_extra_rmrr();
+
+    return ret;
 }
 
 void acpi_dmar_reinstate(void)
@@ -917,3 +1060,67 @@ int platform_supports_x2apic(void)
     unsigned int mask = ACPI_DMAR_INTR_REMAP | ACPI_DMAR_X2APIC_OPT_OUT;
     return cpu_has_x2apic && ((dmar_flags & mask) == ACPI_DMAR_INTR_REMAP);
 }
+
+/*
+ * Parse rmrr Xen command line options and add parsed device and region into
+ * acpi_rmrr_unit list to mapped as RMRRs parsed from ACPI.
+ * Format:
+ * rmrr=start<-end>=[s1]bdf1[,[s1]bdf2[,...]];start<-end>=[s2]bdf1[,[s2]bdf2[,...]]
+ * If the segment of the first device is not specified, segment zero will be used.
+ * If other segments are not specified, first device segment will be used.
+ * If a segment is specified for other than the first device and it does not match
+ * the one specified for the first one, an error will be reported.
+ */
+static void __init parse_rmrr_param(const char *str)
+{
+    const char *s = str, *cur, *stmp;
+    unsigned int seg, bus, dev, func;
+    unsigned long start, end;
+
+    do {
+        start = simple_strtoul(cur = s, &s, 0);
+        if ( cur == s )
+            break;
+
+        if ( *s == '-' )
+        {
+            end = simple_strtoul(cur = s + 1, &s, 0);
+            if ( cur == s )
+                break;
+        }
+        else
+            end = start;
+
+        extra_rmrr_units[nr_rmrr].base_pfn = start;
+        extra_rmrr_units[nr_rmrr].end_pfn = end;
+        extra_rmrr_units[nr_rmrr].dev_count = 0;
+
+        if ( *s != '=' )
+            continue;
+
+        do {
+            bool_t default_segment = 0;
+
+            if ( *s == ';' )
+                break;
+            stmp = __parse_pci(s + 1, &seg, &bus, &dev, &func, &default_segment);
+            if ( !stmp )
+                break;
+
+            /* Not specified segment will be replaced with one from first device. */
+            if ( extra_rmrr_units[nr_rmrr].dev_count && default_segment )
+                seg = PCI_SEG(extra_rmrr_units[nr_rmrr].sbdf[0]);
+
+            /* Keep sbdf's even if they differ and later report an error. */
+            extra_rmrr_units[nr_rmrr].sbdf[extra_rmrr_units[nr_rmrr].dev_count] = PCI_SBDF(seg, bus, dev, func);
+            extra_rmrr_units[nr_rmrr].dev_count++;
+            s = stmp;
+        } while ( (*s == ',' || *s ) &&
+                  extra_rmrr_units[nr_rmrr].dev_count < MAX_EXTRA_RMRR_DEV );
+
+        if ( extra_rmrr_units[nr_rmrr].dev_count )
+            nr_rmrr++;
+
+    } while ( *s++ == ';' && nr_rmrr < MAX_EXTRA_RMRR );
+}
+custom_param("rmrr", parse_rmrr_param);
-- 
2.1.3

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

* Re: [PATCH v10 0/5] iommu: add rmrr Xen command line option
  2015-07-13 18:17 [PATCH v10 0/5] iommu: add rmrr Xen command line option elena.ufimtseva
                   ` (4 preceding siblings ...)
  2015-07-13 18:18 ` [PATCH v10 5/5] iommu: add rmrr Xen command line option for extra rmrrs elena.ufimtseva
@ 2015-07-14 10:18 ` Jan Beulich
  5 siblings, 0 replies; 11+ messages in thread
From: Jan Beulich @ 2015-07-14 10:18 UTC (permalink / raw)
  To: elena.ufimtseva; +Cc: kevin.tian, tim, xen-devel, yang.z.zhang, boris.ostrovsky

>>> On 13.07.15 at 20:17, <elena.ufimtseva@oracle.com> wrote:
> From: Elena Ufimtseva <elena.ufimtseva@oracle.com>
> 
> Add Xen command line option rmrr to specify RMRR                             
>    
> regions for devices that are not defined in ACPI thus                        
>    
> causing IO Page Fault while booting dom0 in PVH mode.                        
>    
> These additional regions will be added to the list of                        
>    
> RMRR regions parsed from ACPI.                                               
>    
> 
> Changes in v10:
>  - incorporate patch 'dmar: device scope mem leak fix' as series requires it.
>  - move patch 'pci: add PCI_SBDF and PCI_SEG macros' close to the last patch 
> which uses it;

Which isn't quite what

>> Or, even better, add such macros when the first user appears. Iirc
>> I said so before...
>>
>Yes, I realized this late. Will move over in the next version if needed. 

(on the 9th) and

>The dependency exists on memory leak patch, so I will add it to this series and 
>squash the first patch from v9.

(on the 13th) meant to me: I expected the patch to be folded into
the consuming one, not moved closer to it in the series. Anyway,
that on its own doesn't require a v11.

Jan

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

* Re: [PATCH v10 5/5] iommu: add rmrr Xen command line option for extra rmrrs
  2015-07-13 18:18 ` [PATCH v10 5/5] iommu: add rmrr Xen command line option for extra rmrrs elena.ufimtseva
@ 2015-07-14 10:43   ` Jan Beulich
  2015-07-15  7:25     ` Jan Beulich
  0 siblings, 1 reply; 11+ messages in thread
From: Jan Beulich @ 2015-07-14 10:43 UTC (permalink / raw)
  To: elena.ufimtseva; +Cc: kevin.tian, tim, xen-devel, yang.z.zhang, boris.ostrovsky

>>> On 13.07.15 at 20:18, <elena.ufimtseva@oracle.com> wrote:
> --- a/xen/drivers/passthrough/vtd/dmar.c
> +++ b/xen/drivers/passthrough/vtd/dmar.c
> @@ -867,6 +867,145 @@ out:
>      return ret;
>  }
>  
> +#define MAX_EXTRA_RMRR_PAGES 16
> +#define MAX_EXTRA_RMRR 10
> +
> +/* RMRR units derived from command line rmrr option. */
> +#define MAX_EXTRA_RMRR_DEV 20
> +struct extra_rmrr_unit {
> +    struct list_head list;
> +    unsigned long base_pfn, end_pfn;
> +    unsigned int dev_count;
> +    u32    sbdf[MAX_EXTRA_RMRR_DEV];

unless you want to align _all_ fields' names, there should be just a
single space between type and name.

> +};
> +static __initdata unsigned int nr_rmrr;
> +static struct __initdata extra_rmrr_unit extra_rmrr_units[MAX_EXTRA_RMRR];
> +
> +/* Macro for RMRR inclusive range formatting. */
> +#define PRI_RMRR(s,e) "[%lx-%lx]"

Just PRI_RMRR (i.e. no parens or parameters) please. And I'm still
missing a macro to pair the respective arguments - as said before,
as single format specifier should be accompanied by a single
argument (as visible to the reader at the use sites).

> +static void __init add_extra_rmrr(void)
> +{
> +    struct acpi_rmrr_unit *acpi_rmrr;
> +    struct acpi_rmrr_unit *rmrru;
> +    unsigned int dev, seg, i, j;
> +    unsigned long pfn;
> +    bool_t overlap;
> +
> +    for ( i = 0; i < nr_rmrr; i++ )
> +    {
> +        if ( extra_rmrr_units[i].base_pfn > extra_rmrr_units[i].end_pfn )
> +        {
> +            printk(XENLOG_ERR VTDPREFIX
> +                   "Invalid RMRR Range "PRI_RMRR(s,e)"\n",
> +                   extra_rmrr_units[i].base_pfn, extra_rmrr_units[i].end_pfn);
> +            continue;
> +        }
> +
> +        if ( extra_rmrr_units[i].end_pfn - extra_rmrr_units[i].base_pfn >=
> +             MAX_EXTRA_RMRR_PAGES )
> +        {
> +            printk(XENLOG_ERR VTDPREFIX
> +                   "RMRR range "PRI_RMRR(s,e)" exceeds "__stringify(MAX_EXTRA_RMRR_PAGES)" pages\n",
> +                   extra_rmrr_units[i].base_pfn, extra_rmrr_units[i].end_pfn);
> +            continue;
> +        }
> +
> +        for ( j = 0; j < nr_rmrr; j++ )
> +        {
> +            if ( i != j &&
> +                 extra_rmrr_units[i].base_pfn <= extra_rmrr_units[j].end_pfn &&
> +                 extra_rmrr_units[j].base_pfn <= extra_rmrr_units[i].end_pfn )
> +            {
> +                printk(XENLOG_ERR VTDPREFIX
> +                      "Overlapping RMRRs "PRI_RMRR(s,e)" and "PRI_RMRR(s,e)"\n",

No "extra" here ...

> +                      extra_rmrr_units[i].base_pfn, extra_rmrr_units[i].end_pfn,
> +                      extra_rmrr_units[j].base_pfn, extra_rmrr_units[j].end_pfn);
> +                break;
> +            }
> +        }
> +        /* Broke out of the overlap loop check, continue with next rmrr. */
> +        if ( j < nr_rmrr )
> +            continue;
> +        overlap = 0;
> +        list_for_each_entry(rmrru, &acpi_rmrr_units, list)
> +        {
> +            if ( pfn_to_paddr(extra_rmrr_units[i].base_pfn <= rmrru->end_address) &&
> +                 rmrru->base_address <= pfn_to_paddr(extra_rmrr_units[i].end_pfn) )
> +            {
> +                printk(XENLOG_ERR VTDPREFIX
> +                       "Overlapping extra RMRRs "PRI_RMRR(s,e)" and ACPI RMRRs "PRI_RMRR(s,e)"\n",

... but here? This may end up being confusing... Also s/RMRRs/RMRR/g
here please.

Also note the misplaced closing parenthesis on the first line of the
enclosing if().

> +                       extra_rmrr_units[i].base_pfn,
> +                       extra_rmrr_units[i].end_pfn,
> +                       paddr_to_pfn(rmrru->base_address),
> +                       paddr_to_pfn(rmrru->end_address));
> +                overlap = 1;
> +                break;
> +            }
> +        }
> +        /* Continue to next RMRR is this one overlaps with one from ACPI. */
> +        if ( overlap )
> +            continue;
> +
> +        pfn = extra_rmrr_units[i].base_pfn;
> +        do
> +        {
> +            if ( !mfn_valid(pfn) || (pfn >> (paddr_bits - PAGE_SHIFT)) )
> +            {
> +                printk(XENLOG_ERR VTDPREFIX
> +                       "Invalid pfn in RMRR range "PRI_RMRR(s,e)"\n",
> +                       extra_rmrr_units[i].base_pfn, extra_rmrr_units[i].end_pfn);
> +                break;
> +            }
> +        } while ( pfn++ <= extra_rmrr_units[i].end_pfn );

Off by one afaict.

> +static void __init parse_rmrr_param(const char *str)
> +{
> +    const char *s = str, *cur, *stmp;
> +    unsigned int seg, bus, dev, func;
> +    unsigned long start, end;
> +
> +    do {
> +        start = simple_strtoul(cur = s, &s, 0);
> +        if ( cur == s )
> +            break;
> +
> +        if ( *s == '-' )
> +        {
> +            end = simple_strtoul(cur = s + 1, &s, 0);
> +            if ( cur == s )
> +                break;
> +        }
> +        else
> +            end = start;
> +
> +        extra_rmrr_units[nr_rmrr].base_pfn = start;
> +        extra_rmrr_units[nr_rmrr].end_pfn = end;
> +        extra_rmrr_units[nr_rmrr].dev_count = 0;
> +
> +        if ( *s != '=' )
> +            continue;
> +
> +        do {
> +            bool_t default_segment = 0;
> +
> +            if ( *s == ';' )
> +                break;
> +            stmp = __parse_pci(s + 1, &seg, &bus, &dev, &func, &default_segment);
> +            if ( !stmp )
> +                break;
> +
> +            /* Not specified segment will be replaced with one from first device. */
> +            if ( extra_rmrr_units[nr_rmrr].dev_count && default_segment )
> +                seg = PCI_SEG(extra_rmrr_units[nr_rmrr].sbdf[0]);
> +
> +            /* Keep sbdf's even if they differ and later report an error. */
> +            extra_rmrr_units[nr_rmrr].sbdf[extra_rmrr_units[nr_rmrr].dev_count] = PCI_SBDF(seg, bus, dev, func);

Long line.

> +            extra_rmrr_units[nr_rmrr].dev_count++;
> +            s = stmp;
> +        } while ( (*s == ',' || *s ) &&
> +                  extra_rmrr_units[nr_rmrr].dev_count < MAX_EXTRA_RMRR_DEV );

This condition is _still_ bogus: If *s == ',' then obviously also *s, i.e.
the former condition is redundant with the latter. But then I don't
think you really mean just *s here, i.e. I'd rather see the latter part
dropped.

Jan

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

* Re: [PATCH v10 5/5] iommu: add rmrr Xen command line option for extra rmrrs
  2015-07-14 10:43   ` Jan Beulich
@ 2015-07-15  7:25     ` Jan Beulich
  2015-07-15 15:27       ` Elena Ufimtseva
  0 siblings, 1 reply; 11+ messages in thread
From: Jan Beulich @ 2015-07-15  7:25 UTC (permalink / raw)
  To: elena.ufimtseva; +Cc: yang.z.zhang, kevin.tian, tim, boris.ostrovsky, xen-devel

>>> On 14.07.15 at 12:43, <JBeulich@suse.com> wrote:
>>>> On 13.07.15 at 20:18, <elena.ufimtseva@oracle.com> wrote:
>> +/* Macro for RMRR inclusive range formatting. */
>> +#define PRI_RMRR(s,e) "[%lx-%lx]"
> 
> Just PRI_RMRR (i.e. no parens or parameters) please. And I'm still
> missing a macro to pair the respective arguments - as said before,
> as single format specifier should be accompanied by a single
> argument (as visible to the reader at the use sites).

Answering your IRC question here:

#define ERU_FMT "[%lx-%lx]"
#define ERU_ARG(eru) eru.base_pfn, eru.end_pfn

(with the acronym "eru" open for improvement).

Jan

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

* Re: [PATCH v10 5/5] iommu: add rmrr Xen command line option for extra rmrrs
  2015-07-15  7:25     ` Jan Beulich
@ 2015-07-15 15:27       ` Elena Ufimtseva
  2015-07-15 16:08         ` Jan Beulich
  0 siblings, 1 reply; 11+ messages in thread
From: Elena Ufimtseva @ 2015-07-15 15:27 UTC (permalink / raw)
  To: Jan Beulich; +Cc: yang.z.zhang, kevin.tian, tim, boris.ostrovsky, xen-devel

On Wed, Jul 15, 2015 at 08:25:06AM +0100, Jan Beulich wrote:
> >>> On 14.07.15 at 12:43, <JBeulich@suse.com> wrote:
> >>>> On 13.07.15 at 20:18, <elena.ufimtseva@oracle.com> wrote:
> >> +/* Macro for RMRR inclusive range formatting. */
> >> +#define PRI_RMRR(s,e) "[%lx-%lx]"
> > 
> > Just PRI_RMRR (i.e. no parens or parameters) please. And I'm still
> > missing a macro to pair the respective arguments - as said before,
> > as single format specifier should be accompanied by a single
> > argument (as visible to the reader at the use sites).
> 
> Answering your IRC question here:
> 
> #define ERU_FMT "[%lx-%lx]"
> #define ERU_ARG(eru) eru.base_pfn, eru.end_pfn
> 
> (with the acronym "eru" open for improvement).

Great! Thanks Jan.
Can ERU be RMRRU? 

> 
> Jan
> 

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

* Re: [PATCH v10 5/5] iommu: add rmrr Xen command line option for extra rmrrs
  2015-07-15 15:27       ` Elena Ufimtseva
@ 2015-07-15 16:08         ` Jan Beulich
  0 siblings, 0 replies; 11+ messages in thread
From: Jan Beulich @ 2015-07-15 16:08 UTC (permalink / raw)
  To: Elena Ufimtseva; +Cc: yang.z.zhang, kevin.tian, tim, boris.ostrovsky, xen-devel

>>> On 15.07.15 at 17:27, <elena.ufimtseva@oracle.com> wrote:
> On Wed, Jul 15, 2015 at 08:25:06AM +0100, Jan Beulich wrote:
>> >>> On 14.07.15 at 12:43, <JBeulich@suse.com> wrote:
>> >>>> On 13.07.15 at 20:18, <elena.ufimtseva@oracle.com> wrote:
>> >> +/* Macro for RMRR inclusive range formatting. */
>> >> +#define PRI_RMRR(s,e) "[%lx-%lx]"
>> > 
>> > Just PRI_RMRR (i.e. no parens or parameters) please. And I'm still
>> > missing a macro to pair the respective arguments - as said before,
>> > as single format specifier should be accompanied by a single
>> > argument (as visible to the reader at the use sites).
>> 
>> Answering your IRC question here:
>> 
>> #define ERU_FMT "[%lx-%lx]"
>> #define ERU_ARG(eru) eru.base_pfn, eru.end_pfn
>> 
>> (with the acronym "eru" open for improvement).
> 
> Great! Thanks Jan.
> Can ERU be RMRRU? 

ERMRRU maybe - I'd like the "extra" to somehow be expressed in
the name.

Jan

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

end of thread, other threads:[~2015-07-15 16:08 UTC | newest]

Thread overview: 11+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2015-07-13 18:17 [PATCH v10 0/5] iommu: add rmrr Xen command line option elena.ufimtseva
2015-07-13 18:17 ` [PATCH v10 1/5] dmar: device scope mem leak fix elena.ufimtseva
2015-07-13 18:17 ` [PATCH v10 2/5] iommu VT-d: separate rmrr addition function elena.ufimtseva
2015-07-13 18:18 ` [PATCH v10 3/5] pci: add wrapper for parse_pci elena.ufimtseva
2015-07-13 18:18 ` [PATCH v10 4/5] pci: add PCI_SBDF and PCI_SEG macros elena.ufimtseva
2015-07-13 18:18 ` [PATCH v10 5/5] iommu: add rmrr Xen command line option for extra rmrrs elena.ufimtseva
2015-07-14 10:43   ` Jan Beulich
2015-07-15  7:25     ` Jan Beulich
2015-07-15 15:27       ` Elena Ufimtseva
2015-07-15 16:08         ` Jan Beulich
2015-07-14 10:18 ` [PATCH v10 0/5] iommu: add rmrr Xen command line option 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.