# GPNC load test Synthetic traffic + verification for the L2-inline detector. Run from a host on the **subscriber side** of the GPNC bridge (e.g. Admin-PC at 10.99.98.199) — frames have to traverse `br-gpnc` for the detector to see them. ## traffic_gen.py ```bash # what's testable right now python3 traffic_gen.py --list # default — drive World of Tanks for 90s, TCP+UDP, 20pps each # (the longer duration matters: it covers ARP warm + detector trigger # + sustained flow so a real session shows up in the UI) python3 traffic_gen.py --game "World of Tanks" # UDP only at 50pps for 120s against a specific game IP python3 traffic_gen.py --game "Albion Online" --proto udp --rate 50 \ --duration 120 --ip 5.188.125.14 # stop at the traffic step (skip post-run journal grep / status diff) python3 traffic_gen.py --game "PC" --no-verify ``` The script: 1. Reads `/api/catalog` to find the game's known /32 IPs + a representative port 2. **Warms ARP** by sending 3 priming packets and waiting 1s — without this, cold subscribers (fresh netns, just-booted laptops) drop the first packets while the kernel resolves the gateway MAC, causing false MISS reports 3. Sends TCP connect()s and/or UDP datagrams at the requested rate 4. Snapshots `/api/status` before+after to detect new active pairs 5. Tails the gpnc journal for matching launch lines Defaults (changed 2026-04-27): - `--rate` = 20 pps (was 10) - `--duration` = 90 s (was 30) - Long enough that the ARP-warm + detector trigger + sustained flow all happen well within the window. Short bursts produced too many false MISSes from netns-style test subscribers. Pre-reqs: - subscriber-side host (not gpnc itself, not Mikrotik — those MACs are on the infra skip list and explicitly ignored by the detector) - network reachability to the catalog game IP (TCP can fail and still trigger the detector — the SYN leaves the host; UDP needs route + no firewall drop) - ssh key to `wtfast@10.80.4.15` for the journal step (else it falls back to a notice — the status-diff verification still works) Exit codes: - `0` = traffic ran AND a new active_pair appeared in /api/status - `4` = traffic ran but no new pair appeared. Common causes: - Detector dedupe from a prior run with the same MAC (use a fresh MAC, or wait 30s) - Engine session reached `active` but the proxy chain to a WTFast exit failed (look at gpnc.log for `control response` or `Driver listen failed`) - Game's pinned exit (e.g. WoT → Israel) is unreachable from this lab — switch test to Albion or another non-pinned game ## Verifying it worked Open `https:///sessions` while the script is still running. You should see a row with: - your subscriber MAC - the game name (e.g. "World of Tanks", not the raw configID) - `active` badge in green - a "Stop" button If the row is there but the badge is "stopping", that's a cosmetic UI bug from before 2026-04-27 — the actual status is fine. Update gpnc-status to the latest build to fix. ## Adding a new test game If the catalog doesn't have your game's IPs yet: 1. Edit `/var/cache/gpnc/manual_games.json` on gpnc-he-1 with the game's name + AppMetaID + ConfigID 2. POST `http://10.80.4.15:50055/reloadmanualgames` to reload 3. `python3 traffic_gen.py --list` will now include it ## Common confusions **"Kernel matching N pkts but no active proxied flows" banner.** This is a *health hint* about the live poll window, NOT a permanent state. If you see it persist across many polls AND the kernel pkt counter is still climbing, then the engine genuinely can't ingest the TPROXY-delivered packets and we have a real bug. If it appears once after a test burst and clears on the next poll, that's the normal "burst ended, flow timed out" behavior. **"My session disappeared from the UI."** Sessions get torn down when: - A `Stop` button click in the UI (you did it) - The Boost websocket reports `IsActiveInCPE=false` AND the initiator is NOT `stateless_*` or `l2_inline_detected` (these are protected from teardown — fixed 2026-04-27) - gpnc restarts **"My traffic doesn't show up at all."** Check that your source MAC isn't on the gpnc infra skip list (Mikrotik, BQN, gpnc itself). Source MACs starting with `01:` or `33:33:` are also skipped (multicast / IPv6 multicast). For test subscribers use `02:*` (locally-administered range — guaranteed not to collide with anything real).