diff --git a/os_net_config/tests/test_utils.py b/os_net_config/tests/test_utils.py index 35cb812d..6c45c46e 100644 --- a/os_net_config/tests/test_utils.py +++ b/os_net_config/tests/test_utils.py @@ -584,6 +584,44 @@ class TestUtils(base.TestCase): def test_interface_mac_raises(self): self.assertRaises(IOError, utils.interface_mac, 'ens20f2p3') + def test_get_dpdk_devargs_mlnx(self): + def test_execute(name, dummy1, dummy2=None, dummy3=None): + if 'ethtool' in name: + out = _PCI_OUTPUT + return out, None + + def test_get_stored_pci_address(ifname, noop): + return "0000:00:07.0" + + self.stub_out('oslo_concurrency.processutils.execute', test_execute) + self.stub_out('os_net_config.utils.get_stored_pci_address', + test_get_stored_pci_address) + tmpdir = tempfile.mkdtemp() + self.stub_out('os_net_config.utils._SYS_CLASS_NET', tmpdir) + nic = 'p4p1' + nic_path = os.path.join(tmpdir, nic) + os.makedirs(nic_path) + os.makedirs(os.path.join(nic_path, 'device')) + # Testing standard Mellanox Connect-X cards + with open(os.path.join(nic_path, 'operstate'), 'w') as f: + f.write('up') + with open(os.path.join(nic_path, 'address'), 'w') as f: + f.write('00:0f:21:69:39:14') + with open(os.path.join(nic_path, 'device', 'vendor'), 'w') as f: + f.write('0x15b3') + self.assertEqual(utils.get_dpdk_devargs(nic, False), + '0000:00:19.0') + # now testing the Mellanox CX3 + with open(os.path.join(nic_path, 'device', 'device'), 'w') as f: + f.write('0x1007') + self.assertEqual(utils.get_dpdk_devargs(nic, False), + 'class=eth,mac=00:0f:21:69:39:14') + with open(os.path.join(nic_path, 'device', 'vendor'), 'w') as f: + f.write('0x15b4') + self.assertEqual(utils.get_dpdk_devargs(nic, False), + '0000:00:07.0') + shutil.rmtree(tmpdir) + def test_is_active_nic_for_sriov_vf(self): tmpdir = tempfile.mkdtemp() diff --git a/os_net_config/utils.py b/os_net_config/utils.py index 6e346c84..b02ba91d 100644 --- a/os_net_config/utils.py +++ b/os_net_config/utils.py @@ -105,14 +105,14 @@ def get_file_data(filename): def interface_mac(name): try: # If the iface is part of a Linux bond, the real MAC is only here. - with open('/sys/class/net/%s/bonding_slave/perm_hwaddr' % name, + with open(_SYS_CLASS_NET + '/%s/bonding_slave/perm_hwaddr' % name, 'r') as f: return f.read().rstrip() except IOError: pass # Iface is not part of a bond, continue try: - with open('/sys/class/net/%s/address' % name, 'r') as f: + with open(_SYS_CLASS_NET + '/%s/address' % name, 'r') as f: return f.read().rstrip() except IOError: # If the interface is bound to a DPDK driver, get the mac address from @@ -385,13 +385,23 @@ def get_dpdk_devargs(ifname, noop): if not noop: vendor_id = get_vendor_id(ifname) device_id = get_device_id(ifname) - if vendor_id == "0x15b3" and device_id == "0x1007": - # Some NICs (i.e. Mellanox ConnectX-3) have only one PCI address - # associated with multiple ports. Using a PCI device won’t work. - # Instead, we should use "class=eth,mac=" - dpdk_devargs = "class=eth,mac=%s" % interface_mac(ifname) + if vendor_id == "0x15b3": + logger.info("Getting devargs for Mellanox cards") + if device_id == "0x1007": + # Some NICs (i.e. Mellanox ConnectX-3) have only one PCI + # address associated with multiple ports. Using a PCI + # device won’t work. Instead, we should use + # "class=eth,mac=" + dpdk_devargs = "class=eth,mac=%s" % interface_mac(ifname) + elif is_active_nic(ifname): + # Other Mellanox devices are active and they are not stored + # in dpdk_mapping.yaml file, so we need to get their pci + # address with ethtool. + dpdk_devargs = get_pci_address(ifname, noop) else: + logger.info("Getting stored PCI address as devarg") dpdk_devargs = get_stored_pci_address(ifname, noop) + logger.debug("Devargs found: %s" % (dpdk_devargs)) return dpdk_devargs