summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorNikola Dipanov <ndipanov@redhat.com>2016-04-05 19:04:07 +0100
committerSahid Orentino Ferdjaoui <sahid.ferdjaoui@redhat.com>2016-06-01 08:51:03 -0400
commit0b85bb4b42ab8d47809ecb9244df88770de5d89b (patch)
treeff6f8fabd1e83879d99df6383e76f742be39861c
parentc469b8466fc5ff5514957a0fbd17d141761774c8 (diff)
downloadnova-0b85bb4b42ab8d47809ecb9244df88770de5d89b.tar.gz
pci: related updates are done without DB lookups
Now that we have all relationships recorded on objects kept in the master-list in memory, we can use those links to do updates (that eventually get saved on pci_tracker.save()) without wrongfully updating objects within the local scope and losing changes immediately. As a convenience, we add two properties to the PciDevice object that take care of fetching related objects without worrying about missing or unset values. We also clarify a bit more how to use PciDevTracker.pci_devs attribute and why we can't just randomly fish PciDevices out of the DB for the purposes of updating them. Change-Id: I118ba35f464afc970fef54759d5560ba20ff9c52 Closes-bug: #1565785
-rw-r--r--nova/objects/pci_device.py62
-rw-r--r--nova/pci/manager.py14
-rw-r--r--nova/pci/stats.py10
-rw-r--r--nova/tests/unit/objects/test_pci_device.py248
-rw-r--r--nova/tests/unit/pci/test_stats.py134
5 files changed, 199 insertions, 269 deletions
diff --git a/nova/objects/pci_device.py b/nova/objects/pci_device.py
index a61a5f3bd7..87e55645e9 100644
--- a/nova/objects/pci_device.py
+++ b/nova/objects/pci_device.py
@@ -279,10 +279,7 @@ class PciDevice(base.NovaPersistentObject, base.NovaObject):
if self.dev_type == fields.PciDeviceType.SRIOV_PF:
# Update PF status to CLAIMED if all of it dependants are free
# and set their status to UNCLAIMABLE
- vfs_list = objects.PciDeviceList.get_by_parent_address(
- self._context,
- self.compute_node_id,
- self.address)
+ vfs_list = self.child_devices
if not all([vf.is_available() for vf in vfs_list]):
raise exception.PciDeviceVFInvalidStatus(
compute_node_id=self.compute_node_id,
@@ -301,10 +298,8 @@ class PciDevice(base.NovaPersistentObject, base.NovaObject):
parent_ok_statuses = (fields.PciDeviceStatus.AVAILABLE,
fields.PciDeviceStatus.UNCLAIMABLE,
fields.PciDeviceStatus.UNAVAILABLE)
- try:
- parent = self.get_by_dev_addr(self._context,
- self.compute_node_id,
- self.parent_addr)
+ parent = self.parent_device
+ if parent:
if parent.status not in parent_ok_statuses:
raise exception.PciDevicePFInvalidStatus(
compute_node_id=self.compute_node_id,
@@ -314,11 +309,11 @@ class PciDevice(base.NovaPersistentObject, base.NovaObject):
# Set PF status
if parent.status == fields.PciDeviceStatus.AVAILABLE:
parent.status = fields.PciDeviceStatus.UNCLAIMABLE
- except exception.PciDeviceNotFound:
+ else:
LOG.debug('Physical function addr: %(pf_addr)s parent of '
- 'VF addr: %(vf_addr)s was not found',
- {'pf_addr': self.parent_addr,
- 'vf_addr': self.address})
+ 'VF addr: %(vf_addr)s was not found',
+ {'pf_addr': self.parent_addr,
+ 'vf_addr': self.address})
self.status = fields.PciDeviceStatus.CLAIMED
self.instance_uuid = instance_uuid
@@ -343,10 +338,7 @@ class PciDevice(base.NovaPersistentObject, base.NovaObject):
address=self.address, owner=self.instance_uuid,
hopeowner=instance['uuid'])
if self.dev_type == fields.PciDeviceType.SRIOV_PF:
- vfs_list = objects.PciDeviceList.get_by_parent_address(
- self._context,
- self.compute_node_id,
- self.address)
+ vfs_list = self.child_devices
if not all([vf.status in dependatns_ok_statuses for
vf in vfs_list]):
raise exception.PciDeviceVFInvalidStatus(
@@ -356,10 +348,8 @@ class PciDevice(base.NovaPersistentObject, base.NovaObject):
fields.PciDeviceStatus.UNAVAILABLE)
elif (self.dev_type == fields.PciDeviceType.SRIOV_VF):
- try:
- parent = self.get_by_dev_addr(self._context,
- self.compute_node_id,
- self.parent_addr)
+ parent = self.parent_device
+ if parent:
if parent.status not in parent_ok_statuses:
raise exception.PciDevicePFInvalidStatus(
compute_node_id=self.compute_node_id,
@@ -368,7 +358,7 @@ class PciDevice(base.NovaPersistentObject, base.NovaObject):
hopestatus=parent_ok_statuses)
# Set PF status
parent.status = fields.PciDeviceStatus.UNAVAILABLE
- except exception.PciDeviceNotFound:
+ else:
LOG.debug('Physical function addr: %(pf_addr)s parent of '
'VF addr: %(vf_addr)s was not found',
{'pf_addr': self.parent_addr,
@@ -412,31 +402,23 @@ class PciDevice(base.NovaPersistentObject, base.NovaObject):
hopeowner=instance['uuid'])
if self.dev_type == fields.PciDeviceType.SRIOV_PF:
# Set all PF dependants status to AVAILABLE
- vfs_list = objects.PciDeviceList.get_by_parent_address(
- self._context,
- self.compute_node_id,
- self.address)
+ vfs_list = self.child_devices
self._bulk_update_status(vfs_list,
fields.PciDeviceStatus.AVAILABLE)
free_devs.extend(vfs_list)
if self.dev_type == fields.PciDeviceType.SRIOV_VF:
# Set PF status to AVAILABLE if all of it's VFs are free
- vfs_list = objects.PciDeviceList.get_by_parent_address(
- self._context,
- self.compute_node_id,
- self.parent_addr)
- if all([vf.is_available() for vf in vfs_list if vf.id != self.id]):
- try:
- parent = self.get_by_dev_addr(self._context,
- self.compute_node_id,
- self.parent_addr)
- parent.status = fields.PciDeviceStatus.AVAILABLE
+ parent = self.parent_device
+ if not parent:
+ LOG.debug('Physical function addr: %(pf_addr)s parent of '
+ 'VF addr: %(vf_addr)s was not found',
+ {'pf_addr': self.parent_addr,
+ 'vf_addr': self.address})
+ else:
+ vfs_list = parent.child_devices
+ if all([vf.is_available() for vf in vfs_list
+ if vf.id != self.id]):
free_devs.append(parent)
- except exception.PciDeviceNotFound:
- LOG.debug('Physical function addr: %(pf_addr)s parent of '
- 'VF addr: %(vf_addr)s was not found',
- {'pf_addr': self.parent_addr,
- 'vf_addr': self.address})
old_status = self.status
self.status = fields.PciDeviceStatus.AVAILABLE
free_devs.append(self)
diff --git a/nova/pci/manager.py b/nova/pci/manager.py
index c98c15c94c..473d5bf4d1 100644
--- a/nova/pci/manager.py
+++ b/nova/pci/manager.py
@@ -40,8 +40,18 @@ class PciDevTracker(object):
It's called by compute node resource tracker to allocate and free
devices to/from instances, and to update the available pci passthrough
- devices information from hypervisor periodically. The devices
- information is updated to DB when devices information is changed.
+ devices information from hypervisor periodically.
+
+ `pci_devs` attribute of this class is the in-memory "master copy" of all
+ devices on each compute host, and all data changes that happen when
+ claiming/allocating/freeing
+ devices HAVE TO be made against instances contained in `pci_devs` list,
+ because they are periodically flushed to the DB when the save()
+ method is called.
+
+ It is unsafe to fetch PciDevice objects elsewhere in the code for update
+ purposes as those changes will end up being overwritten when the `pci_devs`
+ are saved.
"""
def __init__(self, context, node_id=None):
diff --git a/nova/pci/stats.py b/nova/pci/stats.py
index 3185ca66b0..cd713499d5 100644
--- a/nova/pci/stats.py
+++ b/nova/pci/stats.py
@@ -22,7 +22,6 @@ import six
from nova import exception
from nova.i18n import _LE
-from nova import objects
from nova.objects import fields
from nova.objects import pci_device_pool
from nova.pci import utils
@@ -192,18 +191,13 @@ class PciDeviceStats(object):
decreased, unless it is no longer in a pool.
"""
if pci_dev.dev_type == fields.PciDeviceType.SRIOV_PF:
- vfs_list = objects.PciDeviceList.get_by_parent_address(
- pci_dev._context,
- pci_dev.compute_node_id,
- pci_dev.address)
+ vfs_list = pci_dev.child_devices
if vfs_list:
for vf in vfs_list:
self.remove_device(vf)
elif pci_dev.dev_type == fields.PciDeviceType.SRIOV_VF:
try:
- parent = pci_dev.get_by_dev_addr(pci_dev._context,
- pci_dev.compute_node_id,
- pci_dev.parent_addr)
+ parent = pci_dev.parent_device
# Make sure not to decrease PF pool count if this parent has
# been already removed from pools
if parent in self.get_free_devs():
diff --git a/nova/tests/unit/objects/test_pci_device.py b/nova/tests/unit/objects/test_pci_device.py
index 00818a877b..b56cb455fe 100644
--- a/nova/tests/unit/objects/test_pci_device.py
+++ b/nova/tests/unit/objects/test_pci_device.py
@@ -25,7 +25,6 @@ from nova import objects
from nova.objects import fields
from nova.objects import instance
from nova.objects import pci_device
-from nova import test
from nova.tests.unit.objects import test_objects
from nova.tests import uuidsentinel as uuids
@@ -523,6 +522,7 @@ class _TestSRIOVPciDeviceObject(object):
'numa_node': 0}
pci_dev_obj = objects.PciDevice.create(None, pci_dev)
pci_dev_obj.id = num_pfs + 81
+ pci_dev_obj.child_devices = []
self.sriov_pf_devices.append(pci_dev_obj)
self.sriov_vf_devices = []
@@ -538,6 +538,8 @@ class _TestSRIOVPciDeviceObject(object):
'numa_node': 0}
pci_dev_obj = objects.PciDevice.create(None, pci_dev)
pci_dev_obj.id = num_vfs + 1
+ pci_dev_obj.parent_device = self.sriov_pf_devices[int(dev / 4)]
+ pci_dev_obj.parent_device.child_devices.append(pci_dev_obj)
self.sriov_vf_devices.append(pci_dev_obj)
def _create_fake_instance(self):
@@ -553,188 +555,158 @@ class _TestSRIOVPciDeviceObject(object):
self.mox.ReplayAll()
self.pci_device = pci_device.PciDevice.get_by_dev_addr(ctxt, 1, 'a')
- def _fake_get_by_parent_address(self, ctxt, node_id, addr):
+ def _get_children_by_parent_address(self, addr):
vf_devs = []
for dev in self.sriov_vf_devices:
if dev.parent_addr == addr:
vf_devs.append(dev)
return vf_devs
- def _fake_pci_device_get_by_addr(self, ctxt, id, addr):
+ def _get_parent_by_address(self, addr):
for dev in self.sriov_pf_devices:
if dev.address == addr:
return dev
def test_claim_PF(self):
self._create_fake_instance()
- with mock.patch.object(objects.PciDeviceList, 'get_by_parent_address',
- side_effect=self._fake_get_by_parent_address):
- self._create_pci_devices()
- devobj = self.sriov_pf_devices[0]
- devobj.claim(self.inst.uuid)
- self.assertEqual(devobj.status,
- fields.PciDeviceStatus.CLAIMED)
- self.assertEqual(devobj.instance_uuid,
- self.inst.uuid)
- self.assertEqual(len(self.inst.pci_devices), 0)
- # check if the all the dependants are UNCLAIMABLE
- self.assertTrue(all(
- [dev.status == fields.PciDeviceStatus.UNCLAIMABLE for
- dev in self._fake_get_by_parent_address(None, None,
- self.sriov_pf_devices[0].address)]))
+ self._create_pci_devices()
+ devobj = self.sriov_pf_devices[0]
+ devobj.claim(self.inst.uuid)
+ self.assertEqual(devobj.status,
+ fields.PciDeviceStatus.CLAIMED)
+ self.assertEqual(devobj.instance_uuid,
+ self.inst.uuid)
+ self.assertEqual(len(self.inst.pci_devices), 0)
+ # check if the all the dependants are UNCLAIMABLE
+ self.assertTrue(all(
+ [dev.status == fields.PciDeviceStatus.UNCLAIMABLE for
+ dev in self._get_children_by_parent_address(
+ self.sriov_pf_devices[0].address)]))
def test_claim_VF(self):
self._create_fake_instance()
- with mock.patch.object(objects.PciDevice, 'get_by_dev_addr',
- side_effect=self._fake_pci_device_get_by_addr):
- self._create_pci_devices()
- devobj = self.sriov_vf_devices[0]
- devobj.claim(self.inst.uuid)
- self.assertEqual(devobj.status,
- fields.PciDeviceStatus.CLAIMED)
- self.assertEqual(devobj.instance_uuid,
- self.inst.uuid)
- self.assertEqual(len(self.inst.pci_devices), 0)
+ self._create_pci_devices()
+ devobj = self.sriov_vf_devices[0]
+ devobj.claim(self.inst.uuid)
+ self.assertEqual(devobj.status,
+ fields.PciDeviceStatus.CLAIMED)
+ self.assertEqual(devobj.instance_uuid,
+ self.inst.uuid)
+ self.assertEqual(len(self.inst.pci_devices), 0)
- # check if parent device status has been changed to UNCLAIMABLE
- parent = self._fake_pci_device_get_by_addr(None, None,
- devobj.parent_addr)
- self.assertTrue(fields.PciDeviceStatus.UNCLAIMABLE, parent.status)
+ # check if parent device status has been changed to UNCLAIMABLE
+ parent = self._get_parent_by_address(devobj.parent_addr)
+ self.assertTrue(fields.PciDeviceStatus.UNCLAIMABLE, parent.status)
def test_allocate_PF(self):
self._create_fake_instance()
- with mock.patch.object(objects.PciDeviceList, 'get_by_parent_address',
- side_effect=self._fake_get_by_parent_address):
- self._create_pci_devices()
- devobj = self.sriov_pf_devices[0]
- devobj.claim(self.inst.uuid)
- devobj.allocate(self.inst)
- self.assertEqual(devobj.status,
- fields.PciDeviceStatus.ALLOCATED)
- self.assertEqual(devobj.instance_uuid,
- self.inst.uuid)
- self.assertEqual(len(self.inst.pci_devices), 1)
- # check if the all the dependants are UNAVAILABLE
- self.assertTrue(all(
- [dev.status == fields.PciDeviceStatus.UNAVAILABLE for
- dev in self._fake_get_by_parent_address(None, None,
- self.sriov_pf_devices[0].address)]))
+ self._create_pci_devices()
+ devobj = self.sriov_pf_devices[0]
+ devobj.claim(self.inst.uuid)
+ devobj.allocate(self.inst)
+ self.assertEqual(devobj.status,
+ fields.PciDeviceStatus.ALLOCATED)
+ self.assertEqual(devobj.instance_uuid,
+ self.inst.uuid)
+ self.assertEqual(len(self.inst.pci_devices), 1)
+ # check if the all the dependants are UNAVAILABLE
+ self.assertTrue(all(
+ [dev.status == fields.PciDeviceStatus.UNAVAILABLE for
+ dev in self._get_children_by_parent_address(
+ self.sriov_pf_devices[0].address)]))
def test_allocate_VF(self):
self._create_fake_instance()
- with mock.patch.object(objects.PciDevice, 'get_by_dev_addr',
- side_effect=self._fake_pci_device_get_by_addr):
- self._create_pci_devices()
- devobj = self.sriov_vf_devices[0]
- devobj.claim(self.inst.uuid)
- devobj.allocate(self.inst)
- self.assertEqual(devobj.status,
- fields.PciDeviceStatus.ALLOCATED)
- self.assertEqual(devobj.instance_uuid,
- self.inst.uuid)
- self.assertEqual(len(self.inst.pci_devices), 1)
+ self._create_pci_devices()
+ devobj = self.sriov_vf_devices[0]
+ devobj.claim(self.inst.uuid)
+ devobj.allocate(self.inst)
+ self.assertEqual(devobj.status,
+ fields.PciDeviceStatus.ALLOCATED)
+ self.assertEqual(devobj.instance_uuid,
+ self.inst.uuid)
+ self.assertEqual(len(self.inst.pci_devices), 1)
- # check if parent device status has been changed to UNAVAILABLE
- parent = self._fake_pci_device_get_by_addr(None, None,
- devobj.parent_addr)
- self.assertTrue(fields.PciDeviceStatus.UNAVAILABLE, parent.status)
+ # check if parent device status has been changed to UNAVAILABLE
+ parent = self._get_parent_by_address(devobj.parent_addr)
+ self.assertTrue(fields.PciDeviceStatus.UNAVAILABLE, parent.status)
def test_claim_PF_fail(self):
self._create_fake_instance()
- with mock.patch.object(objects.PciDeviceList, 'get_by_parent_address',
- side_effect=self._fake_get_by_parent_address):
- self._create_pci_devices()
- devobj = self.sriov_pf_devices[0]
- self.sriov_vf_devices[0].status = fields.PciDeviceStatus.CLAIMED
+ self._create_pci_devices()
+ devobj = self.sriov_pf_devices[0]
+ self.sriov_vf_devices[0].status = fields.PciDeviceStatus.CLAIMED
- self.assertRaises(exception.PciDeviceVFInvalidStatus,
- devobj.claim, self.inst)
+ self.assertRaises(exception.PciDeviceVFInvalidStatus,
+ devobj.claim, self.inst)
def test_claim_VF_fail(self):
self._create_fake_instance()
- with mock.patch.object(objects.PciDevice, 'get_by_dev_addr',
- side_effect=self._fake_pci_device_get_by_addr):
- self._create_pci_devices()
- devobj = self.sriov_vf_devices[0]
- parent = self._fake_pci_device_get_by_addr(None, None,
- devobj.parent_addr)
- parent.status = fields.PciDeviceStatus.CLAIMED
+ self._create_pci_devices()
+ devobj = self.sriov_vf_devices[0]
+ parent = self._get_parent_by_address(devobj.parent_addr)
+ parent.status = fields.PciDeviceStatus.CLAIMED
- self.assertRaises(exception.PciDevicePFInvalidStatus,
- devobj.claim, self.inst)
+ self.assertRaises(exception.PciDevicePFInvalidStatus,
+ devobj.claim, self.inst)
def test_allocate_PF_fail(self):
self._create_fake_instance()
- with mock.patch.object(objects.PciDeviceList, 'get_by_parent_address',
- side_effect=self._fake_get_by_parent_address):
- self._create_pci_devices()
- devobj = self.sriov_pf_devices[0]
- self.sriov_vf_devices[0].status = fields.PciDeviceStatus.CLAIMED
+ self._create_pci_devices()
+ devobj = self.sriov_pf_devices[0]
+ self.sriov_vf_devices[0].status = fields.PciDeviceStatus.CLAIMED
- self.assertRaises(exception.PciDeviceVFInvalidStatus,
- devobj.allocate, self.inst)
+ self.assertRaises(exception.PciDeviceVFInvalidStatus,
+ devobj.allocate, self.inst)
def test_allocate_VF_fail(self):
self._create_fake_instance()
- with mock.patch.object(objects.PciDevice, 'get_by_dev_addr',
- side_effect=self._fake_pci_device_get_by_addr):
- self._create_pci_devices()
- devobj = self.sriov_vf_devices[0]
- parent = self._fake_pci_device_get_by_addr(None, None,
- devobj.parent_addr)
- parent.status = fields.PciDeviceStatus.CLAIMED
+ self._create_pci_devices()
+ devobj = self.sriov_vf_devices[0]
+ parent = self._get_parent_by_address(devobj.parent_addr)
+ parent.status = fields.PciDeviceStatus.CLAIMED
- self.assertRaises(exception.PciDevicePFInvalidStatus,
- devobj.allocate, self.inst)
+ self.assertRaises(exception.PciDevicePFInvalidStatus,
+ devobj.allocate, self.inst)
def test_free_allocated_PF(self):
self._create_fake_instance()
- with mock.patch.object(objects.PciDeviceList, 'get_by_parent_address',
- side_effect=self._fake_get_by_parent_address):
- self._create_pci_devices()
- devobj = self.sriov_pf_devices[0]
- devobj.claim(self.inst.uuid)
- devobj.allocate(self.inst)
- devobj.free(self.inst)
- self.assertEqual(devobj.status,
- fields.PciDeviceStatus.AVAILABLE)
- self.assertIsNone(devobj.instance_uuid)
- # check if the all the dependants are AVAILABLE
- self.assertTrue(all(
- [dev.status == fields.PciDeviceStatus.AVAILABLE for
- dev in self._fake_get_by_parent_address(None, None,
- self.sriov_pf_devices[0].address)]))
+ self._create_pci_devices()
+ devobj = self.sriov_pf_devices[0]
+ devobj.claim(self.inst.uuid)
+ devobj.allocate(self.inst)
+ devobj.free(self.inst)
+ self.assertEqual(devobj.status,
+ fields.PciDeviceStatus.AVAILABLE)
+ self.assertIsNone(devobj.instance_uuid)
+ # check if the all the dependants are AVAILABLE
+ self.assertTrue(all(
+ [dev.status == fields.PciDeviceStatus.AVAILABLE for
+ dev in self._get_children_by_parent_address(
+ self.sriov_pf_devices[0].address)]))
def test_free_allocated_VF(self):
self._create_fake_instance()
- with test.nested(
- mock.patch.object(objects.PciDevice, 'get_by_dev_addr',
- side_effect=self._fake_pci_device_get_by_addr),
- mock.patch.object(objects.PciDeviceList, 'get_by_parent_address',
- side_effect=self._fake_get_by_parent_address)):
- self._create_pci_devices()
- vf = self.sriov_vf_devices[0]
- dependents = self._fake_get_by_parent_address(None, None,
- vf.parent_addr)
- for devobj in dependents:
- devobj.claim(self.inst.uuid)
- devobj.allocate(self.inst)
- self.assertEqual(devobj.status,
- fields.PciDeviceStatus.ALLOCATED)
- for devobj in dependents[:3]:
- devobj.free(self.inst)
- # check if parent device status is still UNAVAILABLE
- parent = self._fake_pci_device_get_by_addr(None, None,
- devobj.parent_addr)
- self.assertTrue(fields.PciDeviceStatus.UNAVAILABLE,
- parent.status)
- for devobj in dependents[3:]:
- devobj.free(self.inst)
- # check if parent device status is now AVAILABLE
- parent = self._fake_pci_device_get_by_addr(None, None,
- devobj.parent_addr)
- self.assertTrue(fields.PciDeviceStatus.AVAILABLE,
- parent.status)
+ self._create_pci_devices()
+ vf = self.sriov_vf_devices[0]
+ dependents = self._get_children_by_parent_address(vf.parent_addr)
+ for devobj in dependents:
+ devobj.claim(self.inst.uuid)
+ devobj.allocate(self.inst)
+ self.assertEqual(devobj.status,
+ fields.PciDeviceStatus.ALLOCATED)
+ for devobj in dependents[:3]:
+ devobj.free(self.inst)
+ # check if parent device status is still UNAVAILABLE
+ parent = self._get_parent_by_address(devobj.parent_addr)
+ self.assertTrue(fields.PciDeviceStatus.UNAVAILABLE,
+ parent.status)
+ for devobj in dependents[3:]:
+ devobj.free(self.inst)
+ # check if parent device status is now AVAILABLE
+ parent = self._get_parent_by_address(devobj.parent_addr)
+ self.assertTrue(fields.PciDeviceStatus.AVAILABLE,
+ parent.status)
class TestSRIOVPciDeviceListObject(test_objects._LocalTest,
diff --git a/nova/tests/unit/pci/test_stats.py b/nova/tests/unit/pci/test_stats.py
index bf0c1b0f0d..3a42d1435a 100644
--- a/nova/tests/unit/pci/test_stats.py
+++ b/nova/tests/unit/pci/test_stats.py
@@ -367,8 +367,9 @@ class PciDeviceVFPFStatsTestCase(test.NoDBTestCase):
'dev_type': fields.PciDeviceType.SRIOV_PF,
'parent_addr': None,
'numa_node': 0}
- self.sriov_pf_devices.append(objects.PciDevice.create(None,
- pci_dev))
+ dev_obj = objects.PciDevice.create(None, pci_dev)
+ dev_obj.child_devices = []
+ self.sriov_pf_devices.append(dev_obj)
self.sriov_vf_devices = []
for dev in range(8):
@@ -381,95 +382,66 @@ class PciDeviceVFPFStatsTestCase(test.NoDBTestCase):
'dev_type': fields.PciDeviceType.SRIOV_VF,
'parent_addr': '0000:81:00.%d' % int(dev / 4),
'numa_node': 0}
- self.sriov_vf_devices.append(objects.PciDevice.create(None,
- pci_dev))
+ dev_obj = objects.PciDevice.create(None, pci_dev)
+ dev_obj.parent_device = self.sriov_pf_devices[int(dev / 4)]
+ dev_obj.parent_device.child_devices.append(dev_obj)
+ self.sriov_vf_devices.append(dev_obj)
list(map(self.pci_stats.add_device, self.sriov_pf_devices))
list(map(self.pci_stats.add_device, self.sriov_vf_devices))
- def _fake_get_by_parent_address(self, ctxt, node_id, addr):
- vf_devs = []
- for dev in self.sriov_vf_devices:
- if dev.parent_addr == addr:
- vf_devs.append(dev)
- return vf_devs
-
- def _fake_pci_device_get_by_addr(self, ctxt, id, addr):
- for dev in self.sriov_pf_devices:
- if dev.address == addr:
- return dev
-
def test_consume_VF_requests(self):
- with mock.patch.object(objects.PciDevice, 'get_by_dev_addr',
- side_effect=self._fake_pci_device_get_by_addr):
- self._create_pci_devices()
- pci_requests = [objects.InstancePCIRequest(count=2,
- spec=[{'product_id': '1515'}])]
- devs = self.pci_stats.consume_requests(pci_requests)
- self.assertEqual(2, len(devs))
- self.assertEqual(set(['1515']),
- set([dev.product_id for dev in devs]))
- free_devs = self.pci_stats.get_free_devs()
- # Validate that the parents of these VFs has been removed
- # from pools.
- for dev in devs:
- self.assertTrue(all(dev.parent_addr != free_dev.address
- for free_dev in free_devs))
+ self._create_pci_devices()
+ pci_requests = [objects.InstancePCIRequest(count=2,
+ spec=[{'product_id': '1515'}])]
+ devs = self.pci_stats.consume_requests(pci_requests)
+ self.assertEqual(2, len(devs))
+ self.assertEqual(set(['1515']),
+ set([dev.product_id for dev in devs]))
+ free_devs = self.pci_stats.get_free_devs()
+ # Validate that the parents of these VFs has been removed
+ # from pools.
+ for dev in devs:
+ self.assertTrue(all(dev.parent_addr != free_dev.address
+ for free_dev in free_devs))
def test_consume_PF_requests(self):
- with mock.patch.object(objects.PciDeviceList, 'get_by_parent_address',
- side_effect=self._fake_get_by_parent_address):
- self._create_pci_devices()
- pci_requests = [objects.InstancePCIRequest(count=2,
- spec=[{'product_id': '1528',
- 'dev_type': 'type-PF'}])]
- devs = self.pci_stats.consume_requests(pci_requests)
- self.assertEqual(2, len(devs))
- self.assertEqual(set(['1528']),
- set([dev.product_id for dev in devs]))
- free_devs = self.pci_stats.get_free_devs()
- # Validate that there are no free devices left, as when allocating
- # both available PFs, its VFs should not be available.
- self.assertEqual(0, len(free_devs))
+ self._create_pci_devices()
+ pci_requests = [objects.InstancePCIRequest(count=2,
+ spec=[{'product_id': '1528',
+ 'dev_type': 'type-PF'}])]
+ devs = self.pci_stats.consume_requests(pci_requests)
+ self.assertEqual(2, len(devs))
+ self.assertEqual(set(['1528']),
+ set([dev.product_id for dev in devs]))
+ free_devs = self.pci_stats.get_free_devs()
+ # Validate that there are no free devices left, as when allocating
+ # both available PFs, its VFs should not be available.
+ self.assertEqual(0, len(free_devs))
def test_consume_VF_and_PF_requests(self):
- with test.nested(
- mock.patch.object(objects.PciDevice, 'get_by_dev_addr',
- side_effect=self._fake_pci_device_get_by_addr),
- mock.patch.object(objects.PciDeviceList, 'get_by_parent_address',
- side_effect=self._fake_get_by_parent_address)):
- self._create_pci_devices()
- pci_requests = [objects.InstancePCIRequest(count=2,
- spec=[{'product_id': '1515'}]),
- objects.InstancePCIRequest(count=1,
- spec=[{'product_id': '1528',
- 'dev_type': 'type-PF'}])]
- devs = self.pci_stats.consume_requests(pci_requests)
- self.assertEqual(3, len(devs))
- self.assertEqual(set(['1528', '1515']),
- set([dev.product_id for dev in devs]))
+ self._create_pci_devices()
+ pci_requests = [objects.InstancePCIRequest(count=2,
+ spec=[{'product_id': '1515'}]),
+ objects.InstancePCIRequest(count=1,
+ spec=[{'product_id': '1528',
+ 'dev_type': 'type-PF'}])]
+ devs = self.pci_stats.consume_requests(pci_requests)
+ self.assertEqual(3, len(devs))
+ self.assertEqual(set(['1528', '1515']),
+ set([dev.product_id for dev in devs]))
def test_consume_VF_and_PF_requests_failed(self):
- with test.nested(
- mock.patch.object(objects.PciDevice, 'get_by_dev_addr',
- side_effect=self._fake_pci_device_get_by_addr),
- mock.patch.object(objects.PciDeviceList, 'get_by_parent_address',
- side_effect=self._fake_get_by_parent_address)):
- self._create_pci_devices()
- pci_requests = [objects.InstancePCIRequest(count=5,
- spec=[{'product_id': '1515'}]),
- objects.InstancePCIRequest(count=1,
- spec=[{'product_id': '1528',
- 'dev_type': 'type-PF'}])]
- self.assertIsNone(self.pci_stats.consume_requests(pci_requests))
+ self._create_pci_devices()
+ pci_requests = [objects.InstancePCIRequest(count=5,
+ spec=[{'product_id': '1515'}]),
+ objects.InstancePCIRequest(count=1,
+ spec=[{'product_id': '1528',
+ 'dev_type': 'type-PF'}])]
+ self.assertIsNone(self.pci_stats.consume_requests(pci_requests))
def test_consume_VF_and_PF_same_prodict_id_failed(self):
- with test.nested(
- mock.patch.object(objects.PciDevice, 'get_by_dev_addr',
- side_effect=self._fake_pci_device_get_by_addr),
- mock.patch.object(objects.PciDeviceList, 'get_by_parent_address',
- side_effect=self._fake_get_by_parent_address)):
- self._create_pci_devices(pf_product_id=1515)
- pci_requests = [objects.InstancePCIRequest(count=9,
- spec=[{'product_id': '1515'}])]
- self.assertIsNone(self.pci_stats.consume_requests(pci_requests))
+ self._create_pci_devices(pf_product_id=1515)
+ pci_requests = [objects.InstancePCIRequest(count=9,
+ spec=[{'product_id': '1515'}])]
+ self.assertIsNone(self.pci_stats.consume_requests(pci_requests))