Perpatch: Fix bash ansible calls
[csit.git] / resources / libraries / python / HoststackUtil.py
index 9e6e200..dde5cf6 100644 (file)
@@ -15,6 +15,7 @@
 from time import sleep
 from robot.api import logger
 
+from resources.libraries.python.Constants import Constants
 from resources.libraries.python.ssh import exec_cmd, exec_cmd_no_error
 from resources.libraries.python.PapiExecutor import PapiSocketExecutor
 from resources.libraries.python.DUTSetup import DUTSetup
@@ -43,6 +44,8 @@ class HoststackUtil():
             f"socket-name {vpp_echo_attributes[u'vpp_api_socket']} " \
             f"{vpp_echo_attributes[u'json_output']} " \
             f"uri {proto}://{addr}/{port} " \
+            f"nthreads {vpp_echo_attributes[u'nthreads']} " \
+            f"mq-size {vpp_echo_attributes[u'mq_size']} " \
             f"nclients {vpp_echo_attributes[u'nclients']} " \
             f"quic-streams {vpp_echo_attributes[u'quic_streams']} " \
             f"time {vpp_echo_attributes[u'time']} " \
@@ -55,6 +58,49 @@ class HoststackUtil():
             vpp_echo_cmd[u"args"] += u" tx-results-diff"
         return vpp_echo_cmd
 
+    @staticmethod
+    def get_iperf3_command(iperf3_attributes):
+        """Construct the iperf3 command using the specified attributes.
+
+        :param iperf3_attributes: iperf3 test program attributes.
+        :type iperf3_attributes: dict
+        :returns: Command line components of the iperf3 command
+            'env_vars' - environment variables
+            'name' - program name
+            'args' - command arguments.
+        :rtype: dict
+        """
+        # TODO: Use a python class instead of dictionary for the return type
+        iperf3_cmd = {}
+        iperf3_cmd[u"env_vars"] = f"VCL_CONFIG={Constants.REMOTE_FW_DIR}/" \
+            f"{Constants.RESOURCES_TPL_VCL}/" \
+            f"{iperf3_attributes[u'vcl_config']}"
+        if iperf3_attributes[u"ld_preload"]:
+            iperf3_cmd[u"env_vars"] += \
+                f" LD_PRELOAD={Constants.VCL_LDPRELOAD_LIBRARY}"
+        if iperf3_attributes[u'transparent_tls']:
+            iperf3_cmd[u"env_vars"] += u" LDP_ENV_TLS_TRANS=1"
+
+        json_results = u" --json" if iperf3_attributes[u'json'] else u""
+        ip_address = f" {iperf3_attributes[u'ip_address']}" if u"ip_address" \
+                     in iperf3_attributes else u""
+        iperf3_cmd[u"name"] = u"iperf3"
+        iperf3_cmd[u"args"] = f"--{iperf3_attributes[u'role']}{ip_address} " \
+                              f"--interval 0{json_results} " \
+                              f"--version{iperf3_attributes[u'ip_version']}"
+
+        if iperf3_attributes[u"role"] == u"server":
+            iperf3_cmd[u"args"] += u" --one-off"
+        else:
+            iperf3_cmd[u"args"] += u" --get-server-output"
+            if u"parallel" in iperf3_attributes:
+                iperf3_cmd[u"args"] += \
+                    f" --parallel {iperf3_attributes[u'parallel']}"
+            if u"time" in iperf3_attributes:
+                iperf3_cmd[u"args"] += \
+                    f" --time {iperf3_attributes[u'time']}"
+        return iperf3_cmd
+
     @staticmethod
     def set_hoststack_quic_fifo_size(node, fifo_size):
         """Set the QUIC protocol fifo size.
@@ -77,7 +123,7 @@ class HoststackUtil():
         :type node: dict
         :type quic_crypto_engine: str
         """
-        vpp_crypto_engines = {u"openssl", u"ia32", u"ipsecmb"}
+        vpp_crypto_engines = {u"openssl", u"native", u"ipsecmb"}
         if quic_crypto_engine == u"nocrypto":
             logger.trace(u"No QUIC crypto engine.")
             return
@@ -118,20 +164,22 @@ class HoststackUtil():
         return stdout_log, stderr_log
 
     @staticmethod
-    def start_hoststack_test_program(node, namespace, program):
+    def start_hoststack_test_program(node, namespace, core_list, program):
         """Start the specified HostStack test program.
 
         :param node: DUT node.
         :param namespace: Net Namespace to run program in.
+        :param core_list: List of cpu's to pass to taskset to pin the test
+            program to a different set of cores on the same numa node as VPP.
         :param program: Test program.
         :type node: dict
         :type namespace: str
+        :type core_list: str
         :type program: dict
         :returns: Process ID
         :rtype: int
         :raises RuntimeError: If node subtype is not a DUT or startup failed.
         """
-        # TODO: Pin test program to core(s) on same numa node as VPP.
         if node[u"type"] != u"DUT":
             raise RuntimeError(u"Node type is not a DUT!")
 
@@ -145,8 +193,8 @@ class HoststackUtil():
 
         env_vars = f"{program[u'env_vars']} " if u"env_vars" in program else u""
         args = program[u"args"]
-        cmd = f"nohup {shell_cmd} \'{env_vars}{program_name} {args} " \
-            f">/tmp/{program_name}_stdout.log " \
+        cmd = f"nohup {shell_cmd} \'{env_vars}taskset --cpu-list {core_list} " \
+            f"{program_name} {args} >/tmp/{program_name}_stdout.log " \
             f"2>/tmp/{program_name}_stderr.log &\'"
         try:
             exec_cmd_no_error(node, cmd, sudo=True)
@@ -253,10 +301,20 @@ class HoststackUtil():
             raise RuntimeError(test_results)
         if program_stdout:
             bad_test_results = False
-            if program == u"vpp_echo" and u"JSON stats" not in program_stdout:
-                test_results += u"Invalid test data output!\n"
-                bad_test_results = True
-            test_results += program_stdout
+            if program[u"name"] == u"vpp_echo":
+                if u"JSON stats" in program_stdout:
+                    test_results += program_stdout
+                    # TODO: Decode vpp_echo output when JSON format is correct.
+                    # json_start = program_stdout.find(u"{")
+                    # vpp_echo_results = json.loads(program_stdout[json_start:])
+                    if u'"has_failed": "0"' not in program_stdout:
+                        bad_test_results = True
+                else:
+                    test_results += u"Invalid test data output!\n" + \
+                                    program_stdout
+                    bad_test_results = True
+            else:
+                test_results += program_stdout
             if bad_test_results:
                 raise RuntimeError(test_results)
         else: