X-Git-Url: https://gerrit.fd.io/r/gitweb?p=csit.git;a=blobdiff_plain;f=resources%2Flibraries%2Fpython%2FDUTSetup.py;h=bccf108524a14cf82d7d00a4d974183bae8c2389;hp=6b2f5edb83492acaa820cef9f6b5a5b3134e8800;hb=d40746ab2134b0cedb2199685aab0ca8cea649cb;hpb=440370de3fc66d5bb9754a55fa78ccce8c598f5d diff --git a/resources/libraries/python/DUTSetup.py b/resources/libraries/python/DUTSetup.py index 6b2f5edb83..bccf108524 100644 --- a/resources/libraries/python/DUTSetup.py +++ b/resources/libraries/python/DUTSetup.py @@ -15,7 +15,7 @@ from robot.api import logger -from resources.libraries.python.topology import NodeType +from resources.libraries.python.topology import NodeType, Topology from resources.libraries.python.ssh import SSH from resources.libraries.python.constants import Constants from resources.libraries.python.VatExecutor import VatExecutor @@ -48,6 +48,17 @@ class DUTSetup(object): vat = VatExecutor() vat.execute_script("show_version_verbose.vat", node, json_out=False) + @staticmethod + def show_vpp_version_on_all_duts(nodes): + """Show VPP version verbose on all DUTs. + + :param nodes: VPP nodes + :type nodes: dict + """ + for node in nodes.values(): + if node['type'] == NodeType.DUT: + DUTSetup.vpp_show_version_verbose(node) + @staticmethod def vpp_api_trace_save(node): """Run "api trace save" CLI command. @@ -88,8 +99,9 @@ class DUTSetup(object): ssh.connect(node) (ret_code, stdout, stderr) = \ - ssh.exec_command('sudo -Sn bash {0}/{1}/dut_setup.sh'.format( - Constants.REMOTE_FW_DIR, Constants.RESOURCES_LIB_SH), timeout=120) + ssh.exec_command('sudo -Sn bash {0}/{1}/dut_setup.sh'. + format(Constants.REMOTE_FW_DIR, + Constants.RESOURCES_LIB_SH), timeout=120) logger.trace(stdout) logger.trace(stderr) if int(ret_code) != 0: @@ -104,28 +116,38 @@ class DUTSetup(object): :param node: DUT node. :type node: dict - :return: PID + :returns: PID :rtype: int :raises RuntimeError if it is not possible to get the PID. """ ssh = SSH() ssh.connect(node) - ret_code, stdout, stderr = ssh.exec_command('pidof vpp') - logger.trace(stdout) - logger.trace(stderr) + for i in range(3): + logger.trace('Try {}: Get VPP PID'.format(i)) + ret_code, stdout, stderr = ssh.exec_command('pidof vpp') - if int(ret_code) != 0: - logger.debug('Not possible to get PID of VPP process on node: ' - '"{1}"'.format(node['host'], stdout + stderr)) - raise RuntimeError('Not possible to get PID of VPP process on node:' - ' {}'.format(node['host'])) + if int(ret_code) != 0: + raise RuntimeError('Not possible to get PID of VPP process ' + 'on node: {0}\n {1}'. + format(node['host'], stdout + stderr)) + + if len(stdout.splitlines()) == 1: + return int(stdout) + elif len(stdout.splitlines()) == 0: + logger.debug("No VPP PID found on node {0}". + format(node['host'])) + continue + else: + logger.debug("More then one VPP PID found on node {0}". + format(node['host'])) + ret_list = list() + for line in stdout.splitlines(): + ret_list.append(int(line)) + return ret_list - if len(stdout.splitlines()) != 1: - raise RuntimeError("More then one VPP PID found on node {0}". - format(node['host'])) - return int(stdout) + return None @staticmethod def get_vpp_pids(nodes): @@ -133,7 +155,7 @@ class DUTSetup(object): :param nodes: DUT nodes. :type nodes: dict - :return: PIDs + :returns: PIDs :rtype: dict """ @@ -142,3 +164,187 @@ class DUTSetup(object): if node['type'] == NodeType.DUT: pids[node['host']] = DUTSetup.get_vpp_pid(node) return pids + + @staticmethod + def vpp_show_crypto_device_mapping(node): + """Run "show crypto device mapping" CLI command. + + :param node: Node to run command on. + :type node: dict + """ + vat = VatExecutor() + vat.execute_script("show_crypto_device_mapping.vat", node, + json_out=False) + + @staticmethod + def crypto_device_verify(node, force_init=False, numvfs=32): + """Verify if Crypto QAT device virtual functions are initialized on all + DUTs. If parameter force initialization is set to True, then try to + initialize or disable QAT. + + :param node: DUT node. + :param force_init: If True then try to initialize to specific value. + :param numvfs: Number of VFs to initialize, 0 - disable the VFs. + :type node: dict + :type force_init: bool + :type numvfs: int + :returns: nothing + :raises RuntimeError: If QAT is not initialized or failed to initialize. + """ + + ssh = SSH() + ssh.connect(node) + + cryptodev = Topology.get_cryptodev(node) + cmd = 'cat /sys/bus/pci/devices/{}/sriov_numvfs'.\ + format(cryptodev.replace(':', r'\:')) + + # Try to read number of VFs from PCI address of QAT device + for _ in range(3): + ret_code, stdout, _ = ssh.exec_command(cmd) + if int(ret_code) == 0: + try: + sriov_numvfs = int(stdout) + except ValueError: + logger.trace('Reading sriov_numvfs info failed on: {}'. + format(node['host'])) + else: + if sriov_numvfs != numvfs: + if force_init: + # QAT is not initialized and we want to initialize + # with numvfs + DUTSetup.crypto_device_init(node, numvfs) + else: + raise RuntimeError('QAT device {} is not ' + 'initialized to {} on host: {}'. + format(cryptodev, numvfs, + node['host'])) + break + + @staticmethod + def crypto_device_init(node, numvfs): + """Init Crypto QAT device virtual functions on DUT. + + :param node: DUT node. + :param numvfs: Number of VFs to initialize, 0 - disable the VFs. + :type node: dict + :type numvfs: int + :returns: nothing + :raises RuntimeError: If QAT failed to initialize. + """ + + ssh = SSH() + ssh.connect(node) + + cryptodev = Topology.get_cryptodev(node) + + # QAT device must be bind to kernel driver before initialization + DUTSetup.pci_driver_unbind(node, cryptodev) + DUTSetup.pci_driver_bind(node, cryptodev, "dh895xcc") + + # Initialize QAT VFs + ret_code, _, _ = ssh.exec_command( + "sudo sh -c 'echo {} | tee /sys/bus/pci/devices/{}/sriov_numvfs'" + .format(numvfs, cryptodev.replace(':', r'\:'))) + + if int(ret_code) != 0: + raise RuntimeError('Failed to initialize {} VFs on QAT device on ' + 'host: {}'.format(numvfs, node['host'])) + + @staticmethod + def pci_driver_unbind(node, pci_addr): + """Unbind PCI device from current driver on node. + + :param node: DUT node. + :param pci_addr: PCI device address. + :type node: dict + :type pci_addr: str + :returns: nothing + :raises RuntimeError: If PCI device unbind failed. + """ + + ssh = SSH() + ssh.connect(node) + + ret_code, _, _ = ssh.exec_command( + "sudo sh -c 'echo {} | tee /sys/bus/pci/devices/{}/driver/unbind'" + .format(pci_addr, pci_addr.replace(':', r'\:'))) + + if int(ret_code) != 0: + raise RuntimeError('Failed to unbind PCI device from driver on ' + 'host: {}'.format(node['host'])) + + @staticmethod + def pci_driver_bind(node, pci_addr, driver): + """Bind PCI device to driver on node. + + :param node: DUT node. + :param pci_addr: PCI device address. + :param driver: Driver to bind. + :type node: dict + :type pci_addr: str + :type driver: str + :returns: nothing + :raises RuntimeError: If PCI device bind failed. + """ + + ssh = SSH() + ssh.connect(node) + + ret_code, _, _ = ssh.exec_command( + "sudo sh -c 'echo {} | tee /sys/bus/pci/drivers/{}/bind'" + .format(pci_addr, driver)) + + if int(ret_code) != 0: + raise RuntimeError('Failed to bind PCI device to {} driver on ' + 'host: {}'.format(driver, node['host'])) + + @staticmethod + def kernel_module_verify(node, module, force_load=False): + """Verify if kernel module is loaded on all DUTs. If parameter force + load is set to True, then try to load the modules. + + :param node: DUT node. + :param module: Module to verify. + :param force_load: If True then try to load module. + :type node: dict + :type module: str + :type force_init: bool + :returns: nothing + :raises RuntimeError: If module is not loaded or failed to load. + """ + + ssh = SSH() + ssh.connect(node) + + cmd = 'grep -w {} /proc/modules'.format(module) + ret_code, _, _ = ssh.exec_command(cmd) + + if int(ret_code) != 0: + if force_load: + # Module is not loaded and we want to load it + DUTSetup.kernel_module_load(node, module) + else: + raise RuntimeError('Kernel module {} is not loaded on host: {}'. + format(module, node['host'])) + + @staticmethod + def kernel_module_load(node, module): + """Load kernel module on node. + + :param node: DUT node. + :param module: Module to load. + :type node: dict + :type module: str + :returns: nothing + :raises RuntimeError: If loading failed. + """ + + ssh = SSH() + ssh.connect(node) + + ret_code, _, _ = ssh.exec_command_sudo("modprobe {}".format(module)) + + if int(ret_code) != 0: + raise RuntimeError('Failed to load {} kernel module on host: {}'. + format(module, node['host']))