Skip to content

[Workload]: network (multi-protocol variant) #169

Description

@mrhillsman

Workload Name

network (multi-protocol enhancement)

Workload Description

An enhancement to the existing network workload that extends beyond TCP-only iperf3 to generate a configurable mix of TCP, UDP, and (on supported CNIs) SCTP traffic between server and client VMs. Produces sustained multi-protocol throughput signals — TCP bandwidth, UDP jitter and packet loss, and SCTP association throughput — exercising protocol-specific code paths in the CNI, SDN, and network policy stack.

The existing network workload runs iperf3 in TCP mode exclusively. This covers the most common case, but network partners need to validate all three transport protocols because each follows a different kernel and CNI code path:

  • TCP: connection-oriented, flow-controlled — exercises the CNI's conntrack, NAT, and Service proxy path
  • UDP: connectionless, no flow control — exercises the CNI's stateless forwarding, reveals packet loss under load, and is the transport for DNS, VoIP, and media streaming
  • SCTP: multi-stream, message-oriented — used in telco signaling (Diameter, S1AP, NGAP) and is the protocol most likely to be broken by CNI misconfigurations or missing kernel modules

This is not a new workload type — it's a parameterized extension of the existing network workload. The VM pair (server/client) pattern stays the same; the protocol and traffic profile become configurable.

Tooling and Packages

TCP (existing behavior):

  • Tool: iperf3 (already implemented)
  • systemd service: existing virtwork-network.service

UDP:

  • Tool: iperf3 -u (UDP mode)
  • Additional flags: -b 100M (target bandwidth — UDP has no flow control, so a target is required), --length 1400 (packet size)
  • Key metrics: throughput, jitter, packet loss percentage

SCTP:

  • Tool: iperf3 (supports SCTP via --sctp flag on builds compiled with SCTP support) or ncat --sctp (from nmap-ncat) for basic SCTP connectivity
  • RPM packages: lksctp-tools (SCTP kernel module and userspace libraries), nmap-ncat (if using ncat fallback)
  • Key metrics: association establishment, multi-stream throughput

Multi-protocol runner:

  • A wrapper script that cycles through configured protocols, running each for a configurable duration before switching
  • Configurable parameters:
    • network-protocols: comma-separated list (default: tcp — backwards compatible)
    • network-udp-bandwidth: target UDP bandwidth (default: 100M)
    • network-udp-packet-size: UDP packet size in bytes (default: 1400)
    • network-sctp-streams: number of SCTP streams (default: 4)
    • network-protocol-duration: seconds per protocol before rotating (default: 300)

VM Count Model

VM pair - server and client (like network)

Same as existing network workload — MultiVMWorkload with RoleDistribution() []RoleSpec returning server and client roles.

Required Resources

  • Persistent storage (DataVolume)
  • Kubernetes Service (for inter-VM communication)
  • Kubernetes Secret (for credentials or config)
  • Additional CPU/memory beyond defaults
  • GPU or special device passthrough

The Kubernetes Service needs additional port entries for UDP and SCTP. The existing Service exposes TCP port 5201 (iperf3 default). For multi-protocol support:

ports:
  - name: iperf3-tcp
    port: 5201
    protocol: TCP
  - name: iperf3-udp
    port: 5201
    protocol: UDP
  - name: iperf3-sctp
    port: 5201
    protocol: SCTP

Cloud-Init Details

Server VM:

packages:
  - iperf3
  - lksctp-tools
  - nmap-ncat
runcmd:
  # iperf3 server listens on all protocols on the same port
  - systemctl enable --now virtwork-network.service

The existing iperf3 server already listens for TCP connections. For UDP, iperf3 handles UDP traffic on the same port when the client sends UDP packets. For SCTP, iperf3 must be compiled with --enable-sctp or a separate SCTP listener is needed.

Client VM:

packages:
  - iperf3
  - lksctp-tools
  - nmap-ncat
write_files:
  - path: /usr/local/bin/virtwork-network-multiproto.sh
    permissions: '0755'
    content: |
      #!/bin/bash
      set -euo pipefail
      SERVER="${NETWORK_SERVER:-<server-service>}"
      PROTOCOLS="${NETWORK_PROTOCOLS:-tcp}"
      PROTO_DURATION="${NETWORK_PROTOCOL_DURATION:-300}"
      UDP_BW="${NETWORK_UDP_BANDWIDTH:-100M}"
      UDP_LEN="${NETWORK_UDP_PACKET_SIZE:-1400}"
      SCTP_STREAMS="${NETWORK_SCTP_STREAMS:-4}"

      IFS=',' read -ra PROTO_LIST <<< "$PROTOCOLS"

      while true; do
        for proto in "${PROTO_LIST[@]}"; do
          echo "$(date -Iseconds) === Starting $proto test for ${PROTO_DURATION}s ==="
          case "$proto" in
            tcp)
              iperf3 -c "$SERVER" -t "$PROTO_DURATION" -P 4 --forceflush
              ;;
            udp)
              iperf3 -c "$SERVER" -t "$PROTO_DURATION" -u -b "$UDP_BW" \
                --length "$UDP_LEN" -P 4 --forceflush
              ;;
            sctp)
              if iperf3 --help 2>&1 | grep -q sctp; then
                iperf3 -c "$SERVER" -t "$PROTO_DURATION" --sctp \
                  --nstreams "$SCTP_STREAMS" --forceflush
              else
                echo "iperf3 SCTP not supported, falling back to ncat SCTP test"
                timeout "$PROTO_DURATION" bash -c "
                  while true; do
                    dd if=/dev/urandom bs=1024 count=1 2>/dev/null | \
                      ncat --sctp $SERVER 5201
                    sleep 0.1
                  done" || true
              fi
              ;;
            *)
              echo "Unknown protocol: $proto, skipping"
              ;;
          esac
          echo "$(date -Iseconds) === Completed $proto test ==="
        done
      done
  - path: /etc/systemd/system/virtwork-network-multiproto.service
    content: |
      [Unit]
      Description=Virtwork multi-protocol network workload
      After=network-online.target
      Wants=network-online.target
      [Service]
      Type=simple
      Environment=NETWORK_SERVER=<server-service>
      Environment=NETWORK_PROTOCOLS=tcp
      Environment=NETWORK_PROTOCOL_DURATION=300
      Environment=NETWORK_UDP_BANDWIDTH=100M
      ExecStart=/usr/local/bin/virtwork-network-multiproto.sh
      Restart=always
      RestartSec=5
      [Install]
      WantedBy=multi-user.target
