All of lore.kernel.org
 help / color / mirror / Atom feed
* [patch 00/16] xend: pass-through: various clean-ups and infrastructure
@ 2009-06-15  1:55 Simon Horman
  2009-06-15  1:55 ` [patch 01/16] xend: pass-through: Only call setupOneDevice() once per device Simon Horman
                   ` (15 more replies)
  0 siblings, 16 replies; 28+ messages in thread
From: Simon Horman @ 2009-06-15  1:55 UTC (permalink / raw)
  To: xen-devel; +Cc: Masaki Kanno, Dexuan Cui

This series of patches cleans up various aspects of the PCI pass-through
code. This is working towards multi-function pass-through devices in guests.
But most of these changes are useful in their own right, so I am posting
this batch without the rest of the multi-function changes.

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

* [patch 01/16] xend: pass-through: Only call setupOneDevice() once per device
  2009-06-15  1:55 [patch 00/16] xend: pass-through: various clean-ups and infrastructure Simon Horman
@ 2009-06-15  1:55 ` Simon Horman
  2009-06-15  1:55 ` [patch 02/16] xend: pass-through: fix typo: spx -> sxp Simon Horman
                   ` (14 subsequent siblings)
  15 siblings, 0 replies; 28+ messages in thread
From: Simon Horman @ 2009-06-15  1:55 UTC (permalink / raw)
  To: xen-devel; +Cc: Masaki Kanno, Dexuan Cui

[-- Attachment #1: call-setupOneDevice-once.patch --]
[-- Type: text/plain, Size: 1240 bytes --]

As observed by Dexuan Cui, when PCI devices are passed through at
domain-creation-time setupOneDevice() will be called twice.

Once via setupDevice() and once via econfigureDevice() which
is called in pci_device_configure().

This patch removes the first of these.

Cc: Dexuan Cui <dexuan.cui@intel.com>
Cc: Masaki Kanno <kanno.masaki@jp.fujitsu.com>
Signed-off-by: Simon Horman <horms@verge.net.au>

Index: xen-unstable.hg/tools/python/xen/xend/server/pciif.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xend/server/pciif.py	2009-06-15 11:24:00.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xend/server/pciif.py	2009-06-15 11:24:02.000000000 +1000
@@ -436,8 +436,6 @@ class PciController(DevController):
                                     ' same guest with %s'
                                 raise VmError(err_msg % (s, dev.name))
 
-        for (domain, bus, slot, func) in pci_dev_list:
-            self.setupOneDevice(domain, bus, slot, func)
         wPath = '/local/domain/0/backend/pci/%u/0/aerState' % (self.getDomid())
         self.aerStateWatch = xswatch(wPath, self._handleAerStateWatch)
         log.debug('pci: register aer watch %s', wPath)

-- 

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

* [patch 02/16] xend: pass-through: fix typo: spx -> sxp
  2009-06-15  1:55 [patch 00/16] xend: pass-through: various clean-ups and infrastructure Simon Horman
  2009-06-15  1:55 ` [patch 01/16] xend: pass-through: Only call setupOneDevice() once per device Simon Horman
@ 2009-06-15  1:55 ` Simon Horman
  2009-06-15  1:55 ` [patch 03/16] xend: pass-through: tidy up PciController() Simon Horman
                   ` (13 subsequent siblings)
  15 siblings, 0 replies; 28+ messages in thread
From: Simon Horman @ 2009-06-15  1:55 UTC (permalink / raw)
  To: xen-devel; +Cc: Masaki Kanno, Dexuan Cui

[-- Attachment #1: sxp-typo.patch --]
[-- Type: text/plain, Size: 1862 bytes --]

Cc: Dexuan Cui <dexuan.cui@intel.com>
Cc: Masaki Kanno <kanno.masaki@jp.fujitsu.com>
Signed-off-by: Simon Horman <horms@verge.net.au>

Index: xen-unstable.hg/tools/python/xen/util/pci.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/util/pci.py	2009-06-11 19:05:28.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/util/pci.py	2009-06-11 19:05:40.000000000 +1000
@@ -124,7 +124,7 @@ def serialise_pci_opts(opts):
 def split_pci_opts(opts):
     return map(lambda x: x.split('='), opts.split(','))
 
-def pci_opts_list_to_spx(list):
+def pci_opts_list_to_sxp(list):
     ['dev'] + map(lambda x: ['opts', x], list)
 
 def parse_hex(val):
Index: xen-unstable.hg/tools/python/xen/xend/XendDomainInfo.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xend/XendDomainInfo.py	2009-06-11 19:05:28.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xend/XendDomainInfo.py	2009-06-11 19:05:54.000000000 +1000
@@ -39,7 +39,7 @@ from xen.util import asserts, auxbin
 from xen.util.blkif import blkdev_uname_to_file, blkdev_uname_to_taptype
 import xen.util.xsm.xsm as security
 from xen.util import xsconstants
-from xen.util.pci import serialise_pci_opts, pci_opts_list_to_spx
+from xen.util.pci import serialise_pci_opts, pci_opts_list_to_sxp
 
 from xen.xend import balloon, sxp, uuid, image, arch
 from xen.xend import XendOptions, XendNode, XendConfig
@@ -3771,7 +3771,7 @@ class XendDomainInfo:
         opts_dict = xenapi_pci.get('options')
         for k in opts_dict.keys():
             dpci_opts.append([k, opts_dict[k]])
-        opts_sxp = pci_opts_list_to_spx(dpci_opts)
+        opts_sxp = pci_opts_list_to_sxp(dpci_opts)
 
         # Convert xenapi to sxp
         ppci = XendAPIStore.get(xenapi_pci.get('PPCI'), 'PPCI')

-- 

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

* [patch 03/16] xend: pass-through: tidy up PciController()
  2009-06-15  1:55 [patch 00/16] xend: pass-through: various clean-ups and infrastructure Simon Horman
  2009-06-15  1:55 ` [patch 01/16] xend: pass-through: Only call setupOneDevice() once per device Simon Horman
  2009-06-15  1:55 ` [patch 02/16] xend: pass-through: fix typo: spx -> sxp Simon Horman
@ 2009-06-15  1:55 ` Simon Horman
  2009-06-15  1:55 ` [patch 04/16] xend: pass-through: cleanupDevice: move and remove recently added vslot entry Simon Horman
                   ` (12 subsequent siblings)
  15 siblings, 0 replies; 28+ messages in thread
From: Simon Horman @ 2009-06-15  1:55 UTC (permalink / raw)
  To: xen-devel; +Cc: Masaki Kanno, Dexuan Cui

