From c3ce59c652caaee06b3090f387f8826c15102703 Mon Sep 17 00:00:00 2001 From: pmikus Date: Thu, 5 Oct 2023 12:27:08 +0000 Subject: feat(trex): Multilink Signed-off-by: Peter Mikus Change-Id: I36c5d175a34555ad9ce88d69a824f366b54dbc81 --- resources/libraries/python/Constants.py | 39 ++++++++++++++--------- resources/libraries/python/CpuUtils.py | 11 ++++--- resources/libraries/python/TRexConfigGenerator.py | 30 ++++++++++++----- resources/libraries/python/TrafficGenerator.py | 4 +-- 4 files changed, 54 insertions(+), 30 deletions(-) diff --git a/resources/libraries/python/Constants.py b/resources/libraries/python/Constants.py index 93f0b22ac8..a25cd6a30e 100644 --- a/resources/libraries/python/Constants.py +++ b/resources/libraries/python/Constants.py @@ -188,37 +188,46 @@ class Constants: # Docker container arm SUT image DOCKER_SUT_IMAGE_UBUNTU_ARM = u"csit_sut-ubuntu2204:local" - # TRex install directory + # TRex install directory. TREX_INSTALL_DIR = u"/opt/trex-core-3.03" - # TRex pcap files directory + # TRex pcap files directory. TREX_PCAP_DIR = f"{TREX_INSTALL_DIR}/scripts/avl" # TRex limit memory. - TREX_LIMIT_MEMORY = get_int_from_env(u"TREX_LIMIT_MEMORY", 8192) + TREX_LIMIT_MEMORY = get_int_from_env("TREX_LIMIT_MEMORY", 8192) - # TRex number of cores - TREX_CORE_COUNT = get_int_from_env(u"TREX_CORE_COUNT", 16) + # TRex limit memory in case multiple dual interfaces configurations. + TREX_LIMIT_MEMORY_MULTI = get_int_from_env("TREX_LIMIT_MEMORY_MULTI", 16384) - # TRex set number of RX/TX descriptors - # Set to 0 to use default values + # TRex number of cores. + TREX_CORE_COUNT = get_int_from_env("TREX_CORE_COUNT", 16) + + # TRex number of cores in case multiple dual interface configurations. + TREX_CORE_COUNT_MULTI = get_int_from_env("TREX_CORE_COUNT_MULTI", 8) + + # TRex set number of RX/TX descriptors. + # Set to 0 to use default values. TREX_TX_DESCRIPTORS_COUNT = get_int_from_env( - u"TREX_TX_DESCRIPTORS_COUNT", 0 + "TREX_TX_DESCRIPTORS_COUNT", 0 ) + TREX_RX_DESCRIPTORS_COUNT = get_int_from_env( - u"TREX_RX_DESCRIPTORS_COUNT", 0 + "TREX_RX_DESCRIPTORS_COUNT", 0 ) - # Trex force start regardless ports state - TREX_SEND_FORCE = get_pessimistic_bool_from_env(u"TREX_SEND_FORCE") + # Trex force start regardless ports state. + TREX_SEND_FORCE = get_pessimistic_bool_from_env("TREX_SEND_FORCE") - # TRex extra commandline arguments + # TRex extra commandline arguments. TREX_EXTRA_CMDLINE = get_str_from_env( - u"TREX_EXTRA_CMDLINE", u"--mbuf-factor 32") + "TREX_EXTRA_CMDLINE", "--mbuf-factor 32" + ) - # TRex port driver default vfio-pci or set to igb_uio + # TRex port driver default vfio-pci or set to igb_uio. TREX_PORT_DRIVER = get_str_from_env( - u"TREX_PORT_DRIVER", u"vfio-pci") + "TREX_PORT_DRIVER", "vfio-pci" + ) # Graph node variant value GRAPH_NODE_VARIANT = get_str_from_env(u"GRAPH_NODE_VARIANT", u"") diff --git a/resources/libraries/python/CpuUtils.py b/resources/libraries/python/CpuUtils.py index 5f43e211a2..8871a5b651 100644 --- a/resources/libraries/python/CpuUtils.py +++ b/resources/libraries/python/CpuUtils.py @@ -388,7 +388,7 @@ class CpuUtils: @staticmethod def get_affinity_trex( - node, if_key, tg_mtc=1, tg_dtc=1, tg_ltc=1): + node, if_key, tg_mtc=1, tg_dtc=1, tg_ltc=1, tg_dtc_offset=0): """Get affinity for T-Rex. Result will be used to pin T-Rex threads. :param node: TG node. @@ -396,11 +396,13 @@ class CpuUtils: :param tg_mtc: TG main thread count. :param tg_dtc: TG dataplane thread count. :param tg_ltc: TG latency thread count. + :param tg_dtc_offset: TG dataplane thread offset. :type node: dict :type if_key: str :type tg_mtc: int :type tg_dtc: int :type tg_ltc: int + :type tg_dtc_offset: int :returns: List of CPUs allocated to T-Rex including numa node. :rtype: int, int, int, list """ @@ -412,12 +414,11 @@ class CpuUtils: smt_used=False) threads = CpuUtils.cpu_slice_of_list_per_node( - node, cpu_node, skip_cnt=tg_mtc, cpu_cnt=tg_dtc, - smt_used=False) + node, cpu_node, skip_cnt=tg_mtc + tg_ltc + tg_dtc_offset, + cpu_cnt=tg_dtc, smt_used=False) latency_thread_id = CpuUtils.cpu_slice_of_list_per_node( - node, cpu_node, skip_cnt=tg_mtc + tg_dtc, cpu_cnt=tg_ltc, - smt_used=False) + node, cpu_node, skip_cnt=tg_mtc, cpu_cnt=tg_ltc, smt_used=False) return master_thread_id[0], latency_thread_id[0], cpu_node, threads diff --git a/resources/libraries/python/TRexConfigGenerator.py b/resources/libraries/python/TRexConfigGenerator.py index e5ac19647f..c73e24960a 100644 --- a/resources/libraries/python/TRexConfigGenerator.py +++ b/resources/libraries/python/TRexConfigGenerator.py @@ -225,12 +225,12 @@ class TrexConfigGenerator: exec_cmd_no_error(self._node, command, message=message) -class TrexInitConfig: - """TRex Initial Configuration. +class TrexConfig: + """TRex Configuration Class. """ @staticmethod - def init_trex_startup_configuration(node, tg_topology): - """Apply initial TRex startup configuration. + def add_startup_configuration(node, tg_topology): + """Apply TRex startup configuration. :param node: TRex node in the topology. :param tg_topology: Ordered TRex links. @@ -243,16 +243,24 @@ class TrexInitConfig: master_thread_id = None latency_thread_id = None cores = None - limit_memory = f"{Constants.TREX_LIMIT_MEMORY}" sockets = list() - for link in tg_topology: + for idx, link in enumerate(tg_topology): pci_addresses.append( Topology().get_interface_pci_addr(node, link["interface"]) ) + if len(tg_topology) > 2: + # Multiple dual_ifs must not share the cores. + tg_dtc = Constants.TREX_CORE_COUNT_MULTI + tg_dtc_offset = Constants.TREX_CORE_COUNT_MULTI * (idx // 2) + else: + # Single dual_if can share cores. + tg_dtc = Constants.TREX_CORE_COUNT + tg_dtc_offset = 0 master_thread_id, latency_thread_id, socket, threads = \ CpuUtils.get_affinity_trex( - node, link["interface"], tg_dtc=Constants.TREX_CORE_COUNT + node, link["interface"], tg_dtc=tg_dtc, + tg_dtc_offset=tg_dtc_offset ) dual_if.append(dict(socket=socket, threads=threads)) cores = len(threads) @@ -265,10 +273,16 @@ class TrexInitConfig: ) ) sockets.append(socket) - if 0 in sockets and 1 in sockets: + + limit_memory = f"{Constants.TREX_LIMIT_MEMORY}" + if len(tg_topology) <= 2 and 0 in sockets and 1 in sockets: limit_memory = ( f"{Constants.TREX_LIMIT_MEMORY},{Constants.TREX_LIMIT_MEMORY}" ) + if len(tg_topology) > 2: + limit_memory = ( + f"{Constants.TREX_LIMIT_MEMORY_MULTI}" + ) trex_config = TrexConfigGenerator() trex_config.set_node(node) diff --git a/resources/libraries/python/TrafficGenerator.py b/resources/libraries/python/TrafficGenerator.py index f759f52d3a..6f4483b970 100644 --- a/resources/libraries/python/TrafficGenerator.py +++ b/resources/libraries/python/TrafficGenerator.py @@ -30,7 +30,7 @@ from .ssh import exec_cmd_no_error, exec_cmd from .topology import NodeType from .topology import NodeSubTypeTG from .topology import Topology -from .TRexConfigGenerator import TrexInitConfig +from .TRexConfigGenerator import TrexConfig from .DUTSetup import DUTSetup as DS __all__ = [u"TGDropRateSearchImpl", u"TrafficGenerator", u"OptimizedSearch"] @@ -335,7 +335,7 @@ class TrafficGenerator(AbstractMeasurer): self._ifaces_reordered = True trex_topology.reverse() - TrexInitConfig.init_trex_startup_configuration( + TrexConfig.add_startup_configuration( self._node, trex_topology ) TrafficGenerator.startup_trex( -- cgit 1.2.3-korg