Measure Solana peer latency with and without Doublezero (DZ) and compare the results.
The script pings only the peers that appear in both:
doublezero user list(takes theclient_ipcolumn), andsolana gossip(takesIP Address+Identityfor the chosen network)
It then:
- runs ICMP pings to those matched peers,
- (optionally) toggles your DZ tunnel to measure connected vs. disconnected,
- prints a clear summary: improvements, same, regressions, and skipped (ICMP blocked/timeout).
⚠️ By default the script will disconnect and reconnect your DZ tunnel once to run both measurements. You can disable this with--no-toggle(see Modes).
- Linux recommended (uses
pingflags compatible with iputils/BusyBox). - Solana CLI (
solana) installed and in$PATH. - Doublezero CLI (
doublezero) installed and in$PATH. - Ability to connect to Doublezero (you need a valid DZ setup and a whitelisted key that can connect, e.g., IBRL).
- curl (for external IP detection).
- ping (system ICMP ping tool).
The script checks for these tools on startup and exits with an error if any are missing.
- Clone the Repo. :
git clone git@github.com:schmiatz/doublezero-latency-check.git
- Make it executable:
cd doublezero-latency-check && chmod +x doublezero-latency-check.py
- run it:
./doublezero-latency-check.py --mainnet
Choose the Solana network and whether to toggle the DZ tunnel.
# Compare connected vs. disconnected (will toggle DZ, with confirmation)
./doublezero-latency-check.py --mainnet
# Measure only current state (no tunnel changes)
./doublezero-latency-check.py --mainnet --no-toggle# Compare connected vs. disconnected (will toggle DZ, with confirmation)
./doublezero-latency-check.py --testnet
# Measure only current state (no tunnel changes)
./doublezero-latency-check.py --testnet --no-toggle-
Requirement checks
Verifiessolana,doublezero,ping, andcurlare available. -
Network selection
--mainnet→ usessolana gossip -um--testnet→ usessolana gossip -ut
-
Discover current state
- Detects external IP via
curl ifconfig.me. - Reads Doublezero status via
doublezero status.
- Detects external IP via
-
Confirm before toggling (if not
--no-toggle)
Prints a clear warning that DZ will be disconnected/reconnected and asks you to confirm.
If you answery/yes, it proceeds; otherwise it exits without changes. -
Build the target set of peers
- Runs
doublezero user list, collects allclient_ipvalues. - Runs
solana gossip (-um | -ut), extractsIP Address+Identity. - Intersects the two sets → only peers present in both are probed.
- Runs
-
Run the latency tests
- If DZ is currently UP:
- Measure connected first (ICMP ping to each matched peer).
- If toggling is enabled:
doublezero disconnect, actively wait untildoublezero statusreports disconnected.- Measure disconnected.
doublezero connect ibrl, actively wait untildoublezero statusreports up.
- If DZ is currently DOWN:
- Measure disconnected first.
- If toggling is enabled:
doublezero connect ibrl, actively wait until up.- Measure connected.
doublezero disconnect, actively wait until disconnected.
Pings are run concurrently (thread pool).
The script parses average latency from ping output. If no number can be parsed, the result is marked astimeout,unreachable,icmp blocked, orping not found. - If DZ is currently UP:
-
Compare & print results (only when both runs exist)
- Better: connected < disconnected
- Same: connected == disconnected
- Worse: connected > disconnected
- Skipped: one or both sides not numeric (blocked/timeout/etc.)
- only connected measured: connected numeric; disconnected not
- only disconnected measured: disconnected numeric; connected not
- both: neither numeric
The script prints:
- A summary with totals and the skipped breakdown.
- Full lists for improvements, same, regressions (sorted for readability).
- A skipped table with raw statuses for each side.
-
Single-run output (when
--no-toggle)- If DZ is up, prints: “Only 'connected' measurements were taken (--no-toggle)” and a table of IPs/identities/latencies.
- If DZ is down, prints: “Only 'disconnected' measurements were taken (--no-toggle)” and the same kind of table.
- No comparison is performed in this mode.
| Mode | Command example | What happens | When to use |
|---|---|---|---|
| Comparison (default) | ./doublezero-latency-check.py --mainnet |
Measures connected, toggles DZ, measures disconnected, restores original state, then prints full comparison (better/same/worse/skipped). | When you want to objectively compare DZ vs. non-DZ latency. |
| Single-run (no toggle) | ./doublezero-latency-check.py --mainnet --no-toggle |
Measures only the current state (connected if DZ is up; disconnected if DZ is down). Prints a simple table of latencies; no comparison. | Safe mode for production/cron or when you don’t want any tunnel changes. |
- Summary
=== Latency comparison summary === Total peers: 129 Better (connected < disconnected): 47 Same (equal values) : 2 Worse (connected > disconnected): 69 Skipped (non-numeric, ICMP blocked/timeout): 11 [only connected measured: 4; only disconnected measured: 0; both: 7] - Lists
- improvements (connected faster): full list, most improved first.
- same: exact ties.
- regressions (connected slower): full list, worst first.
- skipped: peers where ICMP wasn’t measurable on one/both sides, with the raw statuses shown for each side.
- ICMP only: The script uses ICMP ping exclusively. If a peer blocks ICMP, it will show as
icmp blocked/timeoutand be counted under Skipped. - Linux recommended:
pingoptions vary by OS. The script targets iputils/BusyBox semantics. - Privileges: On some systems, ICMP may require privileges/capabilities. If you see
permission denied, adjust your environment accordingly. - DZ actions: With the default mode, the script disconnects and reconnects your DZ tunnel once. There’s a confirmation prompt; use
--no-toggleto avoid any tunnel changes. - Whitelisting: You must already be able to run
doublezero connect ibrlsuccessfully (i.e., your key/user is whitelisted and configured).
- “ERROR: Missing required tools” → Install the listed tools and ensure they are in
$PATH. - Ping shows
icmp blocked/timeout→ The peer or network likely blocks ICMP; this is expected for some hosts. - DZ never reaches the target state → The script polls
doublezero statusuntil timeout; if it can’t confirmup/disconnected, it will warn and skip that leg. Check your DZ connectivity/config.