UTI: Export results
[csit.git] / resources / libraries / python / DPDK / DPDKTools.py
1 # Copyright (c) 2021 Cisco and/or its affiliates.
2 # Licensed under the Apache License, Version 2.0 (the "License");
3 # you may not use this file except in compliance with the License.
4 # You may obtain a copy of the License at:
5 #
6 #     http://www.apache.org/licenses/LICENSE-2.0
7 #
8 # Unless required by applicable law or agreed to in writing, software
9 # distributed under the License is distributed on an "AS IS" BASIS,
10 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
11 # See the License for the specific language governing permissions and
12 # limitations under the License.
13
14
15 """This module implements initialization and cleanup of DPDK framework."""
16
17 from robot.api import logger
18
19 from resources.libraries.python.Constants import Constants
20 from resources.libraries.python.ssh import exec_cmd_no_error
21 from resources.libraries.python.topology import NodeType, Topology
22
23
24 class DPDKTools:
25     """This class implements:
26     - Initialization of DPDK environment,
27     - Cleanup of DPDK environment.
28     """
29
30     @staticmethod
31     def initialize_dpdk_framework(node, if1, if2, nic_driver):
32         """
33         Initialize the DPDK framework on the DUT node. Bind interfaces to
34         driver.
35
36         :param node: DUT node.
37         :param if1: DUT first interface name.
38         :param if2: DUT second interface name.
39         :param nic_driver: Interface driver.
40         :type node: dict
41         :type if1: str
42         :type if2: str
43         :type nic_driver: str
44         :raises RuntimeError: If it fails to bind the interfaces to driver.
45         """
46         if node[u"type"] == NodeType.DUT:
47             pci_address1 = Topology.get_interface_pci_addr(node, if1)
48             pci_address2 = Topology.get_interface_pci_addr(node, if2)
49
50             command = f"{Constants.REMOTE_FW_DIR}/{Constants.RESOURCES_LIB_SH}"\
51                 f"/entry/init_dpdk.sh " \
52                 f"{nic_driver} {pci_address1} {pci_address2}"
53             message = u"Initialize the DPDK failed!"
54             exec_cmd_no_error(node, command, timeout=600, message=message)
55
56     @staticmethod
57     def cleanup_dpdk_framework(node, if1, if2):
58         """
59         Cleanup the DPDK framework on the DUT node. Bind interfaces to
60         default driver specified in topology.
61
62         :param node: Will cleanup the DPDK on this node.
63         :param if1: DUT first interface name.
64         :param if2: DUT second interface name.
65         :type node: dict
66         :type if1: str
67         :type if2: str
68         :raises RuntimeError: If it fails to cleanup the dpdk.
69         """
70         if node[u"type"] == NodeType.DUT:
71             pci_address1 = Topology.get_interface_pci_addr(node, if1)
72             pci_address2 = Topology.get_interface_pci_addr(node, if2)
73             # We are not supporting more than one driver yet.
74             nic_driver = Topology.get_interface_driver(node, if1)
75
76             command = f"{Constants.REMOTE_FW_DIR}/{Constants.RESOURCES_LIB_SH}"\
77                 f"/entry/cleanup_dpdk.sh " \
78                 f"{nic_driver} {pci_address1} {pci_address2}"
79             message = u"Cleanup the DPDK failed!"
80             exec_cmd_no_error(node, command, timeout=1200, message=message)
81
82     @staticmethod
83     def get_dpdk_version(node):
84         """Log and return the installed DPDK version.
85
86         The logged string ends with newline, the returned one is stripped.
87
88         :param node: Node from topology file.
89         :type node: dict
90         :returns: Stripped DPDK version string.
91         :rtype: str
92         :raises RuntimeError: If command returns nonzero return code.
93         """
94         command = f"cat {Constants.REMOTE_FW_DIR}/dpdk*/VERSION"
95         message = u"Get DPDK version failed!"
96         stdout, _ = exec_cmd_no_error(node, command, message=message)
97         # TODO: PAL should already tolerate stripped value in the log.
98         logger.info(f"DPDK Version: {stdout}")
99         return stdout.strip()
100
101     @staticmethod
102     def install_dpdk_framework(node):
103         """
104         Prepare the DPDK framework on the DUT node.
105
106         :param node: Node from topology file.
107         :type node: dict
108         :raises RuntimeError: If command returns nonzero return code.
109         """
110         command = f"{Constants.REMOTE_FW_DIR}/{Constants.RESOURCES_LIB_SH}" \
111             f"/entry/install_dpdk.sh"
112         message = u"Install the DPDK failed!"
113         exec_cmd_no_error(node, command, timeout=3600, message=message)
114         DPDKTools.get_dpdk_version(node)
115
116     @staticmethod
117     def install_dpdk_framework_on_all_duts(nodes):
118         """
119         Prepare the DPDK framework on all DUTs.
120
121         :param nodes: Nodes from topology file.
122         :type nodes: dict
123         """
124         for node in list(nodes.values()):
125             if node[u"type"] == NodeType.DUT:
126                 DPDKTools.install_dpdk_framework(node)