[-- Attachment #1: cleanupDevice-cleanup.patch --]
[-- Type: text/plain, Size: 3176 bytes --]

Cc: Dexuan Cui <dexuan.cui@intel.com>
Cc: Masaki Kanno <kanno.masaki@jp.fujitsu.com>
Signed-off-by: Simon Horman <horms@verge.net.au>

Index: xen-unstable.hg/tools/python/xen/xend/server/pciif.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xend/server/pciif.py	2009-06-15 11:24:02.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xend/server/pciif.py	2009-06-15 11:24:12.000000000 +1000
@@ -540,33 +540,24 @@ class PciController(DevController):
                 # In HVM case, I/O resources are disabled in ioemu.
                 self.cleanupOneDevice(domain, bus, slot, func)
                 # Remove xenstore nodes.
-                self.removeBackend(devid, 'dev-%i' % i)
-                self.removeBackend(devid, 'vdev-%i' % i)
-                self.removeBackend(devid, 'state-%i' % i)
-                self.removeBackend(devid, 'uuid-%i' % i)
-                tmpopts = self.readBackend(devid, 'opts-%i' % i)
-                if tmpopts is not None:
-                    self.removeBackend(devid, 'opts-%i' % i)
+                list = ['dev', 'vdev', 'state', 'uuid']
+                if self.readBackend(devid, 'opts-%i' % i) is not None:
+                    list.append('opts')
+                for key in list:
+                    self.removeBackend(devid, '%s-%i' % (key, i))
             else:
-                if new_num_devs != i:
-                    tmpdev = self.readBackend(devid, 'dev-%i' % i)
-                    self.writeBackend(devid, 'dev-%i' % new_num_devs, tmpdev)
-                    self.removeBackend(devid, 'dev-%i' % i)
-                    tmpvdev = self.readBackend(devid, 'vdev-%i' % i)
-                    if tmpvdev is not None:
-                        self.writeBackend(devid, 'vdev-%i' % new_num_devs,
-                                          tmpvdev)
-                    self.removeBackend(devid, 'vdev-%i' % i)
-                    tmpstate = self.readBackend(devid, 'state-%i' % i)
-                    self.writeBackend(devid, 'state-%i' % new_num_devs, tmpstate)
-                    self.removeBackend(devid, 'state-%i' % i)
-                    tmpuuid = self.readBackend(devid, 'uuid-%i' % i)
-                    self.writeBackend(devid, 'uuid-%i' % new_num_devs, tmpuuid)
-                    self.removeBackend(devid, 'uuid-%i' % i)
-                    tmpopts = self.readBackend(devid, 'opts-%i' % i)
-                    if tmpopts is not None:
-                        self.removeBackend(devid, 'opts-%i' % i)
                 new_num_devs = new_num_devs + 1
+                if new_num_devs == i + 1:
+                    continue
+
+                list = ['dev', 'vdev', 'state', 'uuid', 'opts']
+                for key in list:
+                    tmp = self.readBackend(devid, '%s-%i' % (key, i))
+                    if tmp is None:
+                        continue
+                    self.removeBackend(devid, '%s-%i' % (key, i))
+                    self.writeBackend(devid,
+                                      '%s-%i' % (key, new_num_devs - 1), tmp)
 
         self.writeBackend(devid, 'num_devs', str(new_num_devs))
 

-- 

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

* [patch 04/16] xend: pass-through: cleanupDevice: move and remove recently added vslot entry
  2009-06-15  1:55 [patch 00/16] xend: pass-through: various clean-ups and infrastructure Simon Horman
                   ` (2 preceding siblings ...)
  2009-06-15  1:55 ` [patch 03/16] xend: pass-through: tidy up PciController() Simon Horman
@ 2009-06-15  1:55 ` Simon Horman
  2009-06-15  1:55 ` [patch 05/16] xend: pass-through: sxp.merge() cant deal with values being a list Simon Horman
                   ` (11 subsequent siblings)
  15 siblings, 0 replies; 28+ messages in thread
From: Simon Horman @ 2009-06-15  1:55 UTC (permalink / raw)
  To: xen-devel; +Cc: Masaki Kanno, Dexuan Cui

[-- Attachment #1: cleanupDevice-vslot.patch --]
[-- Type: text/plain, Size: 1375 bytes --]

Cc: Dexuan Cui <dexuan.cui@intel.com>
Cc: Masaki Kanno <kanno.masaki@jp.fujitsu.com>
Signed-off-by: Simon Horman <horms@verge.net.au>

Index: xen-unstable.hg/tools/python/xen/xend/server/pciif.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xend/server/pciif.py	2009-06-15 11:24:17.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xend/server/pciif.py	2009-06-15 11:24:20.000000000 +1000
@@ -540,7 +540,7 @@ class PciController(DevController):
                 # In HVM case, I/O resources are disabled in ioemu.
                 self.cleanupOneDevice(domain, bus, slot, func)
                 # Remove xenstore nodes.
-                list = ['dev', 'vdev', 'state', 'uuid']
+                list = ['dev', 'vdev', 'state', 'uuid', 'vslot']
                 if self.readBackend(devid, 'opts-%i' % i) is not None:
                     list.append('opts')
                 for key in list:
@@ -550,7 +550,7 @@ class PciController(DevController):
                 if new_num_devs == i + 1:
                     continue
 
-                list = ['dev', 'vdev', 'state', 'uuid', 'opts']
+                list = ['dev', 'vdev', 'state', 'uuid', 'opts', 'vslot']
                 for key in list:
                     tmp = self.readBackend(devid, '%s-%i' % (key, i))
                     if tmp is None:

-- 

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

* [patch 05/16] xend: pass-through: sxp.merge() cant deal with values being a list
  2009-06-15  1:55 [patch 00/16] xend: pass-through: various clean-ups and infrastructure Simon Horman
                   ` (3 preceding siblings ...)
  2009-06-15  1:55 ` [patch 04/16] xend: pass-through: cleanupDevice: move and remove recently added vslot entry Simon Horman
@ 2009-06-15  1:55 ` Simon Horman
  2009-06-15  1:55 ` [patch 06/16] xend: pass-through: Remove PciDeviceNotFoundError, it is never used Simon Horman
                   ` (10 subsequent siblings)
  15 siblings, 0 replies; 28+ messages in thread
From: Simon Horman @ 2009-06-15  1:55 UTC (permalink / raw)
  To: xen-devel; +Cc: Masaki Kanno, Dexuan Cui

[-- Attachment #1: opts-sxp.patch --]
[-- Type: text/plain, Size: 11017 bytes --]

sxp.merge() can't deal with values being a list so instead
of storing pci options as:

[ 'opts', [ 'key1' 'value1'], [ 'key2', 'value2'], ...]

store them as:

[ 'opts', [ 'key1' 'value1'], ['opts', [ 'key2', 'value2']], ...

Cc: Dexuan Cui <dexuan.cui@intel.com>
Cc: Masaki Kanno <kanno.masaki@jp.fujitsu.com>
Signed-off-by: Simon Horman <horms@verge.net.au>

--- 

 tools/python/xen/util/pci.py          |   18 +++++++++++++--
 tools/python/xen/xend/XendConfig.py   |   38 +++++++++++++++------------------
 tools/python/xen/xend/server/pciif.py |    3 +-
 tools/python/xen/xm/create.py         |   23 ++++++++-----------
 tools/python/xen/xm/main.py           |   11 ++++++---
 tools/python/xen/xm/xenapi_create.py  |   12 +++++-----
 6 files changed, 58 insertions(+), 47 deletions(-)

Index: xen-unstable.hg/tools/python/xen/util/pci.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/util/pci.py	2009-06-13 10:32:59.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/util/pci.py	2009-06-13 10:33:14.000000000 +1000
@@ -118,14 +118,26 @@ def PCI_BDF(domain, bus, slot, func):
     return (((domain & 0xffff) << 16) | ((bus & 0xff) << 8) |
             PCI_DEVFN(slot, func))
 
+def check_pci_opts(opts):
+    def f((k, v)):
+        if k not in ['msitranslate', 'power_mgmt'] or \
+           not v.lower() in ['0', '1', 'yes', 'no']:
+            raise PciDeviceParseError('Invalid pci option %s=%s: ' % (k, v))
+
+    map(f, opts)
+
 def serialise_pci_opts(opts):
-    return reduce(lambda x, y: x+','+y, map(lambda (x, y): x+'='+y, opts))
+    return ','.join(map(lambda x: '='.join(x), opts))
 
 def split_pci_opts(opts):
-    return map(lambda x: x.split('='), opts.split(','))
+    return map(lambda x: x.split('='),
+               filter(lambda x: x != '', opts.split(',')))
 
 def pci_opts_list_to_sxp(list):
-    ['dev'] + map(lambda x: ['opts', x], list)
+    return ['dev'] + map(lambda x: ['opts', x], list)
+
+def pci_opts_list_from_sxp(dev):
+    return map(lambda x: sxp.children(x)[0], sxp.children(dev, 'opts'))
 
 def parse_hex(val):
     try:
Index: xen-unstable.hg/tools/python/xen/xend/XendConfig.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xend/XendConfig.py	2009-06-13 10:32:59.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xend/XendConfig.py	2009-06-13 10:33:04.000000000 +1000
@@ -36,6 +36,7 @@ from xen.xend.xenstore.xstransact import
 from xen.xend.server.BlktapController import blktap_disk_types
 from xen.xend.server.netif import randomMAC
 from xen.util.blkif import blkdev_name_to_number, blkdev_uname_to_file
+from xen.util.pci import pci_opts_list_from_sxp
 from xen.util import xsconstants
 import xen.util.auxbin
 
@@ -1596,11 +1597,10 @@ class XendConfig(dict):
         return ''
 
     def pci_convert_dict_to_sxp(self, dev, state, sub_state = None):
-        sxp =  ['pci', ['dev'] + map(lambda (x, y): [x, y], dev.items()),
-                ['state', state]]
+        pci_sxp = ['pci', self.dev_dict_to_sxp(dev), ['state', state]]
         if sub_state != None:
-            sxp.append(['sub_state', sub_state])
-        return sxp
+            pci_sxp.append(['sub_state', sub_state])
+        return pci_sxp
 
     def pci_convert_sxp_to_dict(self, dev_sxp):
         """Convert pci device sxp to dict
@@ -1649,13 +1649,9 @@ class XendConfig(dict):
 
         pci_devs = []
         for pci_dev in sxp.children(dev_sxp, 'dev'):
-            pci_dev_info = {}
-            for opt_val in pci_dev[1:]:
-                try:
-                    opt, val = opt_val
-                    pci_dev_info[opt] = val
-                except (TypeError, ValueError):
-                    pass
+            pci_dev_info = dict(pci_dev[1:])
+            if 'opts' in pci_dev_info:
+                pci_dev_info['opts'] = pci_opts_list_from_sxp(pci_dev)
             # append uuid to each pci device that does't already have one.
             if not pci_dev_info.has_key('uuid'):
                 dpci_uuid = pci_dev_info.get('uuid', uuid.createString())
@@ -1966,6 +1962,15 @@ class XendConfig(dict):
         result.extend([u for u in target['devices'].keys() if u not in result])
         return result
 
+    # This includes a generic equivalent of pci_opts_list_to_sxp()
+    def dev_dict_to_sxp(self, dev):
+        def f((key, val)):
+            if isinstance(val, types.ListType):
+                return map(lambda x: [key, x], val)
+            return [[key, val]]
+        dev_sxp = ['dev'] + reduce(lambda x, y: x + y, map(f, dev.items()))
+        return dev_sxp
+
     def all_devices_sxpr(self, target = None):
         """Returns the SXPR for all devices in the current configuration."""
         sxprs = []
@@ -1988,10 +1993,7 @@ class XendConfig(dict):
                     if dev_info.has_key('backend'):
                         sxpr.append(['backend', dev_info['backend']])
                 for pci_dev_info in dev_info['devs']:
-                    pci_dev_sxpr = ['dev']
-                    for opt, val in pci_dev_info.items():
-                        pci_dev_sxpr.append([opt, val])
-                    sxpr.append(pci_dev_sxpr)
+                    sxpr.append(self.dev_dict_to_sxp(pci_dev_info))
                 sxprs.append((dev_type, sxpr))
             else:
                 sxpr = self.device_sxpr(dev_type = dev_type,
@@ -2118,11 +2120,7 @@ class XendConfig(dict):
                 slot = sxp.child_value(dev, 'slot')
                 func = sxp.child_value(dev, 'func')
                 vslot = sxp.child_value(dev, 'vslot')
-                opts = ''
-                for opt in sxp.child_value(dev, 'opts', []):
-                    if opts:
-                        opts += ','
-                    opts += '%s=%s' % (opt[0], str(opt[1]))
+                opts = pci_opts_list_from_sxp(dev)
                 pci.append([domain, bus, slot, func, vslot, opts])
         self['platform']['pci'] = pci
 
Index: xen-unstable.hg/tools/python/xen/xend/server/pciif.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xend/server/pciif.py	2009-06-13 10:32:59.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xend/server/pciif.py	2009-06-13 10:33:04.000000000 +1000
@@ -222,7 +222,8 @@ class PciController(DevController):
             dev_sxpr = ['dev']
             for dev_key, dev_val in dev.items():
                 if dev_key == 'opts':
-                    dev_sxpr.append(['opts', split_pci_opts(dev_val)])
+                    opts_sxpr = pci_opts_list_to_sxp(split_pci_opts(dev_val))
+                    dev_sxpr = sxp.merge(dev_sxpr, opts_sxpr)
                 else:
                     dev_sxpr.append([dev_key, dev_val])
             sxpr.append(dev_sxpr)
Index: xen-unstable.hg/tools/python/xen/xm/create.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xm/create.py	2009-06-13 10:32:59.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xm/create.py	2009-06-13 10:33:04.000000000 +1000
@@ -38,6 +38,8 @@ from xen.util import vscsi_util
 import xen.util.xsm.xsm as security
 from xen.xm.main import serverType, SERVER_XEN_API, get_single_vm
 from xen.util import utils, auxbin
+from xen.util.pci import split_pci_opts, check_pci_opts, \
+                         pci_opts_list_to_sxp
 
 from xen.xm.opts import *
 
@@ -705,23 +707,18 @@ def configure_pci(config_devs, vals):
     """
     config_pci = []
     for (domain, bus, slot, func, vslot, opts) in vals.pci:
-        config_pci_opts = []
-        d = comma_sep_kv_to_dict(opts)
-
-        def f(k):
-            if k not in ['msitranslate', 'power_mgmt']:
-                err('Invalid pci option: ' + k)
-
-            config_pci_opts.append([k, d[k]])
-
         config_pci_bdf = ['dev', ['domain', domain], ['bus', bus], \
                           ['slot', slot], ['func', func],
                           ['vslot', vslot]]
-        map(f, d.keys())
-        if len(config_pci_opts)>0:
-            config_pci_bdf.append(['opts', config_pci_opts])
 
-        config_pci.append(config_pci_bdf)
+        opts_list = split_pci_opts(opts)
+        try:
+            check_pci_opts(opts_list)
+        except PciDeviceParseError, ex:
+            err(str(ex))
+
+        config_opts = pci_opts_list_to_sxp(split_pci_opts(opts))
+        config_pci.append(sxp.merge(config_pci_bdf, config_opts))
 
     if len(config_pci)>0:
         config_pci.insert(0, 'pci')
Index: xen-unstable.hg/tools/python/xen/xm/main.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xm/main.py	2009-06-13 10:32:59.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xm/main.py	2009-06-13 10:33:04.000000000 +1000
@@ -2504,12 +2504,15 @@ def parse_pci_configuration(args, state,
                 ['slot', '0x'+ pci_dev_info['slot']],
                 ['func', '0x'+ pci_dev_info['func']],
                 ['vslot', '0x%x' % int(vslot, 16)]]
-        if len(opts) > 0:
-            pci_bdf.append(['opts', opts])
-        pci.append(pci_bdf)
-
     except:
         raise OptionError("Invalid argument: %s %s" % (pci_dev_str, vslot))
+
+    try:
+        check_pci_opts(opts)
+    except PciDeviceParseError, ex:
+        raise OptionError(str(ex))
+
+    pci.append(sxp.merge(pci_bdf, pci_opts_list_to_sxp(opts)))
     pci.append(['state', state])
 
     return (dom, pci)
Index: xen-unstable.hg/tools/python/xen/xm/xenapi_create.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xm/xenapi_create.py	2009-06-13 10:32:59.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xm/xenapi_create.py	2009-06-13 10:33:04.000000000 +1000
@@ -26,6 +26,7 @@ from xen.xend.XendAPIConstants import XE
      XEN_API_ON_CRASH_BEHAVIOUR
 from xen.xm.opts import OptionError
 from xen.util import xsconstants
+from xen.util.pci import pci_opts_list_from_sxp
 from xen.util.path import SHAREDIR
 import xen.util.xsm.xsm as security
 
@@ -945,12 +946,11 @@ class sxp2xml:
                     = get_child_by_name(dev_sxp, "func", "0")
                 pci.attributes["vslot"] \
                     = get_child_by_name(dev_sxp, "vslot", "0")
-                for opt in get_child_by_name(dev_sxp, "opts", ""):
-                    if len(opt) > 0:
-                        pci_opt = document.createElement("pci_opt")
-                        pci_opt.attributes["key"] = opt[0]
-                        pci_opt.attributes["value"] = opt[1]
-                        pci.appendChild(pci_opt)
+                for opt in pci_opts_list_from_sxp(dev_sxp):
+                    pci_opt = document.createElement("pci_opt")
+                    pci_opt.attributes["key"] = opt[0]
+                    pci_opt.attributes["value"] = opt[1]
+                    pci.appendChild(pci_opt)
 
                 pcis.append(pci)
 

-- 

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

* [patch 06/16] xend: pass-through: Remove PciDeviceNotFoundError, it is never used
  2009-06-15  1:55 [patch 00/16] xend: pass-through: various clean-ups and infrastructure Simon Horman
                   ` (4 preceding siblings ...)
  2009-06-15  1:55 ` [patch 05/16] xend: pass-through: sxp.merge() cant deal with values being a list Simon Horman
@ 2009-06-15  1:55 ` Simon Horman
  2009-06-15  1:55 ` [patch 07/16] xend: pass-through: Use PCIDevice as the parameter for the constructor for PCIQuirk Simon Horman
                   ` (9 subsequent siblings)
  15 siblings, 0 replies; 28+ messages in thread
From: Simon Horman @ 2009-06-15  1:55 UTC (permalink / raw)
  To: xen-devel; +Cc: Masaki Kanno, Dexuan Cui

[-- Attachment #1: remove-PciDeviceNotFoundError.patch --]
[-- Type: text/plain, Size: 957 bytes --]

Cc: Dexuan Cui <dexuan.cui@intel.com>
Cc: Masaki Kanno <kanno.masaki@jp.fujitsu.com>
Signed-off-by: Simon Horman <horms@verge.net.au>

Index: xen-unstable.hg/tools/python/xen/util/pci.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/util/pci.py	2009-06-15 11:24:25.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/util/pci.py	2009-06-15 11:24:25.000000000 +1000
@@ -375,17 +375,6 @@ def check_mmio_bar(devs_list):
 
     return result
 
-class PciDeviceNotFoundError(Exception):
-    def __init__(self,domain,bus,slot,func):
-        self.domain = domain
-        self.bus = bus
-        self.slot = slot
-        self.func = func
-        self.name = PCI_DEV_FORMAT_STR %(domain, bus, slot, func)
-    
-    def __str__(self):
-        return ('PCI Device %s Not Found' % (self.name))
-
 class PciDeviceParseError(Exception):
     def __init__(self,msg):
         self.message = msg

-- 

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

* [patch 07/16] xend: pass-through: Use PCIDevice as the parameter for the constructor for PCIQuirk
  2009-06-15  1:55 [patch 00/16] xend: pass-through: various clean-ups and infrastructure Simon Horman
                   ` (5 preceding siblings ...)
  2009-06-15  1:55 ` [patch 06/16] xend: pass-through: Remove PciDeviceNotFoundError, it is never used Simon Horman
@ 2009-06-15  1:55 ` Simon Horman
  2009-06-15  1:55 ` [patch 08/16] xend: pass-through: Common parse_pci_name() Simon Horman
                   ` (8 subsequent siblings)
  15 siblings, 0 replies; 28+ messages in thread
From: Simon Horman @ 2009-06-15  1:55 UTC (permalink / raw)
  To: xen-devel; +Cc: Masaki Kanno, Dexuan Cui

[-- Attachment #1: PCIQuirk-use-PCIDevice-for-constructor.patch --]
[-- Type: text/plain, Size: 2332 bytes --]

Cc: Dexuan Cui <dexuan.cui@intel.com>
Cc: Masaki Kanno <kanno.masaki@jp.fujitsu.com>
Signed-off-by: Simon Horman <horms@verge.net.au>

Index: xen-unstable.hg/tools/python/xen/xend/server/pciif.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xend/server/pciif.py	2009-06-05 16:19:26.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xend/server/pciif.py	2009-06-07 21:49:07.000000000 +1000
@@ -301,8 +301,7 @@ class PciController(DevController):
         # if arch.type != "ia64":
         #    dev.do_FLR()
 
-        PCIQuirk(dev.vendor, dev.device, dev.subvendor, dev.subdevice, domain, 
-                bus, slot, func)
+        PCIQuirk(dev)
 
         if not self.vm.info.is_hvm():
             # Setup IOMMU device assignment
Index: xen-unstable.hg/tools/python/xen/xend/server/pciquirk.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xend/server/pciquirk.py	2009-06-05 16:19:20.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xend/server/pciquirk.py	2009-06-05 17:01:20.000000000 +1000
@@ -11,18 +11,19 @@ PERMISSIVE_CONFIG_FILE = auxbin.xen_conf
 PERMISSIVE_SYSFS_NODE = "/sys/bus/pci/drivers/pciback/permissive"
 
 class PCIQuirk:
-    def __init__( self, vendor, device, subvendor, subdevice, domain, bus, slot, func):
-        self.vendor = vendor
-        self.device = device
-        self.subvendor = subvendor
-        self.subdevice = subdevice
-        self.domain = domain
-        self.bus = bus
-        self.slot = slot
-        self.func = func
-
-        self.devid = "%04x:%04x:%04x:%04x" % (vendor, device, subvendor, subdevice)
-        self.pciid = "%04x:%02x:%02x.%01x" % (domain, bus, slot, func)
+    def __init__(self, dev):
+        self.vendor = dev.vendor
+        self.device = dev.device
+        self.subvendor = dev.subvendor
+        self.subdevice = dev.subdevice
+        self.domain = dev.domain
+        self.bus = dev.bus
+        self.slot = dev.slot
+        self.func = dev.func
+
+        self.devid = "%04x:%04x:%04x:%04x" % (self.vendor, self.device,
+                                              self.subvendor, self.subdevice)
+        self.pciid = dev.name
         self.quirks = self.__getQuirksByID()
 
         self.__sendQuirks()

-- 

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

* [patch 08/16] xend: pass-through: Common parse_pci_name()
  2009-06-15  1:55 [patch 00/16] xend: pass-through: various clean-ups and infrastructure Simon Horman
                   ` (6 preceding siblings ...)
  2009-06-15  1:55 ` [patch 07/16] xend: pass-through: Use PCIDevice as the parameter for the constructor for PCIQuirk Simon Horman
@ 2009-06-15  1:55 ` Simon Horman
  2009-06-16 10:43   ` Keir Fraser
  2009-06-15  1:55 ` [patch 09/16] xend: pass-through: Use common parsing code in preprocess_pci() Simon Horman
                   ` (7 subsequent siblings)
  15 siblings, 1 reply; 28+ messages in thread
From: Simon Horman @ 2009-06-15  1:55 UTC (permalink / raw)
  To: xen-devel; +Cc: Masaki Kanno, Dexuan Cui

[-- Attachment #1: xm-parse_pci_name.patch --]
[-- Type: text/plain, Size: 27358 bytes --]

Share some parsing code between different parts of xm.

This has the side-effect that the device specification for
hot-plug may now include the VSLOT and OPTS as per device
specifictions in the domain configuration file.

  SEQ:BUS:DEV.FUNC[,OPT...]

  e.g. 0000:00:01.00@6

Cc: Dexuan Cui <dexuan.cui@intel.com>
Cc: Masaki Kanno <kanno.masaki@jp.fujitsu.com>
Signed-off-by: Simon Horman <horms@verge.net.au>

--- 

Wed, 20 May 2009 23:07:42 +1000
* Fix syntax errors in parse_pci_name() and parse_pci_name_bdf6()
  - unnoticed as they were resolved by the subsequent patch
    "xm: Allow multi-function device specifications to be parsed
* Enhanced error reporting in parse_pci_name()
* Have parse_pci_name_bdf6() return an int rather than a string for vslot in
  keeping with the other integer elements of the bdf6 tuple

Fri, 22 May 2009 15:52:50 +1000
* Consolidate get_all_pci_bdf6() and get_all_pci_devices()

Thu, 28 May 2009 23:56:14 +1000
* Up-port

Index: xen-unstable.hg/tools/python/xen/util/pci.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/util/pci.py	2009-06-15 11:22:35.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/util/pci.py	2009-06-15 11:23:43.000000000 +1000
@@ -15,6 +15,7 @@ import time
 import threading
 from xen.util import utils
 from xen.xend import sxp
+from xen.xend.XendConstants import AUTO_PHP_SLOT
 
 PROC_PCI_PATH = '/proc/bus/pci/devices'
 PROC_PCI_NUM_RESOURCES = 7
@@ -35,7 +36,6 @@ LSPCI_CMD = 'lspci'
 
 PCI_DEV_REG_EXPRESS_STR = r"[0-9a-fA-F]{4}:[0-9a-fA-F]{2}:[0-9a-fA-F]{2}."+ \
             r"[0-9a-fA-F]{1}"
-PCI_DEV_FORMAT_STR = '%04x:%02x:%02x.%01x'
 
 DEV_TYPE_PCIe_ENDPOINT  = 0
 DEV_TYPE_PCIe_BRIDGE    = 1
@@ -148,22 +148,62 @@ def parse_hex(val):
     except ValueError:
         return None
 
+def parse_pci_name_extended(pci_dev_str):
+    pci_match = re.match(r"((?P<domain>[0-9a-fA-F]{1,4})[:,])?" +
+                         r"(?P<bus>[0-9a-fA-F]{1,2})[:,]" +
+                         r"(?P<slot>[0-9a-fA-F]{1,2})[.,]" +
+                         r"(?P<func>(\*|[0-7]))" +
+                         r"(@(?P<vslot>[01]?[0-9a-fA-F]))?" +
+                         r"(,(?P<opts>.*))?$", pci_dev_str)
+
+    if pci_match == None:
+        raise PciDeviceParseError("Failed to parse pci device: %s" %
+                                  pci_dev_str)
+
+    out = {}
+    pci_dev_info = pci_match.groupdict('')
+    if pci_dev_info['domain'] == '':
+        domain = 0
+    else:
+        domain = int(pci_dev_info['domain'], 16)
+    out['domain'] = "0x%04x" % domain
+    out['bus']    = "0x%02x" % int(pci_dev_info['bus'], 16)
+    out['slot']   = "0x%02x" % int(pci_dev_info['slot'], 16)
+    out['func']   = "0x%x"   % int(pci_dev_info['func'], 16)
+    if pci_dev_info['vslot'] == '':
+        vslot = AUTO_PHP_SLOT
+    else:
+        vslot = int(pci_dev_info['vslot'], 16)
+    out['vslot'] = "0x%02x" % vslot
+    if pci_dev_info['opts'] != '':
+        out['opts'] = split_pci_opts(pci_dev_info['opts'])
+        check_pci_opts(out['opts'])
+
+    return out
+
 def parse_pci_name(pci_name_string):
-    pci_match = re.match(r"((?P<domain>[0-9a-fA-F]{1,4})[:,])?" + \
-            r"(?P<bus>[0-9a-fA-F]{1,2})[:,]" + \
-            r"(?P<slot>[0-9a-fA-F]{1,2})[.,]" + \
-            r"(?P<func>[0-7])$", pci_name_string)
-    if pci_match is None:
-        raise PciDeviceParseError(('Failed to parse pci device name: %s' %
-            pci_name_string))
-    pci_dev_info = pci_match.groupdict('0')
-
-    domain = parse_hex(pci_dev_info['domain'])
-    bus = parse_hex(pci_dev_info['bus'])
-    slot = parse_hex(pci_dev_info['slot'])
-    func = parse_hex(pci_dev_info['func'])
+    pci = parse_pci_name_extended(pci_name_string)
+
+    if int(pci['vslot'], 16) != AUTO_PHP_SLOT:
+        raise PciDeviceParseError(("Failed to parse pci device: %s: " +
+                                   "vslot provided where prohibited: %s") %
+                                  (pci_name_string, pci['vslot']))
+    if 'opts' in pci:
+        raise PciDeviceParseError(("Failed to parse pci device: %s: " +
+                                   "options provided where prohibited: %s") %
+                                  (pci_name_string, pci['opts']))
+
+    return pci
+
+def __pci_dict_to_fmt_str(fmt, dev):
+    return fmt % (int(dev['domain'], 16), int(dev['bus'], 16),
+                  int(dev['slot'], 16), int(dev['func'], 16))
 
-    return (domain, bus, slot, func)
+def pci_dict_to_bdf_str(dev):
+    return __pci_dict_to_fmt_str('%04x:%02x:%02x.%01x', dev)
+
+def pci_dict_to_xc_str(dev):
+    return __pci_dict_to_fmt_str('0x%x, 0x%x, 0x%x, 0x%x', dev)
 
 def extract_the_exact_pci_names(pci_names):
     result = []
@@ -198,27 +238,7 @@ def get_all_pci_names():
     return pci_names
 
 def get_all_pci_devices():
-    pci_devs = []
-    for pci_name in get_all_pci_names():
-        pci_match = re.match(r"((?P<domain>[0-9a-fA-F]{1,4})[:,])?" + \
-                r"(?P<bus>[0-9a-fA-F]{1,2})[:,]" + \
-                r"(?P<slot>[0-9a-fA-F]{1,2})[.,]" + \
-                r"(?P<func>[0-7])$", pci_name)
-        if pci_match is None:
-            raise PciDeviceParseError(('Failed to parse pci device name: %s' %
-                pci_name))
-        pci_dev_info = pci_match.groupdict('0')
-        domain = parse_hex(pci_dev_info['domain'])
-        bus = parse_hex(pci_dev_info['bus'])
-        slot = parse_hex(pci_dev_info['slot'])
-        func = parse_hex(pci_dev_info['func'])
-        try:
-            pci_dev = PciDevice(domain, bus, slot, func)
-        except:
-            continue
-        pci_devs.append(pci_dev)
-
-    return pci_devs
+    return map(PciDevice, map(parse_pci_name, get_all_pci_names()))
 
 def _create_lspci_info():
     """Execute 'lspci' command and parse the result.
@@ -237,7 +257,7 @@ def _create_lspci_info():
             try:
                 (opt, value) = line.split(':\t')
                 if opt == 'Slot':
-                    device_name = PCI_DEV_FORMAT_STR % parse_pci_name(value)
+                    device_name = pci_dict_to_bdf_str(parse_pci_name(value))
                 else:
                     device_info[opt] = value
             except:
@@ -287,8 +307,7 @@ def find_all_devices_owned_by_pciback():
     pci_list = extract_the_exact_pci_names(pci_names)
     dev_list = []
     for pci in pci_list:
-        (dom, b, d, f) = parse_pci_name(pci)
-        dev = PciDevice(dom, b, d, f)
+        dev = PciDevice(parse_pci_name(pci))
         dev_list = dev_list + [dev]
     return dev_list
 
@@ -395,12 +414,12 @@ class PciDeviceVslotMissing(Exception):
         return 'pci: no vslot: ' + self.message
 
 class PciDevice:
-    def __init__(self, domain, bus, slot, func):
-        self.domain = domain
-        self.bus = bus
-        self.slot = slot
-        self.func = func
-        self.name = PCI_DEV_FORMAT_STR % (domain, bus, slot, func)
+    def __init__(self, dev):
+        self.domain = int(dev['domain'], 16)
+        self.bus = int(dev['bus'], 16)
+        self.slot = int(dev['slot'], 16)
+        self.func = int(dev['func'], 16)
+        self.name = pci_dict_to_bdf_str(dev)
         self.cfg_space_path = find_sysfs_mnt()+SYSFS_PCI_DEVS_PATH+'/'+ \
             self.name + SYSFS_PCI_DEV_CONFIG_PATH 
         self.irq = 0
@@ -442,14 +461,15 @@ class PciDevice:
                 # We have reached the upmost one.
                 return None
             else:
+                dev = {}
                 lst = parent.split(':')
-                dom = int(lst[0], 16)
-                bus = int(lst[1], 16)
+                dev['dom'] = int(lst[0], 16)
+                dev['bus'] = int(lst[1], 16)
                 lst = lst[2]
                 lst = lst.split('.')
-                dev =  int(lst[0], 16)
-                func =  int(lst[1], 16)
-            return (dom, bus, dev, func)
+                dev['slot'] = int(lst[0], 16)
+                dev['func'] = int(lst[1], 16)
+            return dev
         except OSError, (errno, strerr):
             raise PciDeviceParseError('Can not locate the parent of %s',
                 self.name)
@@ -459,15 +479,13 @@ class PciDevice:
         dev = self.find_parent()
         if dev is None:
             return None
-        (dom, b, d, f) = dev
-        dev = dev_parent = PciDevice(dom, b, d, f)
+        dev = dev_parent = PciDevice(dev)
         while dev_parent.dev_type != DEV_TYPE_PCIe_BRIDGE:
             parent = dev_parent.find_parent()
             if parent is None:
                 break
-            (dom, b, d, f) = parent
             dev = dev_parent
-            dev_parent = PciDevice(dom, b, d, f)
+            dev_parent = PciDevice(parent)
         return dev
 
     def find_all_devices_behind_the_bridge(self, ignore_bridge):
@@ -478,8 +496,7 @@ class PciDevice:
 
         list = [self.name]
         for pci_str in dev_list:
-            (dom, b, d, f) = parse_pci_name(pci_str)
-            dev = PciDevice(dom, b, d, f)
+            dev = PciDevice(parse_pci_name(pci_str))
             if dev.dev_type == DEV_TYPE_PCI_BRIDGE or \
                 dev.dev_type == DEV_TYPE_PCIe_BRIDGE:
                 sub_list_including_self = \
@@ -595,7 +612,7 @@ class PciDevice:
 
     def find_all_the_multi_functions(self):
         sysfs_mnt = find_sysfs_mnt()
-        parent = PCI_DEV_FORMAT_STR % self.find_parent()
+        parent = pci_dict_to_bdf_str(self.find_parent())
         pci_names = os.popen('ls ' + sysfs_mnt + SYSFS_PCI_DEVS_PATH + '/' + \
             parent + '/').read()
         funcs = extract_the_exact_pci_names(pci_names)
@@ -753,8 +770,7 @@ class PciDevice:
         if len(devs) == 0:
             return
         for pci_dev in devs:
-            (dom, b, d, f) = parse_pci_name(pci_dev)
-            dev = PciDevice(dom, b, d, f)
+            dev = PciDevice(parse_pci_name(pci_dev))
             if dev.driver == 'pciback':
                 continue
             err_msg = 'pci: %s must be co-assigned to the same guest with %s' + \
@@ -780,7 +796,7 @@ class PciDevice:
                     funcs = self.find_all_the_multi_functions()
                     self.devs_check_driver(funcs)
 
-                    parent = '%04x:%02x:%02x.%01x' % self.find_parent()
+                    parent = pci_dict_to_bdf_str(self.find_parent())
 
                     # Do Secondary Bus Reset.
                     self.do_secondary_bus_reset(parent, funcs)
Index: xen-unstable.hg/tools/python/xen/xend/XendDomainInfo.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xend/XendDomainInfo.py	2009-06-15 11:22:35.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xend/XendDomainInfo.py	2009-06-15 11:23:43.000000000 +1000
@@ -39,7 +39,8 @@ from xen.util import asserts, auxbin
 from xen.util.blkif import blkdev_uname_to_file, blkdev_uname_to_taptype
 import xen.util.xsm.xsm as security
 from xen.util import xsconstants
-from xen.util.pci import serialise_pci_opts, pci_opts_list_to_sxp
+from xen.util.pci import serialise_pci_opts, pci_opts_list_to_sxp, \
+                         pci_dict_to_bdf_str, pci_dict_to_xc_str
 
 from xen.xend import balloon, sxp, uuid, image, arch
 from xen.xend import XendOptions, XendNode, XendConfig
@@ -310,9 +311,8 @@ def do_FLR(domid):
     dev_str_list = get_assigned_pci_devices(domid)
 
     for dev_str in dev_str_list:
-        (dom, b, d, f) = parse_pci_name(dev_str)
         try:
-            dev = PciDevice(dom, b, d, f)
+            dev = PciDevice(parse_pci_name(dev_str))
         except Exception, e:
             raise VmError("pci: failed to locate device and "+
                     "parse it's resources - "+str(e))
@@ -652,23 +652,15 @@ class XendDomainInfo:
                     raise VmError("device is already inserted")
 
         # Test whether the devices can be assigned with VT-d
-        pci_str = "%s, %s, %s, %s" % (new_dev['domain'],
-                new_dev['bus'],
-                new_dev['slot'],
-                new_dev['func'])
-        bdf = xc.test_assign_device(0, pci_str)
+        bdf = xc.test_assign_device(0, pci_dict_to_xc_str(new_dev))
         if bdf != 0:
             if bdf == -1:
                 raise VmError("failed to assign device: maybe the platform"
                               " doesn't support VT-d, or VT-d isn't enabled"
                               " properly?")
-            bus = (bdf >> 16) & 0xff
-            devfn = (bdf >> 8) & 0xff
-            dev = (devfn >> 3) & 0x1f
-            func = devfn & 0x7
-            raise VmError("fail to assign device(%x:%x.%x): maybe it has"
+            raise VmError("fail to assign device(%s): maybe it has"
                           " already been assigned to other domain, or maybe"
-                          " it doesn't exist." % (bus, dev, func))
+                          " it doesn't exist." % pci_dict_to_bdf_str(new_dev))
 
         # Here, we duplicate some checkings (in some cases, we mustn't allow
         # a device to be hot-plugged into an HVM guest) that are also done in
@@ -680,12 +672,8 @@ class XendDomainInfo:
         # Test whether the device is owned by pciback. For instance, we can't
         # hotplug a device being used by Dom0 itself to an HVM guest.
         from xen.xend.server.pciif import PciDevice, parse_pci_name
-        domain = int(new_dev['domain'],16)
-        bus    = int(new_dev['bus'],16)
-        dev    = int(new_dev['slot'],16)
-        func   = int(new_dev['func'],16)
         try:
-            pci_device = PciDevice(domain, bus, dev, func)
+            pci_device = PciDevice(new_dev)
         except Exception, e:
             raise VmError("pci: failed to locate device and "+
                     "parse it's resources - "+str(e))
@@ -710,9 +698,8 @@ class XendDomainInfo:
         pci_device.devs_check_driver(coassignment_list)
         assigned_pci_device_str_list = self._get_assigned_pci_devices()
         for pci_str in coassignment_list:
-            (domain, bus, dev, func) = parse_pci_name(pci_str) 
-            dev_str =  '0x%x,0x%x,0x%x,0x%x' % (domain, bus, dev, func)
-            if xc.test_assign_device(0, dev_str) == 0:
+            pci_dev = parse_pci_name(pci_str)
+            if xc.test_assign_device(0, pci_dict_to_xc_str(pci_dev)) == 0:
                 continue
             if not pci_str in assigned_pci_device_str_list:
                 raise VmError(("pci: failed to pci-attach %s to domain %s" + \
@@ -742,12 +729,9 @@ class XendDomainInfo:
             if new_dev.has_key('opts'):
                 opts = ',' + serialise_pci_opts(new_dev['opts'])
 
-            bdf_str = "%s:%s:%s.%s@%s%s" % (new_dev['domain'],
-                new_dev['bus'],
-                new_dev['slot'],
-                new_dev['func'],
-                new_dev['vslot'],
-                opts)
+            bdf_str = "%s@%02x%s" % (pci_dict_to_bdf_str(new_dev),
+                                     int(new_dev['vslot'], 16), opts)
+            log.debug("XendDomainInfo.hvm_pci_device_insert_dev: %s" % bdf_str)
             self.image.signalDeviceModel('pci-ins', 'pci-inserted', bdf_str)
 
             vslot = xstransact.Read("/local/domain/0/device-model/%i/parameter"
@@ -864,9 +848,8 @@ class XendDomainInfo:
                         vslot = x['vslot']
                         break
                 if vslot == "":
-                    raise VmError("Device %04x:%02x:%02x.%01x is not connected"
-                                  % (int(dev['domain'],16), int(dev['bus'],16),
-                                     int(dev['slot'],16), int(dev['func'],16)))
+                    raise VmError("Device %s is not connected" %
+                                  pci_dict_to_bdf_str(dev))
                 self.hvm_destroyPCIDevice(int(vslot, 16))
                 # Update vslot
                 dev['vslot'] = vslot
@@ -1152,12 +1135,8 @@ class XendDomainInfo:
         # list of D's co-assignment devices, DD is not assigned (to domN).
         # 
         from xen.xend.server.pciif import PciDevice
-        domain = int(x['domain'],16)
-        bus    = int(x['bus'],16)
-        dev    = int(x['slot'],16)
-        func   = int(x['func'],16)
         try:
-            pci_device = PciDevice(domain, bus, dev, func)
+            pci_device = PciDevice(x)
         except Exception, e:
             raise VmError("pci: failed to locate device and "+
                     "parse it's resources - "+str(e))
@@ -1172,9 +1151,8 @@ class XendDomainInfo:
                     )% (pci_device.name, self.info['name_label'], pci_str))
 
 
-        bdf_str = "%s:%s:%s.%s" % (x['domain'], x['bus'], x['slot'], x['func'])
+        bdf_str = pci_dict_to_bdf_str(x)
         log.info("hvm_destroyPCIDevice:%s:%s!", x, bdf_str)
-
         if self.domid is not None:
             self.image.signalDeviceModel('pci-rem', 'pci-removed', bdf_str)
 
@@ -1338,21 +1316,12 @@ class XendDomainInfo:
         if self.domid is not None:
             return get_assigned_pci_devices(self.domid)
 
-        dev_str_list = []
         dev_info = self._getDeviceInfo_pci(devid)
         if dev_info is None:
-            return dev_str_list
+            return []
         dev_uuid = sxp.child_value(dev_info, 'uuid')
         pci_conf = self.info['devices'][dev_uuid][1]
-        pci_devs = pci_conf['devs']
-        for pci_dev in pci_devs:
-            domain = int(pci_dev['domain'], 16)
-            bus = int(pci_dev['bus'], 16)
-            slot = int(pci_dev['slot'], 16)
-            func = int(pci_dev['func'], 16)
-            dev_str = "%04x:%02x:%02x.%01x" % (domain, bus, slot, func)
-            dev_str_list = dev_str_list + [dev_str]
-        return dev_str_list 
+        return map(pci_dict_to_bdf_str, pci_conf['devs'])
 
     def setMemoryTarget(self, target):
         """Set the memory target of this domain.
@@ -3909,12 +3878,12 @@ class XendDomainInfo:
         target_dev = None
         new_pci_sxp = ['pci']
         for dev in sxp.children(old_pci_sxp, 'dev'):
-            domain = int(sxp.child_value(dev, 'domain'), 16)
-            bus = int(sxp.child_value(dev, 'bus'), 16)
-            slot = int(sxp.child_value(dev, 'slot'), 16)
-            func = int(sxp.child_value(dev, 'func'), 16)
-            name = "%04x:%02x:%02x.%01x" % (domain, bus, slot, func)
-            if ppci.get_name() == name:
+            pci_dev = {}
+            pci_dev['domain'] = sxp.child_value(dev, 'domain')
+            pci_dev['bus'] = sxp.child_value(dev, 'bus')
+            pci_dev['slot'] = sxp.child_value(dev, 'slot')
+            pci_dev['func'] = sxp.child_value(dev, 'func')
+            if ppci.get_name() == pci_dict_to_bdf_str(pci_dev):
                 target_dev = dev
             else:
                 new_pci_sxp.append(dev)
Index: xen-unstable.hg/tools/python/xen/xend/XendNode.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xend/XendNode.py	2009-06-15 11:20:35.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xend/XendNode.py	2009-06-15 11:23:43.000000000 +1000
@@ -340,8 +340,7 @@ class XendNode:
                 except KeyError:
                     pass
 
-        (domain, bus, slot, func) = PciUtil.parse_pci_name(pci_name)
-        pci_dev = PciUtil.PciDevice(domain, bus, slot, func)
+        pci_dev = PciUtil.PciDevice(PciUtil.parse_pci_name(pci_name))
         ppci_record = {
             'domain':                   pci_dev.domain,
             'bus':                      pci_dev.bus,
Index: xen-unstable.hg/tools/python/xen/xend/server/pciif.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xend/server/pciif.py	2009-06-15 11:22:35.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xend/server/pciif.py	2009-06-15 11:23:43.000000000 +1000
@@ -130,13 +130,7 @@ class PciController(DevController):
                     log.debug('Reconfiguring PCI device %s.' % dev)
                     attaching = False
 
-                (domain, bus, slotfunc) = dev.split(':')
-                (slot, func) = slotfunc.split('.')
-                domain = parse_hex(domain)
-                bus = parse_hex(bus)
-                slot = parse_hex(slot)
-                func = parse_hex(func)
-                self.setupOneDevice(domain, bus, slot, func)
+                self.setupOneDevice(parse_pci_name(dev))
 
                 self.writeBackend(devid, 'dev-%i' % devno, dev)
                 self.writeBackend(devid, 'state-%i' % devno,
@@ -248,15 +242,13 @@ class PciController(DevController):
             return
 
         #group string format xx:xx.x,xx:xx.x,
-        devstr_len = group_str.find(',')
-        for i in range(0, len(group_str), devstr_len + 1):
-            (bus, slotfunc) = group_str[i:i + devstr_len].split(':')
-            (slot, func) = slotfunc.split('.')
-            b = parse_hex(bus)
-            d = parse_hex(slot)
-            f = parse_hex(func)
+        for i in group_str.split(','):
+            if i == '':
+                continue
+            pci_dev = parse_pci_name(i)
+            pci_dev['domain'] = '%04x' % dev.domain
             try:
-                sdev = PciDevice(dev.domain, b, d, f)
+                sdev = PciDevice(pci_dev)
             except Exception, e:
                 #no dom0 drivers bound to sdev
                 continue
@@ -270,13 +262,13 @@ class PciController(DevController):
                     )%(sdev.name, dev.name))
         return
 
-    def setupOneDevice(self, domain, bus, slot, func):
+    def setupOneDevice(self, pci_dev):
         """ Attach I/O resources for device to frontend domain
         """
         fe_domid = self.getDomid()
 
         try:
-            dev = PciDevice(domain, bus, slot, func)
+            dev = PciDevice(pci_dev)
         except Exception, e:
             raise VmError("pci: failed to locate device and "+
                     "parse it's resources - "+str(e))
@@ -305,12 +297,11 @@ class PciController(DevController):
 
         if not self.vm.info.is_hvm():
             # Setup IOMMU device assignment
-            pci_str = "0x%x, 0x%x, 0x%x, 0x%x" % (domain, bus, slot, func)
-            bdf = xc.assign_device(fe_domid, pci_str)
+            bdf = xc.assign_device(fe_domid, pci_dict_to_xc_str(pci_dev))
+            pci_str = pci_dict_to_bdf_str(pci_dev)
             if bdf > 0:
-                raise VmError("Failed to assign device to IOMMU (%x:%x.%x)"
-                              % (bus, slot, func))
-            log.debug("pci: assign device %x:%x.%x" % (bus, slot, func))
+                raise VmError("Failed to assign device to IOMMU (%s)" % pci_str)
+            log.debug("pci: assign device %s" % pci_str)
 
         for (start, size) in dev.ioports:
             log.debug('pci: enabling ioport 0x%x/0x%x'%(start,size))
@@ -366,23 +357,15 @@ class PciController(DevController):
     def setupDevice(self, config):
         """Setup devices from config
         """
-        pci_str_list = []
-        pci_dev_list = []
-        for pci_config in config.get('devs', []):
-            domain = parse_hex(pci_config.get('domain', 0))
-            bus = parse_hex(pci_config.get('bus', 0))
-            slot = parse_hex(pci_config.get('slot', 0))
-            func = parse_hex(pci_config.get('func', 0))            
-            pci_str = '%04x:%02x:%02x.%01x' % (domain, bus, slot, func)
-            pci_str_list = pci_str_list + [pci_str]
-            pci_dev_list = pci_dev_list + [(domain, bus, slot, func)]
+        pci_dev_list = config.get('devs', [])
+        pci_str_list = map(pci_dict_to_bdf_str, pci_dev_list)
 
         if len(pci_str_list) != len(set(pci_str_list)):
             raise VmError('pci: duplicate devices specified in guest config?')
 
-        for (domain, bus, slot, func) in pci_dev_list:
+        for pci_dev in pci_dev_list:
             try:
-                dev = PciDevice(domain, bus, slot, func)
+                dev = PciDevice(pci_dev)
             except Exception, e:
                 raise VmError("pci: failed to locate device and "+
                         "parse it's resources - "+str(e))
@@ -427,9 +410,7 @@ class PciController(DevController):
                     dev.devs_check_driver(devs_str)
                     for s in devs_str:
                         if not s in pci_str_list:
-                            (s_dom, s_bus, s_slot, s_func) = parse_pci_name(s)
-                            s_pci_str = '0x%x,0x%x,0x%x,0x%x' % \
-                                (s_dom, s_bus, s_slot, s_func)
+                            s_pci_str = pci_dict_to_bdf_str(parse_pci_name(s))
                             # s has been assigned to other guest?
                             if xc.test_assign_device(0, s_pci_str) != 0:
                                 err_msg = 'pci: %s must be co-assigned to the'+\
@@ -453,13 +434,13 @@ class PciController(DevController):
         return True
 
 
-    def cleanupOneDevice(self, domain, bus, slot, func):
+    def cleanupOneDevice(self, pci_dev):
         """ Detach I/O resources for device from frontend domain
         """
         fe_domid = self.getDomid()
 
         try:
-            dev = PciDevice(domain, bus, slot, func)
+            dev = PciDevice(pci_dev)
         except Exception, e:
             raise VmError("pci: failed to locate device and "+
                     "parse it's resources - "+str(e))
@@ -476,12 +457,11 @@ class PciController(DevController):
         # DMA transaction, etc
         dev.do_FLR()
 
-        pci_str = "0x%x, 0x%x, 0x%x, 0x%x" % (domain, bus, slot, func)
-        bdf = xc.deassign_device(fe_domid, pci_str)
+        bdf = xc.deassign_device(fe_domid, pci_dict_to_xc_str(pci_dev))
+        pci_str = pci_dict_to_bdf_str(pci_dev)
         if bdf > 0:
-            raise VmError("Failed to deassign device from IOMMU (%x:%x.%x)"
-                          % (bus, slot, func))
-        log.debug("pci: Deassign device %x:%x.%x" % (bus, slot, func))
+            raise VmError("Failed to deassign device from IOMMU (%s)" % pci_str)
+        log.debug("pci: Deassign device %s" % pci_str)
 
         for (start, size) in dev.ioports:
             log.debug('pci: disabling ioport 0x%x/0x%x'%(start,size))
@@ -530,15 +510,9 @@ class PciController(DevController):
             state = int(self.readBackend(devid, 'state-%i' % i))
             if state == xenbusState['Closing']:
                 # Detach I/O resources.
-                dev = self.readBackend(devid, 'dev-%i' % i)
-                (domain, bus, slotfunc) = dev.split(':')
-                (slot, func) = slotfunc.split('.')
-                domain = parse_hex(domain)
-                bus = parse_hex(bus)
-                slot = parse_hex(slot)
-                func = parse_hex(func)            
+                pci_dev = parse_pci_name(self.readBackend(devid, 'dev-%i' % i))
                 # In HVM case, I/O resources are disabled in ioemu.
-                self.cleanupOneDevice(domain, bus, slot, func)
+                self.cleanupOneDevice(pci_dev)
                 # Remove xenstore nodes.
                 list = ['dev', 'vdev', 'state', 'uuid', 'vslot']
                 if self.readBackend(devid, 'opts-%i' % i) is not None:

-- 

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

* [patch 09/16] xend: pass-through: Use common parsing code in preprocess_pci()
  2009-06-15  1:55 [patch 00/16] xend: pass-through: various clean-ups and infrastructure Simon Horman
                   ` (7 preceding siblings ...)
  2009-06-15  1:55 ` [patch 08/16] xend: pass-through: Common parse_pci_name() Simon Horman
@ 2009-06-15  1:55 ` Simon Horman
  2009-06-15  1:55 ` [patch 10/16] xend: pass-through: Add pci_dict_cmp() Simon Horman
                   ` (6 subsequent siblings)
  15 siblings, 0 replies; 28+ messages in thread
From: Simon Horman @ 2009-06-15  1:55 UTC (permalink / raw)
  To: xen-devel; +Cc: Masaki Kanno, Dexuan Cui

[-- Attachment #1: preprocess_pci-use-parse_pci_name_dict.patch --]
[-- Type: text/plain, Size: 3289 bytes --]

Cc: Dexuan Cui <dexuan.cui@intel.com>
Cc: Masaki Kanno <kanno.masaki@jp.fujitsu.com>
Signed-off-by: Simon Horman <horms@verge.net.au>

Index: xen-unstable.hg/tools/python/xen/xm/create.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xm/create.py	2009-06-13 11:03:40.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xm/create.py	2009-06-13 11:09:37.000000000 +1000
@@ -38,8 +38,8 @@ from xen.util import vscsi_util
 import xen.util.xsm.xsm as security
 from xen.xm.main import serverType, SERVER_XEN_API, get_single_vm
 from xen.util import utils, auxbin
-from xen.util.pci import split_pci_opts, check_pci_opts, \
-                         pci_opts_list_to_sxp
+from xen.util.pci import pci_opts_list_to_sxp, \
+                         parse_pci_name_extended, PciDeviceParseError
 
 from xen.xm.opts import *
 
@@ -710,14 +710,7 @@ def configure_pci(config_devs, vals):
         config_pci_bdf = ['dev', ['domain', domain], ['bus', bus], \
                           ['slot', slot], ['func', func],
                           ['vslot', vslot]]
-
-        opts_list = split_pci_opts(opts)
-        try:
-            check_pci_opts(opts_list)
-        except PciDeviceParseError, ex:
-            err(str(ex))
-
-        config_opts = pci_opts_list_to_sxp(split_pci_opts(opts))
+        config_opts = pci_opts_list_to_sxp(opts)
         config_pci.append(sxp.merge(config_pci_bdf, config_opts))
 
     if len(config_pci)>0:
@@ -1052,33 +1045,18 @@ def preprocess_cpuid(vals, attr_name):
                 cpuid[input][res['reg']] = res['val'] # new register
             setattr(vals, attr_name, cpuid)
 
+def pci_dict_to_tuple(dev):
+    return (dev['domain'], dev['bus'], dev['slot'], dev['func'],
+            dev['vslot'], dev.get('opts', []))
+
 def preprocess_pci(vals):
-    if not vals.pci: return
-    pci = []
-    for pci_dev_str in vals.pci:
-        pci_match = re.match(r"((?P<domain>[0-9a-fA-F]{1,4})[:,])?" + \
-                r"(?P<bus>[0-9a-fA-F]{1,2})[:,]" + \
-                r"(?P<slot>[0-9a-fA-F]{1,2})[.,]" + \
-                r"(?P<func>[0-7])" + \
-                r"(@(?P<vslot>[01]?[0-9a-fA-F]))?" + \
-                r"(,(?P<opts>.*))?$", \
-                pci_dev_str)
-        if pci_match!=None:
-            pci_dev_info = pci_match.groupdict('')
-            if pci_dev_info['domain']=='':
-                pci_dev_info['domain']='0'
-            if pci_dev_info['vslot']=='':
-                pci_dev_info['vslot']="%02x" % AUTO_PHP_SLOT
-            try:
-                pci.append( ('0x'+pci_dev_info['domain'], \
-                        '0x'+pci_dev_info['bus'], \
-                        '0x'+pci_dev_info['slot'], \
-                        '0x'+pci_dev_info['func'], \
-                        '0x'+pci_dev_info['vslot'], \
-                        pci_dev_info['opts']))
-            except IndexError:
-                err('Error in PCI slot syntax "%s"'%(pci_dev_str))
-    vals.pci = pci
+    if not vals.pci:
+        return
+    try:
+        vals.pci = map(pci_dict_to_tuple,
+                       map(parse_pci_name_extended, vals.pci))
+    except PciDeviceParseError, ex:
+        err(str(ex))
 
 def preprocess_vscsi(vals):
     if not vals.vscsi: return

-- 

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

* [patch 10/16] xend: pass-through: Add pci_dict_cmp()
  2009-06-15  1:55 [patch 00/16] xend: pass-through: various clean-ups and infrastructure Simon Horman
                   ` (8 preceding siblings ...)
  2009-06-15  1:55 ` [patch 09/16] xend: pass-through: Use common parsing code in preprocess_pci() Simon Horman
@ 2009-06-15  1:55 ` Simon Horman
  2009-06-15  1:55 ` [patch 11/16] xend: pass-through: Move pci conversion functions to pci.py Simon Horman
                   ` (5 subsequent siblings)
  15 siblings, 0 replies; 28+ messages in thread
From: Simon Horman @ 2009-06-15  1:55 UTC (permalink / raw)
  To: xen-devel; +Cc: Masaki Kanno, Dexuan Cui

[-- Attachment #1: pci_dict_cmp.patch --]
[-- Type: text/plain, Size: 3933 bytes --]

pci_dict_cmp() compares the two pci devices in dict format.

Cc: Dexuan Cui <dexuan.cui@intel.com>
Cc: Masaki Kanno <kanno.masaki@jp.fujitsu.com>
Signed-off-by: Simon Horman <horms@verge.net.au>

Index: xen-unstable.hg/tools/python/xen/util/pci.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/util/pci.py	2009-06-15 11:24:32.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/util/pci.py	2009-06-15 11:24:34.000000000 +1000
@@ -205,6 +205,10 @@ def pci_dict_to_bdf_str(dev):
 def pci_dict_to_xc_str(dev):
     return __pci_dict_to_fmt_str('0x%x, 0x%x, 0x%x, 0x%x', dev)
 
+def pci_dict_cmp(a, b, keys=['domain', 'bus', 'slot', 'func']):
+    return reduce(lambda x, y: x and y,
+                  map(lambda k: int(a[k], 16) == int(b[k], 16), keys))
+
 def extract_the_exact_pci_names(pci_names):
     result = []
 
Index: xen-unstable.hg/tools/python/xen/xend/XendDomainInfo.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xend/XendDomainInfo.py	2009-06-15 11:24:32.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xend/XendDomainInfo.py	2009-06-15 11:24:34.000000000 +1000
@@ -40,7 +40,7 @@ from xen.util.blkif import blkdev_uname_
 import xen.util.xsm.xsm as security
 from xen.util import xsconstants
 from xen.util.pci import serialise_pci_opts, pci_opts_list_to_sxp, \
-                         pci_dict_to_bdf_str, pci_dict_to_xc_str
+                         pci_dict_to_bdf_str, pci_dict_to_xc_str, pci_dict_cmp
 
 from xen.xend import balloon, sxp, uuid, image, arch
 from xen.xend import XendOptions, XendNode, XendConfig
@@ -645,10 +645,7 @@ class XendDomainInfo:
                    int(x['vslot'], 16) != AUTO_PHP_SLOT):
                     raise VmError("vslot %s already have a device." % (new_dev['vslot']))
 
-                if (int(x['domain'], 16) == int(new_dev['domain'], 16) and
-                   int(x['bus'], 16)    == int(new_dev['bus'], 16) and
-                   int(x['slot'], 16)   == int(new_dev['slot'], 16) and
-                   int(x['func'], 16)   == int(new_dev['func'], 16) ):
+                if (pci_dict_cmp(x, new_dev)):
                     raise VmError("device is already inserted")
 
         # Test whether the devices can be assigned with VT-d
@@ -839,23 +836,18 @@ class XendDomainInfo:
                 existing_dev_uuid = sxp.child_value(existing_dev_info, 'uuid')
                 existing_pci_conf = self.info['devices'][existing_dev_uuid][1]
                 existing_pci_devs = existing_pci_conf['devs']
-                vslot = ""
-                for x in existing_pci_devs:
-                    if ( int(x['domain'], 16) == int(dev['domain'], 16) and
-                         int(x['bus'], 16) == int(dev['bus'], 16) and
-                         int(x['slot'], 16) == int(dev['slot'], 16) and
-                         int(x['func'], 16) == int(dev['func'], 16) ):
-                        vslot = x['vslot']
-                        break
-                if vslot == "":
+                new_devs = filter(lambda x: pci_dict_cmp(x, dev),
+                                  existing_pci_devs)
+                if len(new_devs) < 0:
                     raise VmError("Device %s is not connected" %
                                   pci_dict_to_bdf_str(dev))
-                self.hvm_destroyPCIDevice(int(vslot, 16))
+                new_dev = new_devs[0]
+                self.hvm_destroyPCIDevice(int(new_dev['vslot'], 16))
                 # Update vslot
-                dev['vslot'] = vslot
+                dev['vslot'] = new_dev['vslot']
                 for n in sxp.children(pci_dev):
                     if(n[0] == 'vslot'):
-                        n[1] = vslot
+                        n[1] = new_dev['vslot']
 
         # If pci platform does not exist, create and exit.
         if existing_dev_info is None:

-- 

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

* [patch 11/16] xend: pass-through: Move pci conversion functions to pci.py
  2009-06-15  1:55 [patch 00/16] xend: pass-through: various clean-ups and infrastructure Simon Horman
                   ` (9 preceding siblings ...)
  2009-06-15  1:55 ` [patch 10/16] xend: pass-through: Add pci_dict_cmp() Simon Horman
@ 2009-06-15  1:55 ` Simon Horman
  2009-06-15  5:58   ` [patch 11/16] xend: pass-through: Move pci conversionfunctions " Masaki Kanno
  2009-06-15  1:55 ` [patch 12/16] xend: pass-through: Use generic code in pci_opts_list_to_sxp() Simon Horman
                   ` (4 subsequent siblings)
  15 siblings, 1 reply; 28+ messages in thread
From: Simon Horman @ 2009-06-15  1:55 UTC (permalink / raw)
  To: xen-devel; +Cc: Masaki Kanno, Dexuan Cui

[-- Attachment #1: move-pci_convert_dict_to_sxp.patch --]
[-- Type: text/plain, Size: 12054 bytes --]

Move dev_dict_to_sxp(), pci_convert_dict_to_sxp() and
pci_convert_sxp_to_dict() to pci.py, where other similar functions live.
This makes them accessible outside of the XendConfig class.

Cc: Dexuan Cui <dexuan.cui@intel.com>
Cc: Masaki Kanno <kanno.masaki@jp.fujitsu.com>
Signed-off-by: Simon Horman <horms@verge.net.au>

--- 

 tools/python/xen/util/pci.py            |   83 ++++++++++++++++++++++++++++
 tools/python/xen/xend/XendConfig.py     |   91 +------------------------------
 tools/python/xen/xend/XendDomainInfo.py |   10 ++-
 3 files changed, 94 insertions(+), 90 deletions(-)

Index: xen-unstable.hg/tools/python/xen/util/pci.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/util/pci.py	2009-06-13 21:39:44.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/util/pci.py	2009-06-13 21:39:56.000000000 +1000
@@ -14,6 +14,7 @@ import struct
 import time
 import threading
 from xen.util import utils
+from xen.xend import uuid
 from xen.xend import sxp
 from xen.xend.XendConstants import AUTO_PHP_SLOT
 
@@ -139,6 +140,88 @@ def pci_opts_list_to_sxp(list):
 def pci_opts_list_from_sxp(dev):
     return map(lambda x: sxp.children(x)[0], sxp.children(dev, 'opts'))
 
+# This includes a generic equivalent of pci_opts_list_to_sxp()
+def dev_dict_to_sxp(dev):
+    def f((key, val)):
+        if isinstance(val, types.ListType):
+            return map(lambda x: [key, x], val)
+        return [[key, val]]
+    dev_sxp = ['dev'] + reduce(lambda x, y: x + y, map(f, dev.items()))
+    return dev_sxp
+
+def pci_convert_dict_to_sxp(dev, state, sub_state = None):
+    pci_sxp = ['pci', dev_dict_to_sxp(dev), ['state', state]]
+    if sub_state != None:
+        pci_sxp.append(['sub_state', sub_state])
+    return pci_sxp
+
+def pci_convert_sxp_to_dict(dev_sxp):
+    """Convert pci device sxp to dict
+    @param dev_sxp: device configuration
+    @type  dev_sxp: SXP object (parsed config)
+    @return: dev_config
+    @rtype: dictionary
+    """
+    # Parsing the device SXP's. In most cases, the SXP looks
+    # like this:
+    #
+    # [device, [vif, [mac, xx:xx:xx:xx:xx:xx], [ip 1.3.4.5]]]
+    #
+    # However, for PCI devices it looks like this:
+    #
+    # [device, [pci, [dev, [domain, 0], [bus, 0], [slot, 1], [func, 2]]]
+    #
+    # It seems the reasoning for this difference is because
+    # pciif.py needs all the PCI device configurations at
+    # the same time when creating the devices.
+    #
+    # To further complicate matters, Xen 2.0 configuration format
+    # uses the following for pci device configuration:
+    #
+    # [device, [pci, [domain, 0], [bus, 0], [dev, 1], [func, 2]]]
+
+    # For PCI device hotplug support, the SXP of PCI devices is
+    # extendend like this:
+    #
+    # [device, [pci, [dev, [domain, 0], [bus, 0], [slot, 1], [func, 2],
+    #                      [vslot, 0]],
+    #                [state, 'Initialising']]]
+    #
+    # 'vslot' shows the virtual hotplug slot number which the PCI device
+    # is inserted in. This is only effective for HVM domains.
+    #
+    # state 'Initialising' indicates that the device is being attached,
+    # while state 'Closing' indicates that the device is being detached.
+    #
+    # The Dict looks like this:
+    #
+    # { devs: [{domain: 0, bus: 0, slot: 1, func: 2, vslot: 0}],
+    #   states: ['Initialising'] }
+
+    dev_config = {}
+
+    pci_devs = []
+    for pci_dev in sxp.children(dev_sxp, 'dev'):
+        pci_dev_info = dict(pci_dev[1:])
+        if 'opts' in pci_dev_info:
+            pci_dev_info['opts'] = pci_opts_list_from_sxp(pci_dev)
+        # append uuid to each pci device that does't already have one.
+        if not pci_dev_info.has_key('uuid'):
+            dpci_uuid = pci_dev_info.get('uuid', uuid.createString())
+            pci_dev_info['uuid'] = dpci_uuid
+        pci_devs.append(pci_dev_info)
+    dev_config['devs'] = pci_devs
+
+    pci_states = []
+    for pci_state in sxp.children(dev_sxp, 'state'):
+        try:
+            pci_states.append(pci_state[1])
+        except IndexError:
+            raise XendError("Error reading state while parsing pci sxp")
+    dev_config['states'] = pci_states
+
+    return dev_config
+
 def parse_hex(val):
     try:
         if isinstance(val, types.StringTypes):
Index: xen-unstable.hg/tools/python/xen/xend/XendConfig.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xend/XendConfig.py	2009-06-13 21:39:44.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xend/XendConfig.py	2009-06-13 21:39:56.000000000 +1000
@@ -36,7 +36,8 @@ from xen.xend.xenstore.xstransact import
 from xen.xend.server.BlktapController import blktap_disk_types
 from xen.xend.server.netif import randomMAC
 from xen.util.blkif import blkdev_name_to_number, blkdev_uname_to_file
-from xen.util.pci import pci_opts_list_from_sxp
+from xen.util.pci import pci_opts_list_from_sxp, dev_dict_to_sxp, \
+                         pci_convert_sxp_to_dict
 from xen.util import xsconstants
 import xen.util.auxbin
 
@@ -1296,7 +1297,7 @@ class XendConfig(dict):
                 pci_devs_uuid = sxp.child_value(config, 'uuid',
                                                 uuid.createString())
 
-                pci_dict = self.pci_convert_sxp_to_dict(config)
+                pci_dict = pci_convert_sxp_to_dict(config)
                 pci_devs = pci_dict['devs']
 
                 # create XenAPI DPCI objects.
@@ -1596,79 +1597,6 @@ class XendConfig(dict):
 
         return ''
 
-    def pci_convert_dict_to_sxp(self, dev, state, sub_state = None):
-        pci_sxp = ['pci', self.dev_dict_to_sxp(dev), ['state', state]]
-        if sub_state != None:
-            pci_sxp.append(['sub_state', sub_state])
-        return pci_sxp
-
-    def pci_convert_sxp_to_dict(self, dev_sxp):
-        """Convert pci device sxp to dict
-        @param dev_sxp: device configuration
-        @type  dev_sxp: SXP object (parsed config)
-        @return: dev_config
-        @rtype: dictionary
-        """
-        # Parsing the device SXP's. In most cases, the SXP looks
-        # like this:
-        #
-        # [device, [vif, [mac, xx:xx:xx:xx:xx:xx], [ip 1.3.4.5]]]
-        #
-        # However, for PCI devices it looks like this:
-        #
-        # [device, [pci, [dev, [domain, 0], [bus, 0], [slot, 1], [func, 2]]]
-        #
-        # It seems the reasoning for this difference is because
-        # pciif.py needs all the PCI device configurations at
-        # the same time when creating the devices.
-        #
-        # To further complicate matters, Xen 2.0 configuration format
-        # uses the following for pci device configuration:
-        #
-        # [device, [pci, [domain, 0], [bus, 0], [dev, 1], [func, 2]]]
-
-        # For PCI device hotplug support, the SXP of PCI devices is
-        # extendend like this:
-        #
-        # [device, [pci, [dev, [domain, 0], [bus, 0], [slot, 1], [func, 2],
-        #                      [vslot, 0]],
-        #                [state, 'Initialising']]]
-        #
-        # 'vslot' shows the virtual hotplug slot number which the PCI device
-        # is inserted in. This is only effective for HVM domains.
-        #
-        # state 'Initialising' indicates that the device is being attached,
-        # while state 'Closing' indicates that the device is being detached.
-        #
-        # The Dict looks like this:
-        #
-        # { devs: [{domain: 0, bus: 0, slot: 1, func: 2, vslot: 0}],
-        #   states: ['Initialising'] }
-
-        dev_config = {}
-
-        pci_devs = []
-        for pci_dev in sxp.children(dev_sxp, 'dev'):
-            pci_dev_info = dict(pci_dev[1:])
-            if 'opts' in pci_dev_info:
-                pci_dev_info['opts'] = pci_opts_list_from_sxp(pci_dev)
-            # append uuid to each pci device that does't already have one.
-            if not pci_dev_info.has_key('uuid'):
-                dpci_uuid = pci_dev_info.get('uuid', uuid.createString())
-                pci_dev_info['uuid'] = dpci_uuid
-            pci_devs.append(pci_dev_info)
-        dev_config['devs'] = pci_devs 
-
-        pci_states = []
-        for pci_state in sxp.children(dev_sxp, 'state'):
-            try:
-                pci_states.append(pci_state[1])
-            except IndexError:
-                raise XendError("Error reading state while parsing pci sxp")
-        dev_config['states'] = pci_states
-
-        return dev_config
-
     def vscsi_convert_sxp_to_dict(self, dev_sxp):
         """Convert vscsi device sxp to dict
         @param dev_sxp: device configuration
@@ -1839,7 +1767,7 @@ class XendConfig(dict):
             dev_type, dev_info = self['devices'][dev_uuid]
 
             if dev_type == 'pci': # Special case for pci
-                pci_dict = self.pci_convert_sxp_to_dict(config)
+                pci_dict = pci_convert_sxp_to_dict(config)
                 pci_devs = pci_dict['devs']
 
                 # destroy existing XenAPI DPCI objects
@@ -1962,15 +1890,6 @@ class XendConfig(dict):
         result.extend([u for u in target['devices'].keys() if u not in result])
         return result
 
-    # This includes a generic equivalent of pci_opts_list_to_sxp()
-    def dev_dict_to_sxp(self, dev):
-        def f((key, val)):
-            if isinstance(val, types.ListType):
-                return map(lambda x: [key, x], val)
-            return [[key, val]]
-        dev_sxp = ['dev'] + reduce(lambda x, y: x + y, map(f, dev.items()))
-        return dev_sxp
-
     def all_devices_sxpr(self, target = None):
         """Returns the SXPR for all devices in the current configuration."""
         sxprs = []
@@ -1993,7 +1912,7 @@ class XendConfig(dict):
                     if dev_info.has_key('backend'):
                         sxpr.append(['backend', dev_info['backend']])
                 for pci_dev_info in dev_info['devs']:
-                    sxpr.append(self.dev_dict_to_sxp(pci_dev_info))
+                    sxpr.append(dev_dict_to_sxp(pci_dev_info))
                 sxprs.append((dev_type, sxpr))
             else:
                 sxpr = self.device_sxpr(dev_type = dev_type,
Index: xen-unstable.hg/tools/python/xen/xend/XendDomainInfo.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xend/XendDomainInfo.py	2009-06-13 21:39:44.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xend/XendDomainInfo.py	2009-06-13 21:40:34.000000000 +1000
@@ -40,7 +40,9 @@ from xen.util.blkif import blkdev_uname_
 import xen.util.xsm.xsm as security
 from xen.util import xsconstants
 from xen.util.pci import serialise_pci_opts, pci_opts_list_to_sxp, \
-                         pci_dict_to_bdf_str, pci_dict_to_xc_str, pci_dict_cmp
+                         pci_dict_to_bdf_str, pci_dict_to_xc_str, \
+                         pci_convert_sxp_to_dict, pci_convert_dict_to_sxp, \
+                         pci_dict_cmp
 
 from xen.xend import balloon, sxp, uuid, image, arch
 from xen.xend import XendOptions, XendNode, XendConfig
@@ -616,8 +618,8 @@ class XendDomainInfo:
         pci_conf = self.info['devices'][dev_uuid][1]
         pci_devs = pci_conf['devs']
         request = map(lambda x:
-                      self.info.pci_convert_dict_to_sxp(x, 'Initialising',
-                                                        'Booting'), pci_devs)
+                      pci_convert_dict_to_sxp(x, 'Initialising', 'Booting'),
+                      pci_devs)
 
         for i in request:
                 self.pci_device_configure(i)
@@ -815,7 +817,7 @@ class XendDomainInfo:
             raise XendError("Cannot detach when pci platform does not exist")
 
         pci_dev = sxp.children(dev_sxp, 'dev')[0]
-        dev_config = self.info.pci_convert_sxp_to_dict(dev_sxp)
+        dev_config = pci_convert_sxp_to_dict(dev_sxp)
         dev = dev_config['devs'][0]
                 
         # Do HVM specific processing

-- 

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

* [patch 12/16] xend: pass-through: Use generic code in pci_opts_list_to_sxp()
  2009-06-15  1:55 [patch 00/16] xend: pass-through: various clean-ups and infrastructure Simon Horman
                   ` (10 preceding siblings ...)
  2009-06-15  1:55 ` [patch 11/16] xend: pass-through: Move pci conversion functions to pci.py Simon Horman
@ 2009-06-15  1:55 ` Simon Horman
  2009-06-15 11:59   ` [patch v2] " Simon Horman
  2009-06-15  1:55 ` [patch 13/16] xend: pass-through: Add pci_tuple_to_dict() Simon Horman
                   ` (3 subsequent siblings)
  15 siblings, 1 reply; 28+ messages in thread
From: Simon Horman @ 2009-06-15  1:55 UTC (permalink / raw)
  To: xen-devel; +Cc: Masaki Kanno, Dexuan Cui

[-- Attachment #1: pci_opts_list_to_sxp-dev_dict_to_sxp.patch --]
[-- Type: text/plain, Size: 1027 bytes --]

Use dev_dict_to_sxp() inside pci_opts_list_to_sxp() now that it is
available.

Cc: Dexuan Cui <dexuan.cui@intel.com>
Cc: Masaki Kanno <kanno.masaki@jp.fujitsu.com>
Signed-off-by: Simon Horman <horms@verge.net.au>

Index: xen-unstable.hg/tools/python/xen/util/pci.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/util/pci.py	2009-06-15 11:24:37.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/util/pci.py	2009-06-15 11:24:37.000000000 +1000
@@ -135,12 +135,11 @@ def split_pci_opts(opts):
                filter(lambda x: x != '', opts.split(',')))
 
 def pci_opts_list_to_sxp(list):
-    return ['dev'] + map(lambda x: ['opts', x], list)
+    return dev_dict_to_sxp({'opts': list})
 
 def pci_opts_list_from_sxp(dev):
     return map(lambda x: sxp.children(x)[0], sxp.children(dev, 'opts'))
 
-# This includes a generic equivalent of pci_opts_list_to_sxp()
 def dev_dict_to_sxp(dev):
     def f((key, val)):
         if isinstance(val, types.ListType):

-- 

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

* [patch 13/16] xend: pass-through: Add pci_tuple_to_dict()
  2009-06-15  1:55 [patch 00/16] xend: pass-through: various clean-ups and infrastructure Simon Horman
                   ` (11 preceding siblings ...)
  2009-06-15  1:55 ` [patch 12/16] xend: pass-through: Use generic code in pci_opts_list_to_sxp() Simon Horman
@ 2009-06-15  1:55 ` Simon Horman
  2009-06-15  1:55 ` [patch 14/16] xend: pass-through: Use common parsing code in parse_pci_configuration() Simon Horman
                   ` (2 subsequent siblings)
  15 siblings, 0 replies; 28+ messages in thread
From: Simon Horman @ 2009-06-15  1:55 UTC (permalink / raw)
  To: xen-devel; +Cc: Masaki Kanno, Dexuan Cui

[-- Attachment #1: pci_tuple_to_dict.patch --]
[-- Type: text/plain, Size: 2091 bytes --]

This will be re-used in subsequent patches.

Cc: Dexuan Cui <dexuan.cui@intel.com>
Cc: Masaki Kanno <kanno.masaki@jp.fujitsu.com>
Signed-off-by: Simon Horman <horms@verge.net.au>

Index: xen-unstable.hg/tools/python/xen/xm/create.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xm/create.py	2009-06-13 11:13:29.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xm/create.py	2009-06-13 11:13:42.000000000 +1000
@@ -38,7 +38,7 @@ from xen.util import vscsi_util
 import xen.util.xsm.xsm as security
 from xen.xm.main import serverType, SERVER_XEN_API, get_single_vm
 from xen.util import utils, auxbin
-from xen.util.pci import pci_opts_list_to_sxp, \
+from xen.util.pci import dev_dict_to_sxp, \
                          parse_pci_name_extended, PciDeviceParseError
 
 from xen.xm.opts import *
@@ -706,12 +706,9 @@ def configure_pci(config_devs, vals):
     """Create the config for pci devices.
     """
     config_pci = []
-    for (domain, bus, slot, func, vslot, opts) in vals.pci:
-        config_pci_bdf = ['dev', ['domain', domain], ['bus', bus], \
-                          ['slot', slot], ['func', func],
-                          ['vslot', vslot]]
-        config_opts = pci_opts_list_to_sxp(opts)
-        config_pci.append(sxp.merge(config_pci_bdf, config_opts))
+    for pci_tuple in vals.pci:
+        pci_dev = pci_tuple_to_dict(pci_tuple)
+        config_pci.append(dev_dict_to_sxp(pci_dev))
 
     if len(config_pci)>0:
         config_pci.insert(0, 'pci')
@@ -1049,6 +1046,16 @@ def pci_dict_to_tuple(dev):
     return (dev['domain'], dev['bus'], dev['slot'], dev['func'],
             dev['vslot'], dev.get('opts', []))
 
+def pci_tuple_to_dict((domain, bus, slot, func, vslot, opts)):
+    pci_dev = { 'domain': domain,
+                'bus':    bus,
+                'slot':   slot,
+                'func':   func,
+                'vslot':  vslot}
+    if len(opts) > 0:
+        pci_dev['opts'] = opts
+    return pci_dev
+
 def preprocess_pci(vals):
     if not vals.pci:
         return

-- 

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

* [patch 14/16] xend: pass-through: Use common parsing code in parse_pci_configuration()
  2009-06-15  1:55 [patch 00/16] xend: pass-through: various clean-ups and infrastructure Simon Horman
                   ` (12 preceding siblings ...)
  2009-06-15  1:55 ` [patch 13/16] xend: pass-through: Add pci_tuple_to_dict() Simon Horman
@ 2009-06-15  1:55 ` Simon Horman
  2009-06-15  1:55 ` [patch 15/16] xend: pass-through: Use common parsing code in getDeviceConfiguration() Simon Horman
  2009-06-15  1:55 ` [patch 16/16] xend: pass-through: Clean up hvm_destroyPCIDevice() Simon Horman
  15 siblings, 0 replies; 28+ messages in thread
From: Simon Horman @ 2009-06-15  1:55 UTC (permalink / raw)
  To: xen-devel; +Cc: Masaki Kanno, Dexuan Cui

[-- Attachment #1: parse_pci_configuration-use-pci_parse_name.patch --]
[-- Type: text/plain, Size: 1979 bytes --]

This will be re-used in subsequent patches.

Cc: Dexuan Cui <dexuan.cui@intel.com>
Cc: Masaki Kanno <kanno.masaki@jp.fujitsu.com>
Signed-off-by: Simon Horman <horms@verge.net.au>

Index: xen-unstable.hg/tools/python/xen/xm/main.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xm/main.py	2009-06-13 22:30:08.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xm/main.py	2009-06-14 17:12:19.000000000 +1000
@@ -2486,36 +2486,16 @@ def parse_pci_configuration(args, state,
     dom = args[0]
     pci_dev_str = args[1]
     if len(args) == 3:
-        vslot = args[2]
-    else:
-        vslot = AUTO_PHP_SLOT_STR
-    pci=['pci']
-    pci_match = re.match(r"((?P<domain>[0-9a-fA-F]{1,4})[:,])?" + \
-            r"(?P<bus>[0-9a-fA-F]{1,2})[:,]" + \
-            r"(?P<slot>[0-9a-fA-F]{1,2})[.,]" + \
-            r"(?P<func>[0-7])$", pci_dev_str)
-    if pci_match == None:
-        raise OptionError("Invalid argument: %s %s" % (pci_dev_str, vslot))
-    pci_dev_info = pci_match.groupdict('0')
-
-    try:
-        pci_bdf =['dev', ['domain', '0x'+ pci_dev_info['domain']], \
-                ['bus', '0x'+ pci_dev_info['bus']],
-                ['slot', '0x'+ pci_dev_info['slot']],
-                ['func', '0x'+ pci_dev_info['func']],
-                ['vslot', '0x%x' % int(vslot, 16)]]
-    except:
-        raise OptionError("Invalid argument: %s %s" % (pci_dev_str, vslot))
+        pci_dev_str += '@' + args[2]
+    if len(opts) > 0:
+        pci_dev_str += ',' + serialise_pci_opts(opts)
 
     try:
-        check_pci_opts(opts)
+        pci_dev = parse_pci_name_extended(pci_dev_str)
     except PciDeviceParseError, ex:
         raise OptionError(str(ex))
 
-    pci.append(sxp.merge(pci_bdf, pci_opts_list_to_sxp(opts)))
-    pci.append(['state', state])
-
-    return (dom, pci)
+    return (dom, pci_convert_dict_to_sxp(pci_dev, state))
 
 def xm_pci_attach(args):
     config_pci_opts = []

-- 

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

* [patch 15/16] xend: pass-through: Use common parsing code in getDeviceConfiguration()
  2009-06-15  1:55 [patch 00/16] xend: pass-through: various clean-ups and infrastructure Simon Horman
                   ` (13 preceding siblings ...)
  2009-06-15  1:55 ` [patch 14/16] xend: pass-through: Use common parsing code in parse_pci_configuration() Simon Horman
@ 2009-06-15  1:55 ` Simon Horman
  2009-06-15  1:55 ` [patch 16/16] xend: pass-through: Clean up hvm_destroyPCIDevice() Simon Horman
  15 siblings, 0 replies; 28+ messages in thread
From: Simon Horman @ 2009-06-15  1:55 UTC (permalink / raw)
  To: xen-devel; +Cc: Masaki Kanno, Dexuan Cui

[-- Attachment #1: getDeviceConfiguration-use-pci_parse_name.patch --]
[-- Type: text/plain, Size: 2399 bytes --]

This will be re-used in subsequent patches.

Cc: Dexuan Cui <dexuan.cui@intel.com>
Cc: Masaki Kanno <kanno.masaki@jp.fujitsu.com>
Signed-off-by: Simon Horman <horms@verge.net.au>

Index: xen-unstable.hg/tools/python/xen/xend/server/pciif.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xend/server/pciif.py	2009-06-07 21:58:38.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xend/server/pciif.py	2009-06-07 22:12:13.000000000 +1000
@@ -170,31 +170,18 @@ class PciController(DevController):
         pci_devs = []
 
         for i in range(int(num_devs)):
-            dev_config = self.readBackend(devid, 'dev-%d' % i)
+            pci_dev = parse_pci_name(self.readBackend(devid, 'dev-%d' % i))
 
-            pci_match = re.match(r"((?P<domain>[0-9a-fA-F]{1,4})[:,])?" +
-                                 r"(?P<bus>[0-9a-fA-F]{1,2})[:,]" + 
-                                 r"(?P<slot>[0-9a-fA-F]{1,2})[.,]" + 
-                                 r"(?P<func>[0-7]{1,2})$", dev_config)
-            
-            if pci_match!=None:
-                pci_dev_info = pci_match.groupdict()
-                dev_dict = {'domain': '0x%(domain)s' % pci_dev_info,
-                                 'bus': '0x%(bus)s' % pci_dev_info,
-                                 'slot': '0x%(slot)s' % pci_dev_info,
-                                 'func': '0x%(func)s' % pci_dev_info}
-
-                # Per device uuid info
-                dev_dict['uuid'] = self.readBackend(devid, 'uuid-%d' % i)
-                dev_dict['vslot'] = '0x%s' % \
-                                    self.readBackend(devid, 'vslot-%d' % i)
-
-                #append opts info
-                opts = self.readBackend(devid, 'opts-%d' % i)
-                if opts is not None:
-                    dev_dict['opts'] = opts
+            # Per device uuid info
+            pci_dev['uuid'] = self.readBackend(devid, 'uuid-%d' % i)
+            pci_dev['vslot'] = '0x%s' % self.readBackend(devid, 'vslot-%d' % i)
+
+            #append opts info
+            opts = self.readBackend(devid, 'opts-%d' % i)
+            if opts is not None:
+                pci_dev['opts'] = opts
 
-                pci_devs.append(dev_dict)
+            pci_devs.append(pci_dev)
 
         result['devs'] = pci_devs
         result['uuid'] = self.readBackend(devid, 'uuid')

-- 

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

* [patch 16/16] xend: pass-through: Clean up hvm_destroyPCIDevice()
  2009-06-15  1:55 [patch 00/16] xend: pass-through: various clean-ups and infrastructure Simon Horman
                   ` (14 preceding siblings ...)
  2009-06-15  1:55 ` [patch 15/16] xend: pass-through: Use common parsing code in getDeviceConfiguration() Simon Horman
@ 2009-06-15  1:55 ` Simon Horman
  15 siblings, 0 replies; 28+ messages in thread
From: Simon Horman @ 2009-06-15  1:55 UTC (permalink / raw)
  To: xen-devel; +Cc: Masaki Kanno, Dexuan Cui

[-- Attachment #1: xm-clean-up-hvm_destroyPCIDevice-2.patch --]
[-- Type: text/plain, Size: 3364 bytes --]

There seems to be little need to use the domain, bus, slot and function
to look up the virtual slot to pass as the argument to
hvm_destroyPCIDevice(), only to have hvm_destroyPCIDevice() use
the virtual slot for the sole purpose of looking up the
domain, bus, slot and function.

Cc: Dexuan Cui <dexuan.cui@intel.com>
Cc: Masaki Kanno <kanno.masaki@jp.fujitsu.com>
Signed-off-by: Simon Horman <horms@verge.net.au>

Index: xen-unstable.hg/tools/python/xen/xend/XendDomainInfo.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xend/XendDomainInfo.py	2009-06-15 11:24:37.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xend/XendDomainInfo.py	2009-06-15 11:24:43.000000000 +1000
@@ -844,7 +844,7 @@ class XendDomainInfo:
                     raise VmError("Device %s is not connected" %
                                   pci_dict_to_bdf_str(dev))
                 new_dev = new_devs[0]
-                self.hvm_destroyPCIDevice(int(new_dev['vslot'], 16))
+                self.hvm_destroyPCIDevice(new_dev)
                 # Update vslot
                 dev['vslot'] = new_dev['vslot']
                 for n in sxp.children(pci_dev):
@@ -1098,39 +1098,19 @@ class XendDomainInfo:
         for devclass in XendDevices.valid_devices():
             self.getDeviceController(devclass).waitForDevices()
 
-    def hvm_destroyPCIDevice(self, vslot):
-        log.debug("hvm_destroyPCIDevice called %s", vslot)
+    def hvm_destroyPCIDevice(self, pci_dev):
+        log.debug("hvm_destroyPCIDevice: %s", pci_dev)
 
         if not self.info.is_hvm():
             raise VmError("hvm_destroyPCIDevice called on non-HVM guest")
 
-        #all the PCI devs share one conf node
-        devid = '0'
-        vslot = int(vslot)
-        dev_info = self._getDeviceInfo_pci('0')#from self.info['devices']
-        dev_uuid = sxp.child_value(dev_info, 'uuid')
-
-        #delete the pci bdf config under the pci device
-        pci_conf = self.info['devices'][dev_uuid][1]
-        pci_len = len(pci_conf['devs'])
-
-        #find the pass-through device with the virtual slot
-        devnum = 0
-        for x in pci_conf['devs']:
-            if int(x['vslot'], 16) == vslot:
-                break
-            devnum += 1
-
-        if devnum >= pci_len:
-            raise VmError("Device @ vslot 0x%x doesn't exist." % (vslot))
-
         # Check the co-assignment.
         # To pci-detach a device D from domN, we should ensure: for each DD in the
         # list of D's co-assignment devices, DD is not assigned (to domN).
         # 
         from xen.xend.server.pciif import PciDevice
         try:
-            pci_device = PciDevice(x)
+            pci_device = PciDevice(pci_dev)
         except Exception, e:
             raise VmError("pci: failed to locate device and "+
                     "parse it's resources - "+str(e))
@@ -1145,8 +1125,8 @@ class XendDomainInfo:
                     )% (pci_device.name, self.info['name_label'], pci_str))
 
 
-        bdf_str = pci_dict_to_bdf_str(x)
-        log.info("hvm_destroyPCIDevice:%s:%s!", x, bdf_str)
+        bdf_str = pci_dict_to_bdf_str(pci_dev)
+        log.info("hvm_destroyPCIDevice:%s:%s!", pci_dev, bdf_str)
         if self.domid is not None:
             self.image.signalDeviceModel('pci-rem', 'pci-removed', bdf_str)
 

-- 

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

* Re: [patch 11/16] xend: pass-through: Move pci conversionfunctions to pci.py
  2009-06-15  1:55 ` [patch 11/16] xend: pass-through: Move pci conversion functions to pci.py Simon Horman
@ 2009-06-15  5:58   ` Masaki Kanno
  2009-06-15  6:15     ` Simon Horman
  0 siblings, 1 reply; 28+ messages in thread
From: Masaki Kanno @ 2009-06-15  5:58 UTC (permalink / raw)
  To: Simon Horman, xen-devel; +Cc: Dexuan Cui

[-- Attachment #1: Mail message body --]
[-- Type: text/plain, Size: 12967 bytes --]

Hi Simon,

dev_dict_to_sxp method in XendConfig.py is called for both pci 
devices and vscsi devices.  So, I think that the method should 
be not moved to pci.py. 

I suggest separating the processing of pci devices and the 
processing of vscsi devices in all_devices_sxpr method. 
I attach a patch for separating them. 

Signed-off-by: Masaki Kanno <kanno.masaki@jp.fujitsu.com>

Best regards,
 Kan

Mon, 15 Jun 2009 11:55:26 +1000, Simon Horman wrote:

>Move dev_dict_to_sxp(), pci_convert_dict_to_sxp() and
>pci_convert_sxp_to_dict() to pci.py, where other similar functions live.
>This makes them accessible outside of the XendConfig class.
>
>Cc: Dexuan Cui <dexuan.cui@intel.com>
>Cc: Masaki Kanno <kanno.masaki@jp.fujitsu.com>
>Signed-off-by: Simon Horman <horms@verge.net.au>
>
>--- 
>
> tools/python/xen/util/pci.py            |   83 ++++++++++++++++++++++++++++
> tools/python/xen/xend/XendConfig.py     |   91 +--------------------------
>----
> tools/python/xen/xend/XendDomainInfo.py |   10 ++-
> 3 files changed, 94 insertions(+), 90 deletions(-)
>
>Index: xen-unstable.hg/tools/python/xen/util/pci.py
>===================================================================
>--- xen-unstable.hg.orig/tools/python/xen/util/pci.py	2009-06-13 21:39:44.
>000000000 +1000
>+++ xen-unstable.hg/tools/python/xen/util/pci.py	2009-06-13 21:39:56.
>000000000 +1000
>@@ -14,6 +14,7 @@ import struct
> import time
> import threading
> from xen.util import utils
>+from xen.xend import uuid
> from xen.xend import sxp
> from xen.xend.XendConstants import AUTO_PHP_SLOT
> 
>@@ -139,6 +140,88 @@ def pci_opts_list_to_sxp(list):
> def pci_opts_list_from_sxp(dev):
>     return map(lambda x: sxp.children(x)[0], sxp.children(dev, 'opts'))
> 
>+# This includes a generic equivalent of pci_opts_list_to_sxp()
>+def dev_dict_to_sxp(dev):
>+    def f((key, val)):
>+        if isinstance(val, types.ListType):
>+            return map(lambda x: [key, x], val)
>+        return [[key, val]]
>+    dev_sxp = ['dev'] + reduce(lambda x, y: x + y, map(f, dev.items()))
>+    return dev_sxp
>+
>+def pci_convert_dict_to_sxp(dev, state, sub_state = None):
>+    pci_sxp = ['pci', dev_dict_to_sxp(dev), ['state', state]]
>+    if sub_state != None:
>+        pci_sxp.append(['sub_state', sub_state])
>+    return pci_sxp
>+
>+def pci_convert_sxp_to_dict(dev_sxp):
>+    """Convert pci device sxp to dict
>+    @param dev_sxp: device configuration
>+    @type  dev_sxp: SXP object (parsed config)
>+    @return: dev_config
>+    @rtype: dictionary
>+    """
>+    # Parsing the device SXP's. In most cases, the SXP looks
>+    # like this:
>+    #
>+    # [device, [vif, [mac, xx:xx:xx:xx:xx:xx], [ip 1.3.4.5]]]
>+    #
>+    # However, for PCI devices it looks like this:
>+    #
>+    # [device, [pci, [dev, [domain, 0], [bus, 0], [slot, 1], [func, 2]]]
>+    #
>+    # It seems the reasoning for this difference is because
>+    # pciif.py needs all the PCI device configurations at
>+    # the same time when creating the devices.
>+    #
>+    # To further complicate matters, Xen 2.0 configuration format
>+    # uses the following for pci device configuration:
>+    #
>+    # [device, [pci, [domain, 0], [bus, 0], [dev, 1], [func, 2]]]
>+
>+    # For PCI device hotplug support, the SXP of PCI devices is
>+    # extendend like this:
>+    #
>+    # [device, [pci, [dev, [domain, 0], [bus, 0], [slot, 1], [func, 2],
>+    #                      [vslot, 0]],
>+    #                [state, 'Initialising']]]
>+    #
>+    # 'vslot' shows the virtual hotplug slot number which the PCI device
>+    # is inserted in. This is only effective for HVM domains.
>+    #
>+    # state 'Initialising' indicates that the device is being attached,
>+    # while state 'Closing' indicates that the device is being detached.
>+    #
>+    # The Dict looks like this:
>+    #
>+    # { devs: [{domain: 0, bus: 0, slot: 1, func: 2, vslot: 0}],
>+    #   states: ['Initialising'] }
>+
>+    dev_config = {}
>+
>+    pci_devs = []
>+    for pci_dev in sxp.children(dev_sxp, 'dev'):
>+        pci_dev_info = dict(pci_dev[1:])
>+        if 'opts' in pci_dev_info:
>+            pci_dev_info['opts'] = pci_opts_list_from_sxp(pci_dev)
>+        # append uuid to each pci device that does't already have one.
>+        if not pci_dev_info.has_key('uuid'):
>+            dpci_uuid = pci_dev_info.get('uuid', uuid.createString())
>+            pci_dev_info['uuid'] = dpci_uuid
>+        pci_devs.append(pci_dev_info)
>+    dev_config['devs'] = pci_devs
>+
>+    pci_states = []
>+    for pci_state in sxp.children(dev_sxp, 'state'):
>+        try:
>+            pci_states.append(pci_state[1])
>+        except IndexError:
>+            raise XendError("Error reading state while parsing pci sxp")
>+    dev_config['states'] = pci_states
>+
>+    return dev_config
>+
> def parse_hex(val):
>     try:
>         if isinstance(val, types.StringTypes):
>Index: xen-unstable.hg/tools/python/xen/xend/XendConfig.py
>===================================================================
>--- xen-unstable.hg.orig/tools/python/xen/xend/XendConfig.py	2009-06-13 21:
>39:44.000000000 +1000
>+++ xen-unstable.hg/tools/python/xen/xend/XendConfig.py	2009-06-13 21:
39:56
>.000000000 +1000
>@@ -36,7 +36,8 @@ from xen.xend.xenstore.xstransact import
> from xen.xend.server.BlktapController import blktap_disk_types
> from xen.xend.server.netif import randomMAC
> from xen.util.blkif import blkdev_name_to_number, blkdev_uname_to_file
>-from xen.util.pci import pci_opts_list_from_sxp
>+from xen.util.pci import pci_opts_list_from_sxp, dev_dict_to_sxp, \
>+                         pci_convert_sxp_to_dict
> from xen.util import xsconstants
> import xen.util.auxbin
> 
>@@ -1296,7 +1297,7 @@ class XendConfig(dict):
>                 pci_devs_uuid = sxp.child_value(config, 'uuid',
>                                                 uuid.createString())
> 
>-                pci_dict = self.pci_convert_sxp_to_dict(config)
>+                pci_dict = pci_convert_sxp_to_dict(config)
>                 pci_devs = pci_dict['devs']
> 
>                 # create XenAPI DPCI objects.
>@@ -1596,79 +1597,6 @@ class XendConfig(dict):
> 
>         return ''
> 
>-    def pci_convert_dict_to_sxp(self, dev, state, sub_state = None):
>-        pci_sxp = ['pci', self.dev_dict_to_sxp(dev), ['state', state]]
>-        if sub_state != None:
>-            pci_sxp.append(['sub_state', sub_state])
>-        return pci_sxp
>-
>-    def pci_convert_sxp_to_dict(self, dev_sxp):
>-        """Convert pci device sxp to dict
>-        @param dev_sxp: device configuration
>-        @type  dev_sxp: SXP object (parsed config)
>-        @return: dev_config
>-        @rtype: dictionary
>-        """
>-        # Parsing the device SXP's. In most cases, the SXP looks
>-        # like this:
>-        #
>-        # [device, [vif, [mac, xx:xx:xx:xx:xx:xx], [ip 1.3.4.5]]]
>-        #
>-        # However, for PCI devices it looks like this:
>-        #
>-        # [device, [pci, [dev, [domain, 0], [bus, 0], [slot, 1], [func, 2]]]
>-        #
>-        # It seems the reasoning for this difference is because
>-        # pciif.py needs all the PCI device configurations at
>-        # the same time when creating the devices.
>-        #
>-        # To further complicate matters, Xen 2.0 configuration format
>-        # uses the following for pci device configuration:
>-        #
>-        # [device, [pci, [domain, 0], [bus, 0], [dev, 1], [func, 2]]]
>-
>-        # For PCI device hotplug support, the SXP of PCI devices is
>-        # extendend like this:
>-        #
>-        # [device, [pci, [dev, [domain, 0], [bus, 0], [slot, 1], [func, 2],
>-        #                      [vslot, 0]],
>-        #                [state, 'Initialising']]]
>-        #
>-        # 'vslot' shows the virtual hotplug slot number which the PCI device
>-        # is inserted in. This is only effective for HVM domains.
>-        #
>-        # state 'Initialising' indicates that the device is being attached,
>-        # while state 'Closing' indicates that the device is being detached.
>-        #
>-        # The Dict looks like this:
>-        #
>-        # { devs: [{domain: 0, bus: 0, slot: 1, func: 2, vslot: 0}],
>-        #   states: ['Initialising'] }
>-
>-        dev_config = {}
>-
>-        pci_devs = []
>-        for pci_dev in sxp.children(dev_sxp, 'dev'):
>-            pci_dev_info = dict(pci_dev[1:])
>-            if 'opts' in pci_dev_info:
>-                pci_dev_info['opts'] = pci_opts_list_from_sxp(pci_dev)
>-            # append uuid to each pci device that does't already have one.
>-            if not pci_dev_info.has_key('uuid'):
>-                dpci_uuid = pci_dev_info.get('uuid', uuid.createString())
>-                pci_dev_info['uuid'] = dpci_uuid
>-            pci_devs.append(pci_dev_info)
>-        dev_config['devs'] = pci_devs 
>-
>-        pci_states = []
>-        for pci_state in sxp.children(dev_sxp, 'state'):
>-            try:
>-                pci_states.append(pci_state[1])
>-            except IndexError:
>-                raise XendError("Error reading state while parsing pci sxp")
>-        dev_config['states'] = pci_states
>-
>-        return dev_config
>-
>     def vscsi_convert_sxp_to_dict(self, dev_sxp):
>         """Convert vscsi device sxp to dict
>         @param dev_sxp: device configuration
>@@ -1839,7 +1767,7 @@ class XendConfig(dict):
>             dev_type, dev_info = self['devices'][dev_uuid]
> 
>             if dev_type == 'pci': # Special case for pci
>-                pci_dict = self.pci_convert_sxp_to_dict(config)
>+                pci_dict = pci_convert_sxp_to_dict(config)
>                 pci_devs = pci_dict['devs']
> 
>                 # destroy existing XenAPI DPCI objects
>@@ -1962,15 +1890,6 @@ class XendConfig(dict):
>         result.extend([u for u in target['devices'].keys() if u not in 
>result])
>         return result
> 
>-    # This includes a generic equivalent of pci_opts_list_to_sxp()
>-    def dev_dict_to_sxp(self, dev):
>-        def f((key, val)):
>-            if isinstance(val, types.ListType):
>-                return map(lambda x: [key, x], val)
>-            return [[key, val]]
>-        dev_sxp = ['dev'] + reduce(lambda x, y: x + y, map(f, dev.items()))
>-        return dev_sxp
>-
>     def all_devices_sxpr(self, target = None):
>         """Returns the SXPR for all devices in the current configuration."""
>         sxprs = []
>@@ -1993,7 +1912,7 @@ class XendConfig(dict):
>                     if dev_info.has_key('backend'):
>                         sxpr.append(['backend', dev_info['backend']])
>                 for pci_dev_info in dev_info['devs']:
>-                    sxpr.append(self.dev_dict_to_sxp(pci_dev_info))
>+                    sxpr.append(dev_dict_to_sxp(pci_dev_info))
>                 sxprs.append((dev_type, sxpr))
>             else:
>                 sxpr = self.device_sxpr(dev_type = dev_type,
>Index: xen-unstable.hg/tools/python/xen/xend/XendDomainInfo.py
>===================================================================
>--- xen-unstable.hg.orig/tools/python/xen/xend/XendDomainInfo.py	2009-06
-13
> 21:39:44.000000000 +1000
>+++ xen-unstable.hg/tools/python/xen/xend/XendDomainInfo.py	2009-06-13 21:
>40:34.000000000 +1000
>@@ -40,7 +40,9 @@ from xen.util.blkif import blkdev_uname_
> import xen.util.xsm.xsm as security
> from xen.util import xsconstants
> from xen.util.pci import serialise_pci_opts, pci_opts_list_to_sxp, \
>-                         pci_dict_to_bdf_str, pci_dict_to_xc_str, 
>pci_dict_cmp
>+                         pci_dict_to_bdf_str, pci_dict_to_xc_str, \
>+                         pci_convert_sxp_to_dict, pci_convert_dict_to_sxp, \
>+                         pci_dict_cmp
> 
> from xen.xend import balloon, sxp, uuid, image, arch
> from xen.xend import XendOptions, XendNode, XendConfig
>@@ -616,8 +618,8 @@ class XendDomainInfo:
>         pci_conf = self.info['devices'][dev_uuid][1]
>         pci_devs = pci_conf['devs']
>         request = map(lambda x:
>-                      self.info.pci_convert_dict_to_sxp(x, 'Initialising',
>-                                                        'Booting'), 
>pci_devs)
>+                      pci_convert_dict_to_sxp(x, 'Initialising', 'Booting'),
>+                      pci_devs)
> 
>         for i in request:
>                 self.pci_device_configure(i)
>@@ -815,7 +817,7 @@ class XendDomainInfo:
>             raise XendError("Cannot detach when pci platform does not 
>exist")
> 
>         pci_dev = sxp.children(dev_sxp, 'dev')[0]
>-        dev_config = self.info.pci_convert_sxp_to_dict(dev_sxp)
>+        dev_config = pci_convert_sxp_to_dict(dev_sxp)
>         dev = dev_config['devs'][0]
>                 
>         # Do HVM specific processing
>
>-- 
>
>_______________________________________________
>Xen-devel mailing list
>Xen-devel@lists.xensource.com
>http://lists.xensource.com/xen-devel

[-- Attachment #2: all_devices_sxpr.patch --]
[-- Type: application/octet-stream, Size: 2258 bytes --]

diff -r 4448fae52553 tools/python/xen/xend/XendConfig.py
--- a/tools/python/xen/xend/XendConfig.py	Mon Jun 08 12:24:14 2009 +0100
+++ b/tools/python/xen/xend/XendConfig.py	Mon Jun 15 14:18:38 2009 +0900
@@ -1979,25 +1979,28 @@
         ordered_refs = self.ordered_device_refs(target = target)
         for dev_uuid in ordered_refs:
             dev_type, dev_info = target['devices'][dev_uuid]
-            if dev_type == 'pci' or dev_type == 'vscsi': # special case for pci devices
-                if dev_type == 'pci':
-                    sxpr = ['pci', ['uuid', dev_info['uuid']]]
-                elif dev_type == 'vscsi':
-                    sxpr = ['vscsi', ['uuid', dev_info['uuid']],
-                                     ['feature-host', dev_info['feature-host']]]
-                    if dev_info.has_key('backend'):
-                        sxpr.append(['backend', dev_info['backend']])
+            if dev_type == 'pci': # special case for pci devices
+                sxpr = ['pci', ['uuid', dev_info['uuid']]]
                 for pci_dev_info in dev_info['devs']:
                     pci_dev_sxpr = ['dev']
                     for opt, val in pci_dev_info.items():
                         pci_dev_sxpr.append([opt, val])
                     sxpr.append(pci_dev_sxpr)
-                sxprs.append((dev_type, sxpr))
+            elif dev_type == 'vscsi': # special case for vscsi devices
+                sxpr = ['vscsi', ['uuid', dev_info['uuid']],
+                                 ['feature-host', dev_info['feature-host']]]
+                if dev_info.has_key('backend'):
+                    sxpr.append(['backend', dev_info['backend']])
+                for vscsi_dev_info in dev_info['devs']:
+                    vscsi_dev_sxpr = ['dev']
+                    for opt, val in vscsi_dev_info.items():
+                        vscsi_dev_sxpr.append([opt, val])
+                    sxpr.append(vscsi_dev_sxpr)
             else:
                 sxpr = self.device_sxpr(dev_type = dev_type,
                                         dev_info = dev_info,
                                         target   = target)
-                sxprs.append((dev_type, sxpr))
+            sxprs.append((dev_type, sxpr))
 
         return sxprs
 

[-- Attachment #3: Type: text/plain, Size: 138 bytes --]

_______________________________________________
Xen-devel mailing list
Xen-devel@lists.xensource.com
http://lists.xensource.com/xen-devel

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

* Re: [patch 11/16] xend: pass-through: Move pci conversionfunctions to pci.py
  2009-06-15  5:58   ` [patch 11/16] xend: pass-through: Move pci conversionfunctions " Masaki Kanno
@ 2009-06-15  6:15     ` Simon Horman
  2009-06-15  7:02       ` [patch 11/16] xend: pass-through: Move pciconversionfunctions " Masaki Kanno
  0 siblings, 1 reply; 28+ messages in thread
From: Simon Horman @ 2009-06-15  6:15 UTC (permalink / raw)
  To: Masaki Kanno; +Cc: xen-devel, Dexuan Cui

On Mon, Jun 15, 2009 at 02:58:14PM +0900, Masaki Kanno wrote:
Content-Description: Mail message body
> Hi Simon,
> 
> dev_dict_to_sxp method in XendConfig.py is called for both pci 
> devices and vscsi devices.  So, I think that the method should 
> be not moved to pci.py. 
> 
> I suggest separating the processing of pci devices and the 
> processing of vscsi devices in all_devices_sxpr method. 
> I attach a patch for separating them. 

That seems reasonable.

I haven't had time to work through the vscsi, nor am I likely to in the
near future. But does the logic in dev_dict_to_sxp() make sense for vscsi?
If so, would you be happy it we moved it somewhere else, perhaps
into sxp.py? Or create XendSXPDev.py?

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

* Re: [patch 11/16] xend: pass-through: Move pciconversionfunctions to pci.py
  2009-06-15  6:15     ` Simon Horman
@ 2009-06-15  7:02       ` Masaki Kanno
  2009-06-15  9:04         ` Simon Horman
  0 siblings, 1 reply; 28+ messages in thread
From: Masaki Kanno @ 2009-06-15  7:02 UTC (permalink / raw)
  To: Simon Horman; +Cc: xen-devel, Dexuan Cui

Hi Simon,

Mon, 15 Jun 2009 16:15:59 +1000, Simon Horman wrote:

>On Mon, Jun 15, 2009 at 02:58:14PM +0900, Masaki Kanno wrote:
>Content-Description: Mail message body
>> Hi Simon,
>> 
>> dev_dict_to_sxp method in XendConfig.py is called for both pci 
>> devices and vscsi devices.  So, I think that the method should 
>> be not moved to pci.py. 
>> 
>> I suggest separating the processing of pci devices and the 
>> processing of vscsi devices in all_devices_sxpr method. 
>> I attach a patch for separating them. 
>
>That seems reasonable.
>
>I haven't had time to work through the vscsi, nor am I likely to in the
>near future. But does the logic in dev_dict_to_sxp() make sense for vscsi?

Yes. I confirmed that dev_dict_to_sxp method is working for vscsi.


>If so, would you be happy it we moved it somewhere else, perhaps
>into sxp.py? Or create XendSXPDev.py?

XendSXPDev.py ...

Best regards,
 Kan

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

* Re: [patch 11/16] xend: pass-through: Move pciconversionfunctions to pci.py
  2009-06-15  7:02       ` [patch 11/16] xend: pass-through: Move pciconversionfunctions " Masaki Kanno
@ 2009-06-15  9:04         ` Simon Horman
  2009-06-15 11:58           ` [patch v2] xend: pass-through: Move pci conversion functions " Simon Horman
  0 siblings, 1 reply; 28+ messages in thread
From: Simon Horman @ 2009-06-15  9:04 UTC (permalink / raw)
  To: Masaki Kanno; +Cc: xen-devel, Dexuan Cui

On Mon, Jun 15, 2009 at 04:02:06PM +0900, Masaki Kanno wrote:
> Hi Simon,
> 
> Mon, 15 Jun 2009 16:15:59 +1000, Simon Horman wrote:
> 
> >On Mon, Jun 15, 2009 at 02:58:14PM +0900, Masaki Kanno wrote:
> >Content-Description: Mail message body
> >> Hi Simon,
> >> 
> >> dev_dict_to_sxp method in XendConfig.py is called for both pci 
> >> devices and vscsi devices.  So, I think that the method should 
> >> be not moved to pci.py. 
> >> 
> >> I suggest separating the processing of pci devices and the 
> >> processing of vscsi devices in all_devices_sxpr method. 
> >> I attach a patch for separating them. 
> >
> >That seems reasonable.
> >
> >I haven't had time to work through the vscsi, nor am I likely to in the
> >near future. But does the logic in dev_dict_to_sxp() make sense for vscsi?
> 
> Yes. I confirmed that dev_dict_to_sxp method is working for vscsi.
> 
> 
> >If so, would you be happy it we moved it somewhere else, perhaps
> >into sxp.py? Or create XendSXPDev.py?
> 
> XendSXPDev.py ...

Ok, will do.

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

* [patch v2] xend: pass-through: Move pci conversion functions to pci.py
  2009-06-15  9:04         ` Simon Horman
@ 2009-06-15 11:58           ` Simon Horman
  2009-06-15 23:36             ` [patch 11/16 v3] " Simon Horman
  0 siblings, 1 reply; 28+ messages in thread
From: Simon Horman @ 2009-06-15 11:58 UTC (permalink / raw)
  To: Masaki Kanno; +Cc: xen-devel, Dexuan Cui

Move dev_dict_to_sxp() into XendSXPDev.py.  Move pci_convert_dict_to_sxp()
and pci_convert_sxp_to_dict() to pci.py, where other similar functions
live.  This makes these functions accessible outside of the XendConfig
class.

Cc: Dexuan Cui <dexuan.cui@intel.com>
Cc: Masaki Kanno <kanno.masaki@jp.fujitsu.com>
Signed-off-by: Simon Horman <horms@verge.net.au>

--- 

Mon, 15 Jun 2009 11:55:26 +1000
* Initial posting

Mon, 15 Jun 2009 20:39:43 +1000
* Move dev_dict_to_sxp into XendSXPDev.py as it is used by
  non-pci as well as pci devices

Index: xen-unstable.hg/tools/python/xen/util/pci.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/util/pci.py	2009-06-13 21:39:44.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/util/pci.py	2009-06-13 21:39:56.000000000 +1000
@@ -14,6 +14,7 @@ import struct
 import time
 import threading
 from xen.util import utils
+from xen.xend import uuid
 from xen.xend import sxp
 from xen.xend.XendConstants import AUTO_PHP_SLOT
 
@@ -139,6 +140,88 @@ def pci_opts_list_to_sxp(list):
 def pci_opts_list_from_sxp(dev):
     return map(lambda x: sxp.children(x)[0], sxp.children(dev, 'opts'))
 
+# This includes a generic equivalent of pci_opts_list_to_sxp()
+def dev_dict_to_sxp(dev):
+    def f((key, val)):
+        if isinstance(val, types.ListType):
+            return map(lambda x: [key, x], val)
+        return [[key, val]]
+    dev_sxp = ['dev'] + reduce(lambda x, y: x + y, map(f, dev.items()))
+    return dev_sxp
+
+def pci_convert_dict_to_sxp(dev, state, sub_state = None):
+    pci_sxp = ['pci', dev_dict_to_sxp(dev), ['state', state]]
+    if sub_state != None:
+        pci_sxp.append(['sub_state', sub_state])
+    return pci_sxp
+
+def pci_convert_sxp_to_dict(dev_sxp):
+    """Convert pci device sxp to dict
+    @param dev_sxp: device configuration
+    @type  dev_sxp: SXP object (parsed config)
+    @return: dev_config
+    @rtype: dictionary
+    """
+    # Parsing the device SXP's. In most cases, the SXP looks
+    # like this:
+    #
+    # [device, [vif, [mac, xx:xx:xx:xx:xx:xx], [ip 1.3.4.5]]]
+    #
+    # However, for PCI devices it looks like this:
+    #
+    # [device, [pci, [dev, [domain, 0], [bus, 0], [slot, 1], [func, 2]]]
+    #
+    # It seems the reasoning for this difference is because
+    # pciif.py needs all the PCI device configurations at
+    # the same time when creating the devices.
+    #
+    # To further complicate matters, Xen 2.0 configuration format
+    # uses the following for pci device configuration:
+    #
+    # [device, [pci, [domain, 0], [bus, 0], [dev, 1], [func, 2]]]
+
+    # For PCI device hotplug support, the SXP of PCI devices is
+    # extendend like this:
+    #
+    # [device, [pci, [dev, [domain, 0], [bus, 0], [slot, 1], [func, 2],
+    #                      [vslot, 0]],
+    #                [state, 'Initialising']]]
+    #
+    # 'vslot' shows the virtual hotplug slot number which the PCI device
+    # is inserted in. This is only effective for HVM domains.
+    #
+    # state 'Initialising' indicates that the device is being attached,
+    # while state 'Closing' indicates that the device is being detached.
+    #
+    # The Dict looks like this:
+    #
+    # { devs: [{domain: 0, bus: 0, slot: 1, func: 2, vslot: 0}],
+    #   states: ['Initialising'] }
+
+    dev_config = {}
+
+    pci_devs = []
+    for pci_dev in sxp.children(dev_sxp, 'dev'):
+        pci_dev_info = dict(pci_dev[1:])
+        if 'opts' in pci_dev_info:
+            pci_dev_info['opts'] = pci_opts_list_from_sxp(pci_dev)
+        # append uuid to each pci device that does't already have one.
+        if not pci_dev_info.has_key('uuid'):
+            dpci_uuid = pci_dev_info.get('uuid', uuid.createString())
+            pci_dev_info['uuid'] = dpci_uuid
+        pci_devs.append(pci_dev_info)
+    dev_config['devs'] = pci_devs
+
+    pci_states = []
+    for pci_state in sxp.children(dev_sxp, 'state'):
+        try:
+            pci_states.append(pci_state[1])
+        except IndexError:
+            raise XendError("Error reading state while parsing pci sxp")
+    dev_config['states'] = pci_states
+
+    return dev_config
+
 def parse_hex(val):
     try:
         if isinstance(val, types.StringTypes):
Index: xen-unstable.hg/tools/python/xen/xend/XendConfig.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xend/XendConfig.py	2009-06-13 21:39:44.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xend/XendConfig.py	2009-06-13 21:39:56.000000000 +1000
@@ -36,7 +36,8 @@ from xen.xend.xenstore.xstransact import
 from xen.xend.server.BlktapController import blktap_disk_types
 from xen.xend.server.netif import randomMAC
 from xen.util.blkif import blkdev_name_to_number, blkdev_uname_to_file
-from xen.util.pci import pci_opts_list_from_sxp
+from xen.util.pci import pci_opts_list_from_sxp, dev_dict_to_sxp, \
+                         pci_convert_sxp_to_dict
 from xen.util import xsconstants
 import xen.util.auxbin
 
@@ -1296,7 +1297,7 @@ class XendConfig(dict):
                 pci_devs_uuid = sxp.child_value(config, 'uuid',
                                                 uuid.createString())
 
-                pci_dict = self.pci_convert_sxp_to_dict(config)
+                pci_dict = pci_convert_sxp_to_dict(config)
                 pci_devs = pci_dict['devs']
 
                 # create XenAPI DPCI objects.
@@ -1596,79 +1597,6 @@ class XendConfig(dict):
 
         return ''
 
-    def pci_convert_dict_to_sxp(self, dev, state, sub_state = None):
-        pci_sxp = ['pci', self.dev_dict_to_sxp(dev), ['state', state]]
-        if sub_state != None:
-            pci_sxp.append(['sub_state', sub_state])
-        return pci_sxp
-
-    def pci_convert_sxp_to_dict(self, dev_sxp):
-        """Convert pci device sxp to dict
-        @param dev_sxp: device configuration
-        @type  dev_sxp: SXP object (parsed config)
-        @return: dev_config
-        @rtype: dictionary
-        """
-        # Parsing the device SXP's. In most cases, the SXP looks
-        # like this:
-        #
-        # [device, [vif, [mac, xx:xx:xx:xx:xx:xx], [ip 1.3.4.5]]]
-        #
-        # However, for PCI devices it looks like this:
-        #
-        # [device, [pci, [dev, [domain, 0], [bus, 0], [slot, 1], [func, 2]]]
-        #
-        # It seems the reasoning for this difference is because
-        # pciif.py needs all the PCI device configurations at
-        # the same time when creating the devices.
-        #
-        # To further complicate matters, Xen 2.0 configuration format
-        # uses the following for pci device configuration:
-        #
-        # [device, [pci, [domain, 0], [bus, 0], [dev, 1], [func, 2]]]
-
-        # For PCI device hotplug support, the SXP of PCI devices is
-        # extendend like this:
-        #
-        # [device, [pci, [dev, [domain, 0], [bus, 0], [slot, 1], [func, 2],
-        #                      [vslot, 0]],
-        #                [state, 'Initialising']]]
-        #
-        # 'vslot' shows the virtual hotplug slot number which the PCI device
-        # is inserted in. This is only effective for HVM domains.
-        #
-        # state 'Initialising' indicates that the device is being attached,
-        # while state 'Closing' indicates that the device is being detached.
-        #
-        # The Dict looks like this:
-        #
-        # { devs: [{domain: 0, bus: 0, slot: 1, func: 2, vslot: 0}],
-        #   states: ['Initialising'] }
-
-        dev_config = {}
-
-        pci_devs = []
-        for pci_dev in sxp.children(dev_sxp, 'dev'):
-            pci_dev_info = dict(pci_dev[1:])
-            if 'opts' in pci_dev_info:
-                pci_dev_info['opts'] = pci_opts_list_from_sxp(pci_dev)
-            # append uuid to each pci device that does't already have one.
-            if not pci_dev_info.has_key('uuid'):
-                dpci_uuid = pci_dev_info.get('uuid', uuid.createString())
-                pci_dev_info['uuid'] = dpci_uuid
-            pci_devs.append(pci_dev_info)
-        dev_config['devs'] = pci_devs 
-
-        pci_states = []
-        for pci_state in sxp.children(dev_sxp, 'state'):
-            try:
-                pci_states.append(pci_state[1])
-            except IndexError:
-                raise XendError("Error reading state while parsing pci sxp")
-        dev_config['states'] = pci_states
-
-        return dev_config
-
     def vscsi_convert_sxp_to_dict(self, dev_sxp):
         """Convert vscsi device sxp to dict
         @param dev_sxp: device configuration
@@ -1839,7 +1767,7 @@ class XendConfig(dict):
             dev_type, dev_info = self['devices'][dev_uuid]
 
             if dev_type == 'pci': # Special case for pci
-                pci_dict = self.pci_convert_sxp_to_dict(config)
+                pci_dict = pci_convert_sxp_to_dict(config)
                 pci_devs = pci_dict['devs']
 
                 # destroy existing XenAPI DPCI objects
@@ -1962,15 +1890,6 @@ class XendConfig(dict):
         result.extend([u for u in target['devices'].keys() if u not in result])
         return result
 
-    # This includes a generic equivalent of pci_opts_list_to_sxp()
-    def dev_dict_to_sxp(self, dev):
-        def f((key, val)):
-            if isinstance(val, types.ListType):
-                return map(lambda x: [key, x], val)
-            return [[key, val]]
-        dev_sxp = ['dev'] + reduce(lambda x, y: x + y, map(f, dev.items()))
-        return dev_sxp
-
     def all_devices_sxpr(self, target = None):
         """Returns the SXPR for all devices in the current configuration."""
         sxprs = []
@@ -1993,7 +1912,7 @@ class XendConfig(dict):
                     if dev_info.has_key('backend'):
                         sxpr.append(['backend', dev_info['backend']])
                 for pci_dev_info in dev_info['devs']:
-                    sxpr.append(self.dev_dict_to_sxp(pci_dev_info))
+                    sxpr.append(dev_dict_to_sxp(pci_dev_info))
                 sxprs.append((dev_type, sxpr))
             else:
                 sxpr = self.device_sxpr(dev_type = dev_type,
Index: xen-unstable.hg/tools/python/xen/xend/XendDomainInfo.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xend/XendDomainInfo.py	2009-06-13 21:39:44.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xend/XendDomainInfo.py	2009-06-13 21:40:34.000000000 +1000
@@ -40,7 +40,9 @@ from xen.util.blkif import blkdev_uname_
 import xen.util.xsm.xsm as security
 from xen.util import xsconstants
 from xen.util.pci import serialise_pci_opts, pci_opts_list_to_sxp, \
-                         pci_dict_to_bdf_str, pci_dict_to_xc_str, pci_dict_cmp
+                         pci_dict_to_bdf_str, pci_dict_to_xc_str, \
+                         pci_convert_sxp_to_dict, pci_convert_dict_to_sxp, \
+                         pci_dict_cmp
 
 from xen.xend import balloon, sxp, uuid, image, arch
 from xen.xend import XendOptions, XendNode, XendConfig
@@ -616,8 +618,8 @@ class XendDomainInfo:
         pci_conf = self.info['devices'][dev_uuid][1]
         pci_devs = pci_conf['devs']
         request = map(lambda x:
-                      self.info.pci_convert_dict_to_sxp(x, 'Initialising',
-                                                        'Booting'), pci_devs)
+                      pci_convert_dict_to_sxp(x, 'Initialising', 'Booting'),
+                      pci_devs)
 
         for i in request:
                 self.pci_device_configure(i)
@@ -815,7 +817,7 @@ class XendDomainInfo:
             raise XendError("Cannot detach when pci platform does not exist")
 
         pci_dev = sxp.children(dev_sxp, 'dev')[0]
-        dev_config = self.info.pci_convert_sxp_to_dict(dev_sxp)
+        dev_config = pci_convert_sxp_to_dict(dev_sxp)
         dev = dev_config['devs'][0]
                 
         # Do HVM specific processing

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

* [patch v2] xend: pass-through: Use generic code in pci_opts_list_to_sxp()
  2009-06-15  1:55 ` [patch 12/16] xend: pass-through: Use generic code in pci_opts_list_to_sxp() Simon Horman
@ 2009-06-15 11:59   ` Simon Horman
  0 siblings, 0 replies; 28+ messages in thread
From: Simon Horman @ 2009-06-15 11:59 UTC (permalink / raw)
  To: xen-devel; +Cc: Masaki Kanno, Dexuan Cui

Use dev_dict_to_sxp() inside pci_opts_list_to_sxp() now that it is
available.

Cc: Dexuan Cui <dexuan.cui@intel.com>
Cc: Masaki Kanno <kanno.masaki@jp.fujitsu.com>
Signed-off-by: Simon Horman <horms@verge.net.au>

--- 

Mon, 15 Jun 2009 11:55:27 +1000
* Initial posting

Mon, 15 Jun 2009 20:38:21 +1000
* dev_dict_to_sxp() is now in XendSXPDev.py

Index: xen-unstable.hg/tools/python/xen/util/pci.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/util/pci.py	2009-06-15 20:13:52.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/util/pci.py	2009-06-15 20:35:32.000000000 +1000
@@ -136,7 +136,7 @@ def split_pci_opts(opts):
                filter(lambda x: x != '', opts.split(',')))
 
 def pci_opts_list_to_sxp(list):
-    return ['dev'] + map(lambda x: ['opts', x], list)
+    return dev_dict_to_sxp({'opts': list})
 
 def pci_opts_list_from_sxp(dev):
     return map(lambda x: sxp.children(x)[0], sxp.children(dev, 'opts'))
Index: xen-unstable.hg/tools/python/xen/xend/XendSXPDev.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xend/XendSXPDev.py	2009-06-15 20:35:56.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xend/XendSXPDev.py	2009-06-15 20:36:06.000000000 +1000
@@ -4,7 +4,6 @@
 
 import types
 
-# This includes a generic equivalent of pci_opts_list_to_sxp()
 def dev_dict_to_sxp(dev):
     def f((key, val)):
         if isinstance(val, types.ListType):

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

* [patch 11/16 v3] xend: pass-through: Move pci conversion functions to pci.py
  2009-06-15 11:58           ` [patch v2] xend: pass-through: Move pci conversion functions " Simon Horman
@ 2009-06-15 23:36             ` Simon Horman
  0 siblings, 0 replies; 28+ messages in thread
From: Simon Horman @ 2009-06-15 23:36 UTC (permalink / raw)
  To: Masaki Kanno; +Cc: xen-devel, Dexuan Cui

Move dev_dict_to_sxp() into XendSXPDev.py.  Move pci_convert_dict_to_sxp()
and pci_convert_sxp_to_dict() to pci.py, where other similar functions
live.  This makes these functions accessible outside of the XendConfig
class.

Cc: Dexuan Cui <dexuan.cui@intel.com>
Cc: Masaki Kanno <kanno.masaki@jp.fujitsu.com>
Signed-off-by: Simon Horman <horms@verge.net.au>

--- 

Mon, 15 Jun 2009 11:55:26 +1000
* Initial posting

Mon, 15 Jun 2009 20:39:43 +1000
* Miss-post - XendSXPDev.py change was omitted

Tue, 16 Jun 2009 09:33:17 +1000
* Move dev_dict_to_sxp into XendSXPDev.py.
  As pointed out by Masaki Kanno, it is used by non-pci as well as pci devices.

Index: xen-unstable.hg/tools/python/xen/util/pci.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/util/pci.py	2009-06-15 19:37:07.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/util/pci.py	2009-06-16 09:31:18.000000000 +1000
@@ -14,8 +14,10 @@ import struct
 import time
 import threading
 from xen.util import utils
+from xen.xend import uuid
 from xen.xend import sxp
 from xen.xend.XendConstants import AUTO_PHP_SLOT
+from xen.xend.XendSXPDev import dev_dict_to_sxp
 
 PROC_PCI_PATH = '/proc/bus/pci/devices'
 PROC_PCI_NUM_RESOURCES = 7
@@ -139,6 +141,79 @@ def pci_opts_list_to_sxp(list):
 def pci_opts_list_from_sxp(dev):
     return map(lambda x: sxp.children(x)[0], sxp.children(dev, 'opts'))
 
+def pci_convert_dict_to_sxp(dev, state, sub_state = None):
+    pci_sxp = ['pci', dev_dict_to_sxp(dev), ['state', state]]
+    if sub_state != None:
+        pci_sxp.append(['sub_state', sub_state])
+    return pci_sxp
+
+def pci_convert_sxp_to_dict(dev_sxp):
+    """Convert pci device sxp to dict
+    @param dev_sxp: device configuration
+    @type  dev_sxp: SXP object (parsed config)
+    @return: dev_config
+    @rtype: dictionary
+    """
+    # Parsing the device SXP's. In most cases, the SXP looks
+    # like this:
+    #
+    # [device, [vif, [mac, xx:xx:xx:xx:xx:xx], [ip 1.3.4.5]]]
+    #
+    # However, for PCI devices it looks like this:
+    #
+    # [device, [pci, [dev, [domain, 0], [bus, 0], [slot, 1], [func, 2]]]
+    #
+    # It seems the reasoning for this difference is because
+    # pciif.py needs all the PCI device configurations at
+    # the same time when creating the devices.
+    #
+    # To further complicate matters, Xen 2.0 configuration format
+    # uses the following for pci device configuration:
+    #
+    # [device, [pci, [domain, 0], [bus, 0], [dev, 1], [func, 2]]]
+
+    # For PCI device hotplug support, the SXP of PCI devices is
+    # extendend like this:
+    #
+    # [device, [pci, [dev, [domain, 0], [bus, 0], [slot, 1], [func, 2],
+    #                      [vslot, 0]],
+    #                [state, 'Initialising']]]
+    #
+    # 'vslot' shows the virtual hotplug slot number which the PCI device
+    # is inserted in. This is only effective for HVM domains.
+    #
+    # state 'Initialising' indicates that the device is being attached,
+    # while state 'Closing' indicates that the device is being detached.
+    #
+    # The Dict looks like this:
+    #
+    # { devs: [{domain: 0, bus: 0, slot: 1, func: 2, vslot: 0}],
+    #   states: ['Initialising'] }
+
+    dev_config = {}
+
+    pci_devs = []
+    for pci_dev in sxp.children(dev_sxp, 'dev'):
+        pci_dev_info = dict(pci_dev[1:])
+        if 'opts' in pci_dev_info:
+            pci_dev_info['opts'] = pci_opts_list_from_sxp(pci_dev)
+        # append uuid to each pci device that does't already have one.
+        if not pci_dev_info.has_key('uuid'):
+            dpci_uuid = pci_dev_info.get('uuid', uuid.createString())
+            pci_dev_info['uuid'] = dpci_uuid
+        pci_devs.append(pci_dev_info)
+    dev_config['devs'] = pci_devs
+
+    pci_states = []
+    for pci_state in sxp.children(dev_sxp, 'state'):
+        try:
+            pci_states.append(pci_state[1])
+        except IndexError:
+            raise XendError("Error reading state while parsing pci sxp")
+    dev_config['states'] = pci_states
+
+    return dev_config
+
 def parse_hex(val):
     try:
         if isinstance(val, types.StringTypes):
Index: xen-unstable.hg/tools/python/xen/xend/XendConfig.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xend/XendConfig.py	2009-06-15 19:36:53.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xend/XendConfig.py	2009-06-16 09:31:17.000000000 +1000
@@ -36,7 +36,8 @@ from xen.xend.xenstore.xstransact import
 from xen.xend.server.BlktapController import blktap_disk_types
 from xen.xend.server.netif import randomMAC
 from xen.util.blkif import blkdev_name_to_number, blkdev_uname_to_file
-from xen.util.pci import pci_opts_list_from_sxp
+from xen.util.pci import pci_opts_list_from_sxp, pci_convert_sxp_to_dict
+from xen.xend.XendSXPDev import dev_dict_to_sxp
 from xen.util import xsconstants
 import xen.util.auxbin
 
@@ -1296,7 +1297,7 @@ class XendConfig(dict):
                 pci_devs_uuid = sxp.child_value(config, 'uuid',
                                                 uuid.createString())
 
-                pci_dict = self.pci_convert_sxp_to_dict(config)
+                pci_dict = pci_convert_sxp_to_dict(config)
                 pci_devs = pci_dict['devs']
 
                 # create XenAPI DPCI objects.
@@ -1596,79 +1597,6 @@ class XendConfig(dict):
 
         return ''
 
-    def pci_convert_dict_to_sxp(self, dev, state, sub_state = None):
-        pci_sxp = ['pci', self.dev_dict_to_sxp(dev), ['state', state]]
-        if sub_state != None:
-            pci_sxp.append(['sub_state', sub_state])
-        return pci_sxp
-
-    def pci_convert_sxp_to_dict(self, dev_sxp):
-        """Convert pci device sxp to dict
-        @param dev_sxp: device configuration
-        @type  dev_sxp: SXP object (parsed config)
-        @return: dev_config
-        @rtype: dictionary
-        """
-        # Parsing the device SXP's. In most cases, the SXP looks
-        # like this:
-        #
-        # [device, [vif, [mac, xx:xx:xx:xx:xx:xx], [ip 1.3.4.5]]]
-        #
-        # However, for PCI devices it looks like this:
-        #
-        # [device, [pci, [dev, [domain, 0], [bus, 0], [slot, 1], [func, 2]]]
-        #
-        # It seems the reasoning for this difference is because
-        # pciif.py needs all the PCI device configurations at
-        # the same time when creating the devices.
-        #
-        # To further complicate matters, Xen 2.0 configuration format
-        # uses the following for pci device configuration:
-        #
-        # [device, [pci, [domain, 0], [bus, 0], [dev, 1], [func, 2]]]
-
-        # For PCI device hotplug support, the SXP of PCI devices is
-        # extendend like this:
-        #
-        # [device, [pci, [dev, [domain, 0], [bus, 0], [slot, 1], [func, 2],
-        #                      [vslot, 0]],
-        #                [state, 'Initialising']]]
-        #
-        # 'vslot' shows the virtual hotplug slot number which the PCI device
-        # is inserted in. This is only effective for HVM domains.
-        #
-        # state 'Initialising' indicates that the device is being attached,
-        # while state 'Closing' indicates that the device is being detached.
-        #
-        # The Dict looks like this:
-        #
-        # { devs: [{domain: 0, bus: 0, slot: 1, func: 2, vslot: 0}],
-        #   states: ['Initialising'] }
-
-        dev_config = {}
-
-        pci_devs = []
-        for pci_dev in sxp.children(dev_sxp, 'dev'):
-            pci_dev_info = dict(pci_dev[1:])
-            if 'opts' in pci_dev_info:
-                pci_dev_info['opts'] = pci_opts_list_from_sxp(pci_dev)
-            # append uuid to each pci device that does't already have one.
-            if not pci_dev_info.has_key('uuid'):
-                dpci_uuid = pci_dev_info.get('uuid', uuid.createString())
-                pci_dev_info['uuid'] = dpci_uuid
-            pci_devs.append(pci_dev_info)
-        dev_config['devs'] = pci_devs 
-
-        pci_states = []
-        for pci_state in sxp.children(dev_sxp, 'state'):
-            try:
-                pci_states.append(pci_state[1])
-            except IndexError:
-                raise XendError("Error reading state while parsing pci sxp")
-        dev_config['states'] = pci_states
-
-        return dev_config
-
     def vscsi_convert_sxp_to_dict(self, dev_sxp):
         """Convert vscsi device sxp to dict
         @param dev_sxp: device configuration
@@ -1839,7 +1767,7 @@ class XendConfig(dict):
             dev_type, dev_info = self['devices'][dev_uuid]
 
             if dev_type == 'pci': # Special case for pci
-                pci_dict = self.pci_convert_sxp_to_dict(config)
+                pci_dict = pci_convert_sxp_to_dict(config)
                 pci_devs = pci_dict['devs']
 
                 # destroy existing XenAPI DPCI objects
@@ -1962,15 +1890,6 @@ class XendConfig(dict):
         result.extend([u for u in target['devices'].keys() if u not in result])
         return result
 
-    # This includes a generic equivalent of pci_opts_list_to_sxp()
-    def dev_dict_to_sxp(self, dev):
-        def f((key, val)):
-            if isinstance(val, types.ListType):
-                return map(lambda x: [key, x], val)
-            return [[key, val]]
-        dev_sxp = ['dev'] + reduce(lambda x, y: x + y, map(f, dev.items()))
-        return dev_sxp
-
     def all_devices_sxpr(self, target = None):
         """Returns the SXPR for all devices in the current configuration."""
         sxprs = []
@@ -1993,7 +1912,7 @@ class XendConfig(dict):
                     if dev_info.has_key('backend'):
                         sxpr.append(['backend', dev_info['backend']])
                 for pci_dev_info in dev_info['devs']:
-                    sxpr.append(self.dev_dict_to_sxp(pci_dev_info))
+                    sxpr.append(dev_dict_to_sxp(pci_dev_info))
                 sxprs.append((dev_type, sxpr))
             else:
                 sxpr = self.device_sxpr(dev_type = dev_type,
Index: xen-unstable.hg/tools/python/xen/xend/XendDomainInfo.py
===================================================================
--- xen-unstable.hg.orig/tools/python/xen/xend/XendDomainInfo.py	2009-06-15 19:37:07.000000000 +1000
+++ xen-unstable.hg/tools/python/xen/xend/XendDomainInfo.py	2009-06-16 09:31:18.000000000 +1000
@@ -40,7 +40,9 @@ from xen.util.blkif import blkdev_uname_
 import xen.util.xsm.xsm as security
 from xen.util import xsconstants
 from xen.util.pci import serialise_pci_opts, pci_opts_list_to_sxp, \
-                         pci_dict_to_bdf_str, pci_dict_to_xc_str, pci_dict_cmp
+                         pci_dict_to_bdf_str, pci_dict_to_xc_str, \
+                         pci_convert_sxp_to_dict, pci_convert_dict_to_sxp, \
+                         pci_dict_cmp
 
 from xen.xend import balloon, sxp, uuid, image, arch
 from xen.xend import XendOptions, XendNode, XendConfig
@@ -616,8 +618,8 @@ class XendDomainInfo:
         pci_conf = self.info['devices'][dev_uuid][1]
         pci_devs = pci_conf['devs']
         request = map(lambda x:
-                      self.info.pci_convert_dict_to_sxp(x, 'Initialising',
-                                                        'Booting'), pci_devs)
+                      pci_convert_dict_to_sxp(x, 'Initialising', 'Booting'),
+                      pci_devs)
 
         for i in request:
                 self.pci_device_configure(i)
@@ -815,7 +817,7 @@ class XendDomainInfo:
             raise XendError("Cannot detach when pci platform does not exist")
 
         pci_dev = sxp.children(dev_sxp, 'dev')[0]
-        dev_config = self.info.pci_convert_sxp_to_dict(dev_sxp)
+        dev_config = pci_convert_sxp_to_dict(dev_sxp)
         dev = dev_config['devs'][0]
                 
         # Do HVM specific processing
Index: xen-unstable.hg/tools/python/xen/xend/XendSXPDev.py
===================================================================
--- /dev/null	1970-01-01 00:00:00.000000000 +0000
+++ xen-unstable.hg/tools/python/xen/xend/XendSXPDev.py	2009-06-16 09:31:18.000000000 +1000
@@ -0,0 +1,14 @@
+#!/usr/bin/env python
+#
+# Helper functions for dealing with the sxp representation of devices
+
+import types
+
+# This includes a generic equivalent of pci_opts_list_to_sxp()
+def dev_dict_to_sxp(dev):
+    def f((key, val)):
+        if isinstance(val, types.ListType):
+            return map(lambda x: [key, x], val)
+        return [[key, val]]
+    dev_sxp = ['dev'] + reduce(lambda x, y: x + y, map(f, dev.items()))
+    return dev_sxp

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

* Re: [patch 08/16] xend: pass-through: Common parse_pci_name()
  2009-06-15  1:55 ` [patch 08/16] xend: pass-through: Common parse_pci_name() Simon Horman
@ 2009-06-16 10:43   ` Keir Fraser
  2009-06-16 11:20     ` Simon Horman
  0 siblings, 1 reply; 28+ messages in thread
From: Keir Fraser @ 2009-06-16 10:43 UTC (permalink / raw)
  To: Simon Horman, xen-devel; +Cc: Masaki Kanno, Dexuan Cui

This patch didn't apply. I applied patches 1-7 and also patch 9 of your
series, but beyond that it was a bit of a trainwreck. Please refresh patch 8
and patches 10+ and resend.

 Thanks,
 Keir

On 15/06/2009 02:55, "Simon Horman" <horms@verge.net.au> wrote:

> Share some parsing code between different parts of xm.
> 
> This has the side-effect that the device specification for
> hot-plug may now include the VSLOT and OPTS as per device
> specifictions in the domain configuration file.
> 
>   SEQ:BUS:DEV.FUNC[,OPT...]
> 
>   e.g. 0000:00:01.00@6
> 
> Cc: Dexuan Cui <dexuan.cui@intel.com>
> Cc: Masaki Kanno <kanno.masaki@jp.fujitsu.com>
> Signed-off-by: Simon Horman <horms@verge.net.au>
> 
> ---
> 
> Wed, 20 May 2009 23:07:42 +1000
> * Fix syntax errors in parse_pci_name() and parse_pci_name_bdf6()
>   - unnoticed as they were resolved by the subsequent patch
>     "xm: Allow multi-function device specifications to be parsed
> * Enhanced error reporting in parse_pci_name()
> * Have parse_pci_name_bdf6() return an int rather than a string for vslot in
>   keeping with the other integer elements of the bdf6 tuple
> 
> Fri, 22 May 2009 15:52:50 +1000
> * Consolidate get_all_pci_bdf6() and get_all_pci_devices()
> 
> Thu, 28 May 2009 23:56:14 +1000
> * Up-port
> 
> Index: xen-unstable.hg/tools/python/xen/util/pci.py
> ===================================================================
> --- xen-unstable.hg.orig/tools/python/xen/util/pci.py   2009-06-15
> 11:22:35.000000000 +1000
> +++ xen-unstable.hg/tools/python/xen/util/pci.py        2009-06-15
> 11:23:43.000000000 +1000
> @@ -15,6 +15,7 @@ import time
>  import threading
>  from xen.util import utils
>  from xen.xend import sxp
> +from xen.xend.XendConstants import AUTO_PHP_SLOT
> 
>  PROC_PCI_PATH = '/proc/bus/pci/devices'
>  PROC_PCI_NUM_RESOURCES = 7
> @@ -35,7 +36,6 @@ LSPCI_CMD = 'lspci'
> 
>  PCI_DEV_REG_EXPRESS_STR = r"[0-9a-fA-F]{4}:[0-9a-fA-F]{2}:[0-9a-fA-F]{2}."+ \
>              r"[0-9a-fA-F]{1}"
> -PCI_DEV_FORMAT_STR = '%04x:%02x:%02x.%01x'
> 
>  DEV_TYPE_PCIe_ENDPOINT  = 0
>  DEV_TYPE_PCIe_BRIDGE    = 1
> @@ -148,22 +148,62 @@ def parse_hex(val):
>      except ValueError:
>          return None
> 
> +def parse_pci_name_extended(pci_dev_str):
> +    pci_match = re.match(r"((?P<domain>[0-9a-fA-F]{1,4})[:,])?" +
> +                         r"(?P<bus>[0-9a-fA-F]{1,2})[:,]" +
> +                         r"(?P<slot>[0-9a-fA-F]{1,2})[.,]" +
> +                         r"(?P<func>(\*|[0-7]))" +
> +                         r"(@(?P<vslot>[01]?[0-9a-fA-F]))?" +
> +                         r"(,(?P<opts>.*))?$", pci_dev_str)
> +
> +    if pci_match == None:
> +        raise PciDeviceParseError("Failed to parse pci device: %s" %
> +                                  pci_dev_str)
> +
> +    out = {}
> +    pci_dev_info = pci_match.groupdict('')
> +    if pci_dev_info['domain'] == '':
> +        domain = 0
> +    else:
> +        domain = int(pci_dev_info['domain'], 16)
> +    out['domain'] = "0x%04x" % domain
> +    out['bus']    = "0x%02x" % int(pci_dev_info['bus'], 16)
> +    out['slot']   = "0x%02x" % int(pci_dev_info['slot'], 16)
> +    out['func']   = "0x%x"   % int(pci_dev_info['func'], 16)
> +    if pci_dev_info['vslot'] == '':
> +        vslot = AUTO_PHP_SLOT
> +    else:
> +        vslot = int(pci_dev_info['vslot'], 16)
> +    out['vslot'] = "0x%02x" % vslot
> +    if pci_dev_info['opts'] != '':
> +        out['opts'] = split_pci_opts(pci_dev_info['opts'])
> +        check_pci_opts(out['opts'])
> +
> +    return out
> +
>  def parse_pci_name(pci_name_string):
> -    pci_match = re.match(r"((?P<domain>[0-9a-fA-F]{1,4})[:,])?" + \
> -            r"(?P<bus>[0-9a-fA-F]{1,2})[:,]" + \
> -            r"(?P<slot>[0-9a-fA-F]{1,2})[.,]" + \
> -            r"(?P<func>[0-7])$", pci_name_string)
> -    if pci_match is None:
> -        raise PciDeviceParseError(('Failed to parse pci device name: %s' %
> -            pci_name_string))
> -    pci_dev_info = pci_match.groupdict('0')
> -
> -    domain = parse_hex(pci_dev_info['domain'])
> -    bus = parse_hex(pci_dev_info['bus'])
> -    slot = parse_hex(pci_dev_info['slot'])
> -    func = parse_hex(pci_dev_info['func'])
> +    pci = parse_pci_name_extended(pci_name_string)
> +
> +    if int(pci['vslot'], 16) != AUTO_PHP_SLOT:
> +        raise PciDeviceParseError(("Failed to parse pci device: %s: " +
> +                                   "vslot provided where prohibited: %s") %
> +                                  (pci_name_string, pci['vslot']))
> +    if 'opts' in pci:
> +        raise PciDeviceParseError(("Failed to parse pci device: %s: " +
> +                                   "options provided where prohibited: %s") %
> +                                  (pci_name_string, pci['opts']))
> +
> +    return pci
> +
> +def __pci_dict_to_fmt_str(fmt, dev):
> +    return fmt % (int(dev['domain'], 16), int(dev['bus'], 16),
> +                  int(dev['slot'], 16), int(dev['func'], 16))
> 
> -    return (domain, bus, slot, func)
> +def pci_dict_to_bdf_str(dev):
> +    return __pci_dict_to_fmt_str('%04x:%02x:%02x.%01x', dev)
> +
> +def pci_dict_to_xc_str(dev):
> +    return __pci_dict_to_fmt_str('0x%x, 0x%x, 0x%x, 0x%x', dev)
> 
>  def extract_the_exact_pci_names(pci_names):
>      result = []
> @@ -198,27 +238,7 @@ def get_all_pci_names():
>      return pci_names
> 
>  def get_all_pci_devices():
> -    pci_devs = []
> -    for pci_name in get_all_pci_names():
> -        pci_match = re.match(r"((?P<domain>[0-9a-fA-F]{1,4})[:,])?" + \
> -                r"(?P<bus>[0-9a-fA-F]{1,2})[:,]" + \
> -                r"(?P<slot>[0-9a-fA-F]{1,2})[.,]" + \
> -                r"(?P<func>[0-7])$", pci_name)
> -        if pci_match is None:
> -            raise PciDeviceParseError(('Failed to parse pci device name: %s'
> %
> -                pci_name))
> -        pci_dev_info = pci_match.groupdict('0')
> -        domain = parse_hex(pci_dev_info['domain'])
> -        bus = parse_hex(pci_dev_info['bus'])
> -        slot = parse_hex(pci_dev_info['slot'])
> -        func = parse_hex(pci_dev_info['func'])
> -        try:
> -            pci_dev = PciDevice(domain, bus, slot, func)
> -        except:
> -            continue
> -        pci_devs.append(pci_dev)
> -
> -    return pci_devs
> +    return map(PciDevice, map(parse_pci_name, get_all_pci_names()))
> 
>  def _create_lspci_info():
>      """Execute 'lspci' command and parse the result.
> @@ -237,7 +257,7 @@ def _create_lspci_info():
>              try:
>                  (opt, value) = line.split(':\t')
>                  if opt == 'Slot':
> -                    device_name = PCI_DEV_FORMAT_STR % parse_pci_name(value)
> +                    device_name = pci_dict_to_bdf_str(parse_pci_name(value))
>                  else:
>                      device_info[opt] = value
>              except:
> @@ -287,8 +307,7 @@ def find_all_devices_owned_by_pciback():
>      pci_list = extract_the_exact_pci_names(pci_names)
>      dev_list = []
>      for pci in pci_list:
> -        (dom, b, d, f) = parse_pci_name(pci)
> -        dev = PciDevice(dom, b, d, f)
> +        dev = PciDevice(parse_pci_name(pci))
>          dev_list = dev_list + [dev]
>      return dev_list
> 
> @@ -395,12 +414,12 @@ class PciDeviceVslotMissing(Exception):
>          return 'pci: no vslot: ' + self.message
> 
>  class PciDevice:
> -    def __init__(self, domain, bus, slot, func):
> -        self.domain = domain
> -        self.bus = bus
> -        self.slot = slot
> -        self.func = func
> -        self.name = PCI_DEV_FORMAT_STR % (domain, bus, slot, func)
> +    def __init__(self, dev):
> +        self.domain = int(dev['domain'], 16)
> +        self.bus = int(dev['bus'], 16)
> +        self.slot = int(dev['slot'], 16)
> +        self.func = int(dev['func'], 16)
> +        self.name = pci_dict_to_bdf_str(dev)
>          self.cfg_space_path = find_sysfs_mnt()+SYSFS_PCI_DEVS_PATH+'/'+ \
>              self.name + SYSFS_PCI_DEV_CONFIG_PATH
>          self.irq = 0
> @@ -442,14 +461,15 @@ class PciDevice:
>                  # We have reached the upmost one.
>                  return None
>              else:
> +                dev = {}
>                  lst = parent.split(':')
> -                dom = int(lst[0], 16)
> -                bus = int(lst[1], 16)
> +                dev['dom'] = int(lst[0], 16)
> +                dev['bus'] = int(lst[1], 16)
>                  lst = lst[2]
>                  lst = lst.split('.')
> -                dev =  int(lst[0], 16)
> -                func =  int(lst[1], 16)
> -            return (dom, bus, dev, func)
> +                dev['slot'] = int(lst[0], 16)
> +                dev['func'] = int(lst[1], 16)
> +            return dev
>          except OSError, (errno, strerr):
>              raise PciDeviceParseError('Can not locate the parent of %s',
>                  self.name)
> @@ -459,15 +479,13 @@ class PciDevice:
>          dev = self.find_parent()
>          if dev is None:
>              return None
> -        (dom, b, d, f) = dev
> -        dev = dev_parent = PciDevice(dom, b, d, f)
> +        dev = dev_parent = PciDevice(dev)
>          while dev_parent.dev_type != DEV_TYPE_PCIe_BRIDGE:
>              parent = dev_parent.find_parent()
>              if parent is None:
>                  break
> -            (dom, b, d, f) = parent
>              dev = dev_parent
> -            dev_parent = PciDevice(dom, b, d, f)
> +            dev_parent = PciDevice(parent)
>          return dev
> 
>      def find_all_devices_behind_the_bridge(self, ignore_bridge):
> @@ -478,8 +496,7 @@ class PciDevice:
> 
>          list = [self.name]
>          for pci_str in dev_list:
> -            (dom, b, d, f) = parse_pci_name(pci_str)
> -            dev = PciDevice(dom, b, d, f)
> +            dev = PciDevice(parse_pci_name(pci_str))
>              if dev.dev_type == DEV_TYPE_PCI_BRIDGE or \
>                  dev.dev_type == DEV_TYPE_PCIe_BRIDGE:
>                  sub_list_including_self = \
> @@ -595,7 +612,7 @@ class PciDevice:
> 
>      def find_all_the_multi_functions(self):
>          sysfs_mnt = find_sysfs_mnt()
> -        parent = PCI_DEV_FORMAT_STR % self.find_parent()
> +        parent = pci_dict_to_bdf_str(self.find_parent())
>          pci_names = os.popen('ls ' + sysfs_mnt + SYSFS_PCI_DEVS_PATH + '/' +
> \
>              parent + '/').read()
>          funcs = extract_the_exact_pci_names(pci_names)
> @@ -753,8 +770,7 @@ class PciDevice:
>          if len(devs) == 0:
>              return
>          for pci_dev in devs:
> -            (dom, b, d, f) = parse_pci_name(pci_dev)
> -            dev = PciDevice(dom, b, d, f)
> +            dev = PciDevice(parse_pci_name(pci_dev))
>              if dev.driver == 'pciback':
>                  continue
>              err_msg = 'pci: %s must be co-assigned to the same guest with %s'
> + \
> @@ -780,7 +796,7 @@ class PciDevice:
>                      funcs = self.find_all_the_multi_functions()
>                      self.devs_check_driver(funcs)
> 
> -                    parent = '%04x:%02x:%02x.%01x' % self.find_parent()
> +                    parent = pci_dict_to_bdf_str(self.find_parent())
> 
>                      # Do Secondary Bus Reset.
>                      self.do_secondary_bus_reset(parent, funcs)
> Index: xen-unstable.hg/tools/python/xen/xend/XendDomainInfo.py
> ===================================================================
> --- xen-unstable.hg.orig/tools/python/xen/xend/XendDomainInfo.py
> 2009-06-15 11:22:35.000000000 +1000
> +++ xen-unstable.hg/tools/python/xen/xend/XendDomainInfo.py     2009-06-15
> 11:23:43.000000000 +1000
> @@ -39,7 +39,8 @@ from xen.util import asserts, auxbin
>  from xen.util.blkif import blkdev_uname_to_file, blkdev_uname_to_taptype
>  import xen.util.xsm.xsm as security
>  from xen.util import xsconstants
> -from xen.util.pci import serialise_pci_opts, pci_opts_list_to_sxp
> +from xen.util.pci import serialise_pci_opts, pci_opts_list_to_sxp, \
> +                         pci_dict_to_bdf_str, pci_dict_to_xc_str
> 
>  from xen.xend import balloon, sxp, uuid, image, arch
>  from xen.xend import XendOptions, XendNode, XendConfig
> @@ -310,9 +311,8 @@ def do_FLR(domid):
>      dev_str_list = get_assigned_pci_devices(domid)
> 
>      for dev_str in dev_str_list:
> -        (dom, b, d, f) = parse_pci_name(dev_str)
>          try:
> -            dev = PciDevice(dom, b, d, f)
> +            dev = PciDevice(parse_pci_name(dev_str))
>          except Exception, e:
>              raise VmError("pci: failed to locate device and "+
>                      "parse it's resources - "+str(e))
> @@ -652,23 +652,15 @@ class XendDomainInfo:
>                      raise VmError("device is already inserted")
> 
>          # Test whether the devices can be assigned with VT-d
> -        pci_str = "%s, %s, %s, %s" % (new_dev['domain'],
> -                new_dev['bus'],
> -                new_dev['slot'],
> -                new_dev['func'])
> -        bdf = xc.test_assign_device(0, pci_str)
> +        bdf = xc.test_assign_device(0, pci_dict_to_xc_str(new_dev))
>          if bdf != 0:
>              if bdf == -1:
>                  raise VmError("failed to assign device: maybe the platform"
>                                " doesn't support VT-d, or VT-d isn't enabled"
>                                " properly?")
> -            bus = (bdf >> 16) & 0xff
> -            devfn = (bdf >> 8) & 0xff
> -            dev = (devfn >> 3) & 0x1f
> -            func = devfn & 0x7
> -            raise VmError("fail to assign device(%x:%x.%x): maybe it has"
> +            raise VmError("fail to assign device(%s): maybe it has"
>                            " already been assigned to other domain, or maybe"
> -                          " it doesn't exist." % (bus, dev, func))
> +                          " it doesn't exist." %
> pci_dict_to_bdf_str(new_dev))
> 
>          # Here, we duplicate some checkings (in some cases, we mustn't allow
>          # a device to be hot-plugged into an HVM guest) that are also done in
> @@ -680,12 +672,8 @@ class XendDomainInfo:
>          # Test whether the device is owned by pciback. For instance, we can't
>          # hotplug a device being used by Dom0 itself to an HVM guest.
>          from xen.xend.server.pciif import PciDevice, parse_pci_name
> -        domain = int(new_dev['domain'],16)
> -        bus    = int(new_dev['bus'],16)
> -        dev    = int(new_dev['slot'],16)
> -        func   = int(new_dev['func'],16)
>          try:
> -            pci_device = PciDevice(domain, bus, dev, func)
> +            pci_device = PciDevice(new_dev)
>          except Exception, e:
>              raise VmError("pci: failed to locate device and "+
>                      "parse it's resources - "+str(e))
> @@ -710,9 +698,8 @@ class XendDomainInfo:
>          pci_device.devs_check_driver(coassignment_list)
>          assigned_pci_device_str_list = self._get_assigned_pci_devices()
>          for pci_str in coassignment_list:
> -            (domain, bus, dev, func) = parse_pci_name(pci_str)
> -            dev_str =  '0x%x,0x%x,0x%x,0x%x' % (domain, bus, dev, func)
> -            if xc.test_assign_device(0, dev_str) == 0:
> +            pci_dev = parse_pci_name(pci_str)
> +            if xc.test_assign_device(0, pci_dict_to_xc_str(pci_dev)) == 0:
>                  continue
>              if not pci_str in assigned_pci_device_str_list:
>                  raise VmError(("pci: failed to pci-attach %s to domain %s" +
> \
> @@ -742,12 +729,9 @@ class XendDomainInfo:
>              if new_dev.has_key('opts'):
>                  opts = ',' + serialise_pci_opts(new_dev['opts'])
> 
> -            bdf_str = "%s:%s:%s.%s@%s%s" % (new_dev['domain'],
> -                new_dev['bus'],
> -                new_dev['slot'],
> -                new_dev['func'],
> -                new_dev['vslot'],
> -                opts)
> +            bdf_str = "%s@%02x%s" % (pci_dict_to_bdf_str(new_dev),
> +                                     int(new_dev['vslot'], 16), opts)
> +            log.debug("XendDomainInfo.hvm_pci_device_insert_dev: %s" %
> bdf_str)
>              self.image.signalDeviceModel('pci-ins', 'pci-inserted', bdf_str)
> 
>              vslot =
> xstransact.Read("/local/domain/0/device-model/%i/parameter"
> @@ -864,9 +848,8 @@ class XendDomainInfo:
>                          vslot = x['vslot']
>                          break
>                  if vslot == "":
> -                    raise VmError("Device %04x:%02x:%02x.%01x is not
> connected"
> -                                  % (int(dev['domain'],16),
> int(dev['bus'],16),
> -                                     int(dev['slot'],16),
> int(dev['func'],16)))
> +                    raise VmError("Device %s is not connected" %
> +                                  pci_dict_to_bdf_str(dev))
>                  self.hvm_destroyPCIDevice(int(vslot, 16))
>                  # Update vslot
>                  dev['vslot'] = vslot
> @@ -1152,12 +1135,8 @@ class XendDomainInfo:
>          # list of D's co-assignment devices, DD is not assigned (to domN).
>          #
>          from xen.xend.server.pciif import PciDevice
> -        domain = int(x['domain'],16)
> -        bus    = int(x['bus'],16)
> -        dev    = int(x['slot'],16)
> -        func   = int(x['func'],16)
>          try:
> -            pci_device = PciDevice(domain, bus, dev, func)
> +            pci_device = PciDevice(x)
>          except Exception, e:
>              raise VmError("pci: failed to locate device and "+
>                      "parse it's resources - "+str(e))
> @@ -1172,9 +1151,8 @@ class XendDomainInfo:
>                      )% (pci_device.name, self.info['name_label'], pci_str))
> 
> 
> -        bdf_str = "%s:%s:%s.%s" % (x['domain'], x['bus'], x['slot'],
> x['func'])
> +        bdf_str = pci_dict_to_bdf_str(x)
>          log.info("hvm_destroyPCIDevice:%s:%s!", x, bdf_str)
> -
>          if self.domid is not None:
>              self.image.signalDeviceModel('pci-rem', 'pci-removed', bdf_str)
> 
> @@ -1338,21 +1316,12 @@ class XendDomainInfo:
>          if self.domid is not None:
>              return get_assigned_pci_devices(self.domid)
> 
> -        dev_str_list = []
>          dev_info = self._getDeviceInfo_pci(devid)
>          if dev_info is None:
> -            return dev_str_list
> +            return []
>          dev_uuid = sxp.child_value(dev_info, 'uuid')
>          pci_conf = self.info['devices'][dev_uuid][1]
> -        pci_devs = pci_conf['devs']
> -        for pci_dev in pci_devs:
> -            domain = int(pci_dev['domain'], 16)
> -            bus = int(pci_dev['bus'], 16)
> -            slot = int(pci_dev['slot'], 16)
> -            func = int(pci_dev['func'], 16)
> -            dev_str = "%04x:%02x:%02x.%01x" % (domain, bus, slot, func)
> -            dev_str_list = dev_str_list + [dev_str]
> -        return dev_str_list
> +        return map(pci_dict_to_bdf_str, pci_conf['devs'])
> 
>      def setMemoryTarget(self, target):
>          """Set the memory target of this domain.
> @@ -3909,12 +3878,12 @@ class XendDomainInfo:
>          target_dev = None
>          new_pci_sxp = ['pci']
>          for dev in sxp.children(old_pci_sxp, 'dev'):
> -            domain = int(sxp.child_value(dev, 'domain'), 16)
> -            bus = int(sxp.child_value(dev, 'bus'), 16)
> -            slot = int(sxp.child_value(dev, 'slot'), 16)
> -            func = int(sxp.child_value(dev, 'func'), 16)
> -            name = "%04x:%02x:%02x.%01x" % (domain, bus, slot, func)
> -            if ppci.get_name() == name:
> +            pci_dev = {}
> +            pci_dev['domain'] = sxp.child_value(dev, 'domain')
> +            pci_dev['bus'] = sxp.child_value(dev, 'bus')
> +            pci_dev['slot'] = sxp.child_value(dev, 'slot')
> +            pci_dev['func'] = sxp.child_value(dev, 'func')
> +            if ppci.get_name() == pci_dict_to_bdf_str(pci_dev):
>                  target_dev = dev
>              else:
>                  new_pci_sxp.append(dev)
> Index: xen-unstable.hg/tools/python/xen/xend/XendNode.py
> ===================================================================
> --- xen-unstable.hg.orig/tools/python/xen/xend/XendNode.py      2009-06-15
> 11:20:35.000000000 +1000
> +++ xen-unstable.hg/tools/python/xen/xend/XendNode.py   2009-06-15
> 11:23:43.000000000 +1000
> @@ -340,8 +340,7 @@ class XendNode:
>                  except KeyError:
>                      pass
> 
> -        (domain, bus, slot, func) = PciUtil.parse_pci_name(pci_name)
> -        pci_dev = PciUtil.PciDevice(domain, bus, slot, func)
> +        pci_dev = PciUtil.PciDevice(PciUtil.parse_pci_name(pci_name))
>          ppci_record = {
>              'domain':                   pci_dev.domain,
>              'bus':                      pci_dev.bus,
> Index: xen-unstable.hg/tools/python/xen/xend/server/pciif.py
> ===================================================================
> --- xen-unstable.hg.orig/tools/python/xen/xend/server/pciif.py  2009-06-15
> 11:22:35.000000000 +1000
> +++ xen-unstable.hg/tools/python/xen/xend/server/pciif.py       2009-06-15
> 11:23:43.000000000 +1000
> @@ -130,13 +130,7 @@ class PciController(DevController):
>                      log.debug('Reconfiguring PCI device %s.' % dev)
>                      attaching = False
> 
> -                (domain, bus, slotfunc) = dev.split(':')
> -                (slot, func) = slotfunc.split('.')
> -                domain = parse_hex(domain)
> -                bus = parse_hex(bus)
> -                slot = parse_hex(slot)
> -                func = parse_hex(func)
> -                self.setupOneDevice(domain, bus, slot, func)
> +                self.setupOneDevice(parse_pci_name(dev))
> 
>                  self.writeBackend(devid, 'dev-%i' % devno, dev)
>                  self.writeBackend(devid, 'state-%i' % devno,
> @@ -248,15 +242,13 @@ class PciController(DevController):
>              return
> 
>          #group string format xx:xx.x,xx:xx.x,
> -        devstr_len = group_str.find(',')
> -        for i in range(0, len(group_str), devstr_len + 1):
> -            (bus, slotfunc) = group_str[i:i + devstr_len].split(':')
> -            (slot, func) = slotfunc.split('.')
> -            b = parse_hex(bus)
> -            d = parse_hex(slot)
> -            f = parse_hex(func)
> +        for i in group_str.split(','):
> +            if i == '':
> +                continue
> +            pci_dev = parse_pci_name(i)
> +            pci_dev['domain'] = '%04x' % dev.domain
>              try:
> -                sdev = PciDevice(dev.domain, b, d, f)
> +                sdev = PciDevice(pci_dev)
>              except Exception, e:
>                  #no dom0 drivers bound to sdev
>                  continue
> @@ -270,13 +262,13 @@ class PciController(DevController):
>                      )%(sdev.name, dev.name))
>          return
> 
> -    def setupOneDevice(self, domain, bus, slot, func):
> +    def setupOneDevice(self, pci_dev):
>          """ Attach I/O resources for device to frontend domain
>          """
>          fe_domid = self.getDomid()
> 
>          try:
> -            dev = PciDevice(domain, bus, slot, func)
> +            dev = PciDevice(pci_dev)
>          except Exception, e:
>              raise VmError("pci: failed to locate device and "+
>                      "parse it's resources - "+str(e))
> @@ -305,12 +297,11 @@ class PciController(DevController):
> 
>          if not self.vm.info.is_hvm():
>              # Setup IOMMU device assignment
> -            pci_str = "0x%x, 0x%x, 0x%x, 0x%x" % (domain, bus, slot, func)
> -            bdf = xc.assign_device(fe_domid, pci_str)
> +            bdf = xc.assign_device(fe_domid, pci_dict_to_xc_str(pci_dev))
> +            pci_str = pci_dict_to_bdf_str(pci_dev)
>              if bdf > 0:
> -                raise VmError("Failed to assign device to IOMMU (%x:%x.%x)"
> -                              % (bus, slot, func))
> -            log.debug("pci: assign device %x:%x.%x" % (bus, slot, func))
> +                raise VmError("Failed to assign device to IOMMU (%s)" %
> pci_str)
> +            log.debug("pci: assign device %s" % pci_str)
> 
>          for (start, size) in dev.ioports:
>              log.debug('pci: enabling ioport 0x%x/0x%x'%(start,size))
> @@ -366,23 +357,15 @@ class PciController(DevController):
>      def setupDevice(self, config):
>          """Setup devices from config
>          """
> -        pci_str_list = []
> -        pci_dev_list = []
> -        for pci_config in config.get('devs', []):
> -            domain = parse_hex(pci_config.get('domain', 0))
> -            bus = parse_hex(pci_config.get('bus', 0))
> -            slot = parse_hex(pci_config.get('slot', 0))
> -            func = parse_hex(pci_config.get('func', 0))
> -            pci_str = '%04x:%02x:%02x.%01x' % (domain, bus, slot, func)
> -            pci_str_list = pci_str_list + [pci_str]
> -            pci_dev_list = pci_dev_list + [(domain, bus, slot, func)]
> +        pci_dev_list = config.get('devs', [])
> +        pci_str_list = map(pci_dict_to_bdf_str, pci_dev_list)
> 
>          if len(pci_str_list) != len(set(pci_str_list)):
>              raise VmError('pci: duplicate devices specified in guest
> config?')
> 
> -        for (domain, bus, slot, func) in pci_dev_list:
> +        for pci_dev in pci_dev_list:
>              try:
> -                dev = PciDevice(domain, bus, slot, func)
> +                dev = PciDevice(pci_dev)
>              except Exception, e:
>                  raise VmError("pci: failed to locate device and "+
>                          "parse it's resources - "+str(e))
> @@ -427,9 +410,7 @@ class PciController(DevController):
>                      dev.devs_check_driver(devs_str)
>                      for s in devs_str:
>                          if not s in pci_str_list:
> -                            (s_dom, s_bus, s_slot, s_func) =
> parse_pci_name(s)
> -                            s_pci_str = '0x%x,0x%x,0x%x,0x%x' % \
> -                                (s_dom, s_bus, s_slot, s_func)
> +                            s_pci_str =
> pci_dict_to_bdf_str(parse_pci_name(s))
>                              # s has been assigned to other guest?
>                              if xc.test_assign_device(0, s_pci_str) != 0:
>                                  err_msg = 'pci: %s must be co-assigned to
> the'+\
> @@ -453,13 +434,13 @@ class PciController(DevController):
>          return True
> 
> 
> -    def cleanupOneDevice(self, domain, bus, slot, func):
> +    def cleanupOneDevice(self, pci_dev):
>          """ Detach I/O resources for device from frontend domain
>          """
>          fe_domid = self.getDomid()
> 
>          try:
> -            dev = PciDevice(domain, bus, slot, func)
> +            dev = PciDevice(pci_dev)
>          except Exception, e:
>              raise VmError("pci: failed to locate device and "+
>                      "parse it's resources - "+str(e))
> @@ -476,12 +457,11 @@ class PciController(DevController):
>          # DMA transaction, etc
>          dev.do_FLR()
> 
> -        pci_str = "0x%x, 0x%x, 0x%x, 0x%x" % (domain, bus, slot, func)
> -        bdf = xc.deassign_device(fe_domid, pci_str)
> +        bdf = xc.deassign_device(fe_domid, pci_dict_to_xc_str(pci_dev))
> +        pci_str = pci_dict_to_bdf_str(pci_dev)
>          if bdf > 0:
> -            raise VmError("Failed to deassign device from IOMMU (%x:%x.%x)"
> -                          % (bus, slot, func))
> -        log.debug("pci: Deassign device %x:%x.%x" % (bus, slot, func))
> +            raise VmError("Failed to deassign device from IOMMU (%s)" %
> pci_str)
> +        log.debug("pci: Deassign device %s" % pci_str)
> 
>          for (start, size) in dev.ioports:
>              log.debug('pci: disabling ioport 0x%x/0x%x'%(start,size))
> @@ -530,15 +510,9 @@ class PciController(DevController):
>              state = int(self.readBackend(devid, 'state-%i' % i))
>              if state == xenbusState['Closing']:
>                  # Detach I/O resources.
> -                dev = self.readBackend(devid, 'dev-%i' % i)
> -                (domain, bus, slotfunc) = dev.split(':')
> -                (slot, func) = slotfunc.split('.')
> -                domain = parse_hex(domain)
> -                bus = parse_hex(bus)
> -                slot = parse_hex(slot)
> -                func = parse_hex(func)
> +                pci_dev = parse_pci_name(self.readBackend(devid, 'dev-%i' %
> i))
>                  # In HVM case, I/O resources are disabled in ioemu.
> -                self.cleanupOneDevice(domain, bus, slot, func)
> +                self.cleanupOneDevice(pci_dev)
>                  # Remove xenstore nodes.
>                  list = ['dev', 'vdev', 'state', 'uuid', 'vslot']
>                  if self.readBackend(devid, 'opts-%i' % i) is not None:
> 
> --
> 
> _______________________________________________
> Xen-devel mailing list
> Xen-devel@lists.xensource.com
> http://lists.xensource.com/xen-devel

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

* Re: [patch 08/16] xend: pass-through: Common parse_pci_name()
  2009-06-16 10:43   ` Keir Fraser
@ 2009-06-16 11:20     ` Simon Horman
  2009-06-16 12:22       ` Keir Fraser
  0 siblings, 1 reply; 28+ messages in thread
From: Simon Horman @ 2009-06-16 11:20 UTC (permalink / raw)
  To: Keir Fraser; +Cc: xen-devel, Masaki Kanno, Dexuan Cui

On Tue, Jun 16, 2009 at 11:43:32AM +0100, Keir Fraser wrote:
> This patch didn't apply. I applied patches 1-7 and also patch 9 of your
> series, but beyond that it was a bit of a trainwreck. Please refresh patch 8
> and patches 10+ and resend.

Which version of what tree are you applying against?

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

* Re: [patch 08/16] xend: pass-through: Common parse_pci_name()
  2009-06-16 11:20     ` Simon Horman
@ 2009-06-16 12:22       ` Keir Fraser
  2009-06-16 12:38         ` Simon Horman
  0 siblings, 1 reply; 28+ messages in thread
From: Keir Fraser @ 2009-06-16 12:22 UTC (permalink / raw)
  To: Simon Horman; +Cc: xen-devel, Masaki Kanno, Dexuan Cui

On 16/06/2009 12:20, "Simon Horman" <horms@verge.net.au> wrote:

> On Tue, Jun 16, 2009 at 11:43:32AM +0100, Keir Fraser wrote:
>> This patch didn't apply. I applied patches 1-7 and also patch 9 of your
>> series, but beyond that it was a bit of a trainwreck. Please refresh patch 8
>> and patches 10+ and resend.
> 
> Which version of what tree are you applying against?

Xen-unstable tip. Now c/s 19763.

 -- Keir

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

* Re: [patch 08/16] xend: pass-through: Common parse_pci_name()
  2009-06-16 12:22       ` Keir Fraser
@ 2009-06-16 12:38         ` Simon Horman
  0 siblings, 0 replies; 28+ messages in thread
From: Simon Horman @ 2009-06-16 12:38 UTC (permalink / raw)
  To: Keir Fraser; +Cc: xen-devel, Masaki Kanno, Dexuan Cui

On Tue, Jun 16, 2009 at 01:22:55PM +0100, Keir Fraser wrote:
> On 16/06/2009 12:20, "Simon Horman" <horms@verge.net.au> wrote:
> 
> > On Tue, Jun 16, 2009 at 11:43:32AM +0100, Keir Fraser wrote:
> >> This patch didn't apply. I applied patches 1-7 and also patch 9 of your
> >> series, but beyond that it was a bit of a trainwreck. Please refresh patch 8
> >> and patches 10+ and resend.
> > 
> > Which version of what tree are you applying against?
> 
> Xen-unstable tip. Now c/s 19763.

Thanks, I'll fix things up and repost.

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

end of thread, other threads:[~2009-06-16 12:38 UTC | newest]

Thread overview: 28+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2009-06-15  1:55 [patch 00/16] xend: pass-through: various clean-ups and infrastructure Simon Horman
2009-06-15  1:55 ` [patch 01/16] xend: pass-through: Only call setupOneDevice() once per device Simon Horman
2009-06-15  1:55 ` [patch 02/16] xend: pass-through: fix typo: spx -> sxp Simon Horman
2009-06-15  1:55 ` [patch 03/16] xend: pass-through: tidy up PciController() Simon Horman
2009-06-15  1:55 ` [patch 04/16] xend: pass-through: cleanupDevice: move and remove recently added vslot entry Simon Horman
2009-06-15  1:55 ` [patch 05/16] xend: pass-through: sxp.merge() cant deal with values being a list Simon Horman
2009-06-15  1:55 ` [patch 06/16] xend: pass-through: Remove PciDeviceNotFoundError, it is never used Simon Horman
2009-06-15  1:55 ` [patch 07/16] xend: pass-through: Use PCIDevice as the parameter for the constructor for PCIQuirk Simon Horman
2009-06-15  1:55 ` [patch 08/16] xend: pass-through: Common parse_pci_name() Simon Horman
2009-06-16 10:43   ` Keir Fraser
2009-06-16 11:20     ` Simon Horman
2009-06-16 12:22       ` Keir Fraser
2009-06-16 12:38         ` Simon Horman
2009-06-15  1:55 ` [patch 09/16] xend: pass-through: Use common parsing code in preprocess_pci() Simon Horman
2009-06-15  1:55 ` [patch 10/16] xend: pass-through: Add pci_dict_cmp() Simon Horman
2009-06-15  1:55 ` [patch 11/16] xend: pass-through: Move pci conversion functions to pci.py Simon Horman
2009-06-15  5:58   ` [patch 11/16] xend: pass-through: Move pci conversionfunctions " Masaki Kanno
2009-06-15  6:15     ` Simon Horman
2009-06-15  7:02       ` [patch 11/16] xend: pass-through: Move pciconversionfunctions " Masaki Kanno
2009-06-15  9:04         ` Simon Horman
2009-06-15 11:58           ` [patch v2] xend: pass-through: Move pci conversion functions " Simon Horman
2009-06-15 23:36             ` [patch 11/16 v3] " Simon Horman
2009-06-15  1:55 ` [patch 12/16] xend: pass-through: Use generic code in pci_opts_list_to_sxp() Simon Horman
2009-06-15 11:59   ` [patch v2] " Simon Horman
2009-06-15  1:55 ` [patch 13/16] xend: pass-through: Add pci_tuple_to_dict() Simon Horman
2009-06-15  1:55 ` [patch 14/16] xend: pass-through: Use common parsing code in parse_pci_configuration() Simon Horman
2009-06-15  1:55 ` [patch 15/16] xend: pass-through: Use common parsing code in getDeviceConfiguration() Simon Horman
2009-06-15  1:55 ` [patch 16/16] xend: pass-through: Clean up hvm_destroyPCIDevice() Simon Horman

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.