Imported from perftool-incubator/bench-trafficgen (
AGENTS.md). Install upstream withnpx skills add perftool-incubator/bench-trafficgen. Copyright stays with the author.
Bench-trafficgen
Purpose
Scripts and configuration to run traffic generation benchmarks within the crucible framework. Uses TRex and testpmd with binary search optimization for:
- Finding maximum packet forwarding throughput at a given loss rate (STL/stateless mode)
- Finding maximum connection rate (CPS) for stateful DUT validation (ASTF mode)
Languages
- Bash: wrapper scripts (trafficgen-base, trafficgen-client, trafficgen-server-start/stop, trafficgen-infra, trafficgen-import-files)
- Python: core implementation in
trafficgen/subdirectory (binary-search.py, tg_lib.py, trex-txrx.py, trex-astf.py, etc.) andtrafficgen-post-process.py
Key Files
| File | Purpose |
|---|---|
rickshaw.json |
Rickshaw integration: client/server/infra scripts, parameter transformations |
multiplex.json |
Parameter validation, presets (including ASTF NFV presets), and device/protocol options |
benchmark-metadata.json |
Machine-readable description and CDM-indexed source/type list (consumed by crucible benchmarks list) |
trafficgen-client |
Runs binary-search.py with DPDK device resolution; strips infra params from passthru |
trafficgen-server-start/stop |
Manages server DUT: testpmd (L2), grout (L3), or null (passthrough) |
trafficgen-infra |
Launches TRex service; adds --astf flag when traffic-generator=trex-astf |
trafficgen-post-process.py |
Parses test JSON into CDM-compliant metrics (STL and ASTF) |
trafficgen/binary-search.py |
Core binary search algorithm; supports STL and ASTF backends |
trafficgen/tg_lib.py |
Generic traffic generator utilities |
trafficgen/trex_tg_lib.py |
TRex STL (stateless) packet builders and helpers |
trafficgen/trex_astf_lib.py |
TRex ASTF shared helpers: profile builders, stats extraction, ramp-up stabilization |
trafficgen/trex-astf.py |
ASTF trial runner: ASTFClient subprocess with TCP/UDP/mixed support, VLAN, IPv6 |
trafficgen/trex-astf-query.py |
Port info query for ASTF-mode TRex (STLClient cannot connect to ASTF server) |
trafficgen/astf-profiles/ |
NFV scenario profiles: short-lived-tcp, long-lived-tcp, short-lived-udp, mixed-tcp-udp, http-like-tcp, vlan-tcp |
trafficgen/README-trex-astf.md |
Complete ASTF user guide |
trafficgen/install-grout.sh |
Grout installer: bundled RPM fallback + GitHub download for version override |
trafficgen/grout/grout.x86_64.rpm |
Bundled Grout RPM (v0.16.0) for offline installation |
trafficgen/grout-stats-collector.sh |
Periodic Grout stats poller: hardware (per-port) + software (per-node) CSV output |
trafficgen/ptp-latency.c |
HW timestamped latency measurement using kernel SO_TIMESTAMPING |
trafficgen/build-ptp-latency.sh |
Compiles ptp-latency.c inside the engine container image |
client-workshop-01-trex.json |
Client engine image build stage 1: TRex, DPDK, and dependencies (alma9 userenv) |
client-workshop-02-ptp-latency.json |
Client engine image build stage 2: ptp-latency compilation and posix_ipc |
server-workshop.json |
Server engine image build: testpmd and dependencies, Grout (alma9/alma10 userenvs) |
Conventions
- Primary branch is
main - Modular design: wrapper scripts at root, core implementation in
trafficgen/ - TRex v3.08 (STL) / v3.04 (ASTF) on alma9 userenv; version auto-selected by
trafficgen-infrabased on--traffic-generator - Supports TRex STL, TRex ASTF, and testpmd traffic generators
- STL traffic profiles: JSON files in
trafficgen/trex-profiles/(validated againsttraffic-profile-schema.json) - ASTF traffic profiles: Python
.pyfiles intrafficgen/astf-profiles/(NOT validated by JSON schema) - TRex version is mode-based: STL backends use v3.08, ASTF uses v3.04. Both are pre-installed in the engine image (
client-workshop.json). Version constants (TREX_VER_STL,TREX_VER_ASTF) live intrafficgen-infra; runtime switches the/opt/trex/currentsymlink only - Mellanox NICs require
trex-software-mode=onandtrex-mellanox-support=onfor performance (enables multi-queue RX via RSS instead of single-queue hardware filter mode) - Default Grout version is configured in
trafficgen/install-grout.sh(v0.16.0); the bundled RPM attrafficgen/grout/grout.x86_64.rpmis installed offline at image build time; a different version can be requested at runtime via the--grout-versionrunfile parameter (triggers a GitHub download only when the requested version differs from bundled) - Server
switch-typecontrols the DUT:testpmd(L2 forwarding),grout(L3 IPv4/IPv6 forwarding via Grout DPDK router), ornull(no DUT) - Grout parameters use
--grout-*prefix:--grout-ip-addrs,--grout-routes,--grout-forward-mode,--grout-rxqs,--grout-qsize,--grout-datapath-cpus,--grout-control-cpus,--grout-static-arp,--grout-version - Grout integration is purely server-side; all three TRex backends (trex-txrx, trex-txrx-profile, trex-astf) work with Grout unmodified
- Grout CPU affinity (
affinity cpus set) is ONLY applied when--grout-datapath-cpusis explicitly set; automatic fallback to WORKLOAD_CPUS is intentionally avoided to prevent graph restarts - Auto MAC/IP collection: When
--grout-static-arpis omitted from the runfile,trafficgen-server-startauto-generates nexthop entries from the TRex infra message (MACs + IPs sent bytrafficgen-infra). Similarly,trafficgen-clientauto-collects Grout's port MACs from the server message and overrides any manually-specified--dst-macs. This eliminates the need for manual MAC/IP configuration in most Grout runfiles. The--src-ipsparam (client-role) is embedded in the infra message so the server knows which IPs to pair with each TRex MAC for nexthop entries. If--src-ipsis not set, IPs are derived from the Grout subnet (host part replaced with.100). Manual--grout-static-arpand--dst-macsin the runfile still work as overrides.
Known Issues (Grout Integration)
| Issue | Impact | Workaround |
|---|---|---|
| DPDK/grout#545: ARP doesn't work on hardware PF ports (i40e, ice) | Dynamic ARP resolution fails; nexthop stays unresolved | Auto-generated from infra message; use --grout-static-arp to override |
affinity cpus set triggers full graph restart |
All datapath workers destroyed/recreated; can disrupt nexthop state | Don't set explicit CPU affinity unless needed; let Grout auto-detect |
| Connected routes require ARP for next-hop MAC | Even with static nexthops, fast-path activation may be delayed | Nexthops are auto-generated; ensure --src-ips is set for accurate IP-to-MAC pairing |
| Too many datapath CPUs for few RX queues | Excessive workers (e.g., 26 for 2 queues) waste resources | Match --grout-datapath-cpus count to rxqs * num_ports |
TRex Version Strategy
TRex uses mode-based version selection to work around an upstream ASTF regression on i40e NICs:
- Image contents: both v3.08 and v3.04 are installed at image build time via
client-workshop.json(twoinstall-trex.shinvocations) - STL backends (
trex-txrx,trex-txrx-profile): use v3.08 - ASTF backend (
trex-astf): use v3.04 - Version constants:
TREX_VER_STLandTREX_VER_ASTFintrafficgen-infra - No user-facing parameter: version is implicit from
--traffic-generator; no--trex-versionoverride exists - Mechanism:
trafficgen-infraswitches/opt/trex/currentsymlink to the required version before the mode/version-mismatch check; no runtime download - Reason for pinning: TRex v3.08 has a regression where ASTF DP cores do not poll server-port RX queues in
MULTI_QUEmode on i40e NICs (#130) - Removal condition: update
TREX_VER_ASTFintrafficgen-infraand remove the secondinstall-trex.shcall fromclient-workshop.jsonwhen upstream ships a fix
Grout Version Management
Grout follows the same offline-first pattern as TRex:
- Bundled RPM:
trafficgen/grout/grout.x86_64.rpmis committed to the repo and copied into the engine image at build time viaserver-workshop.json(no internet needed) - Install script:
trafficgen/install-grout.shhandles installation — compares the requested version against the bundled RPM version and installs locally if they match, or downloads from GitHub if they differ - Runtime override: Users can set
grout-version=vX.Y.Zin the runfile (validated bymultiplex.json);trafficgen-server-startcallsinstall-grout.sh --version vX.Y.Z --insecureat runtime only when the requested version differs from what is installed - Updating the bundled version: Download the new RPM to
trafficgen/grout/grout.x86_64.rpm, update the default version ininstall-grout.sh, and commit
Grout Data Collection
Grout data collection operates at two levels:
Periodic stats (during test)
trafficgen-server-start launches grout-stats-collector.sh as a background process after Grout configuration is applied and FIB has settled. Stats counters are reset (stats reset) before the collector starts so counters only reflect test traffic.
Output files:
trafficgen-grout-hw-stats.csv— per-port hardware counters (rx/tx packets, bytes, errors, drops) sampled every 5 secondstrafficgen-grout-sw-stats.csv— per-graph-node software counters (calls, packets, cycles/pkt) sampled every 5 seconds
The collector is stopped by trafficgen-server-stop before the Grout daemon is killed.
Post-test snapshot (at stop)
trafficgen-server-stop captures a comprehensive state dump to trafficgen-grout-post-test-stats.txt before killing the daemon:
stats show software— cumulative graph node cycle countsstats show hardware— cumulative per-port packet/byte countersinterface show— final interface state and MACsnexthop show— final nexthop reachability (static vs. new vs. reachable)route show— active routesgraph config show— vector/burst size configurationaffinity show— CPU-to-queue pinning
Grout L3 Testing Requirements
For functional validation with Grout as DUT:
- Server
userenv=alma10(Grout v0.16.0 requires glibc 2.38+) - Client
userenv=alma9(TRex bundled Scapy requires Python <3.12) - Set
--grout-ip-addrs(server-role) with IP/prefix per Grout port (e.g.,10.0.0.1/24,10.0.1.1/24) - Set
--src-ips(client-role) with TRex source IPs matching the Grout subnets — these are auto-forwarded to the server for nexthop generation --grout-static-arpand--dst-macsare auto-collected via rickshaw messaging and no longer need to be manually specified- Optional: set
--grout-static-arp(server-role) to override auto-generated nexthops; set--dst-macs(client-role) to override auto-collected Grout MACs - Optional: set
--grout-version(server-role) to request a specific Grout version at runtime (e.g.,v0.17.0)