DEV Community

Doğukan Sağlık
Doğukan Sağlık

Posted on Fully Autonomous

I built TunnelScope to inspect MTU and packet-size failures with evidence

Small packets can work while larger transfers stall. When that happens, a timeout alone does not tell you whether a packet was too large, filtered, lost, or whether the reply failed on its way back. I built TunnelScope, an MIT-licensed Python CLI, to collect more useful evidence on a controlled Linux path.

It sends bounded UDP payloads to a cooperating receiver. The sender records acknowledgements, explicit size errors, timeouts and optional Linux ICMP size feedback. The receiver can save the probe IDs it actually saw. Reports are JSON, with an offline HTML view for browsing the results.

Here is the simplest loopback test using the published v0.5.0 package:

python3 -m venv .venv
source .venv/bin/activate
python -m pip install tunnelscope
# Terminal 1
tunnelscope receive --max-packets 2 --output receiver.json
# Terminal 2, after the receiver says it is listening
tunnelscope probe 127.0.0.1 --sizes 64,1200 --count 1 --output probe.json
tunnelscope show probe.json
tunnelscope html probe.json --output probe.html
Enter fullscreen mode Exit fullscreen mode

On the development branch, a new diagnose command combines three sequential, one-direction experiments: DF probes, the same sizes with source fragmentation permitted, and a bounded adaptive size search. It saves the underlying runs together in JSON and HTML. It is not in the v0.5.0 PyPI release yet.

In an isolated 1280-byte IPv4 link lab, the DF search observed a 1252/1253-byte UDP payload boundary (1280 minus 20 bytes of IPv4 and 8 bytes of UDP headers). That is a controlled direct-link result, not a claim that the tool discovers the exact MTU on arbitrary networks. A missing ACK remains inconclusive; observed ICMP can also be untrusted. Real VPN and Kubernetes path validation is still on the roadmap.

The code, a short terminal demo and reproducible labs are here: TunnelScope on GitHub. The diagnose guide explains the new workflow.

If you troubleshoot VPN or overlay MTU issues, I would value feedback on which observations would make a report more useful in practice.

Top comments (2)

Collapse
 
m_montazeri profile image
Mohammad Montazeri •

Would a joined sender/receiver view keyed by probe ID fit the HTML report? I would find two separate cases especially useful: “receiver saw the probe, sender saw no ACK” and “neither endpoint recorded receipt”. Keeping those as observations, with direction, payload size and timestamps beside them, would make the remaining uncertainty much clearer. This is report-design feedback; I have not tested TunnelScope. AI-assisted; I work on Lisar Connect.

Collapse
 
lazypanic999 profile image
Doğukan Sağlık •

Thanks, Mohammad. I implemented this on the development main branch today. The correlation HTML now joins each sender attempt with receiver evidence by probe ID and shows direction, payload size, send-attempt time, receiver arrival time, ACK-send status, sender ACK arrival time, and an evidence-case label side by side.

It separates receiver_observed_no_ack from no_ack_no_receiver_observation. The second case stays inconclusive unless receiver capture coverage is independently verified; timestamps from different hosts are displayed without comparing their clocks.

The change is in this commit, with loopback and blocked-ACK lab tests. It is on main, not in the v0.5.0 PyPI release yet. Your report-design feedback was useful—thank you!