runcmd:
  - systemctl enable --now virtwork-network-multiproto.service

Use Case

  • Network / CNI partners (Tigera/Calico, Cilium, Juniper, VMware NSX): The primary audience. Each transport protocol exercises a different code path in the CNI data plane. TCP goes through conntrack and NAT tables. UDP bypasses flow control and reveals forwarding-plane packet loss. SCTP requires kernel module support (sctp.ko) and specific conntrack helpers that many CNIs don't test with VM traffic. A partner that only validates TCP cannot claim full protocol coverage.
  • OVN-Kubernetes validation: OVN-Kubernetes is OpenShift's default CNI. UDP and SCTP flows through OVN follow different OVS (Open vSwitch) pipelines than TCP. UDP kernel bypass (XDP/AF_XDP) and SCTP association tracking are known areas where KubeVirt VM traffic differs from pod traffic. Multi-protocol testing surfaces these differences.
  • Network policy partners: NetworkPolicy and AdminNetworkPolicy resources can match on protocol (TCP, UDP, SCTP). Partners building network policy management tools need multi-protocol traffic to validate that their policies correctly allow/deny by protocol. A TCP-only workload can't test a "deny all UDP" rule.
  • Telco partners (5G core, IMS, signaling): SCTP is the transport protocol for telco signaling — Diameter, S1AP (LTE), NGAP (5G NR). Telco VNFs running in KubeVirt VMs use SCTP for control-plane communication between network functions. Telco partners need SCTP traffic between VMs to validate that their CNI (often with Multus + secondary networks) correctly handles SCTP associations, multi-homing, and failover.
  • Load balancer / Service mesh partners: L4 load balancers must handle all three protocols. Many Service mesh implementations (Istio, Linkerd) have limited or no SCTP support — this workload surfaces that gap explicitly rather than discovering it in production.
  • QoS / traffic shaping partners: Different protocols respond differently to traffic shaping. TCP backs off under congestion (flow control). UDP doesn't — it keeps sending and packets drop. SCTP has its own congestion control distinct from TCP. Partners implementing QoS features need all three protocols to validate their traffic shaping behavior.

Additional Context

  • Backwards compatibility: The default network-protocols=tcp preserves the existing behavior. Users who don't set the flag get identical behavior to the current network workload. Multi-protocol is opt-in.
  • Implementation approach: This can be implemented as either:
    1. Enhancement to existing network workload: Add network-protocols config parameter. The UserdataForRole method generates different cloud-init based on configured protocols. Minimal code duplication.
    2. Separate network-multiproto workload: Cleaner separation but duplicates the server/client VM pattern.
      Option 1 is recommended — it follows the principle that workload variants should be configuration, not new types.
  • SCTP kernel module: SCTP requires modprobe sctp and the lksctp-tools package. On most Fedora/RHEL images, the kernel module is available but not loaded by default. The cloud-init should load it explicitly. On some hardened images, SCTP may be blacklisted — the fallback to ncat handles this gracefully.
  • UDP packet loss measurement: iperf3's UDP mode reports packet loss percentage — this is a critical metric for network partners. At 100M target bandwidth, packet loss on a properly configured cluster should be <0.01%. Any measurable loss indicates a CNI forwarding issue, buffer sizing problem, or QoS misconfiguration.
  • Service definition: The Kubernetes Service needs protocol: UDP and protocol: SCTP port entries. Kubernetes Services support all three protocols, but some CNIs have incomplete SCTP Service support. If SCTP Service proxying fails, the workload should log the error clearly — this itself is a useful finding for the partner.
  • Composability: Multi-protocol network pairs naturally with:
    • chaos-network — inject latency/loss specifically on UDP or SCTP flows
    • dns-stress — DNS is UDP; running both validates UDP forwarding under load
    • chaos-migration — validate that multi-protocol connections survive live migration

Metadata

Metadata

Assignees

No one assigned

    Labels

    good first issueDenotes an issue ready for a new contributor, according to the "help wanted" guidelines.needs-triageIndicates an issue or PR lacks a `triage/foo` label and requires one.size/LDenotes a PR that changes 100-499 lines, ignoring generated files.workload-requestRequest for a new workload typeworkload/variantEnhancement or extension of an existing workload type.

    Type

    No type

    Fields

    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions