ttl: A Faster mtr That Can Diff Two Traceroutes and Export Prometheus Metrics
Scenario: a user says "the app is slow from the Frankfurt office" and you open mtr. You get loss and latency for each hop, then you go look up who owns each IP by hand, guess whether the loss on hop 7 is real or just ICMP rate limiting, and take a screenshot so you can compare tomorrow. ttl is a Rust traceroute/mtr replacement that does all of that in one tool. The last few releases also added things mtr never had: diffing two traces and running headless as a Prometheus exporter.
The current release is v0.23.0 (September 2026). It added RFC 5837 support, so routers that include interface and next-hop details in their ICMP errors can now tell you which interface the probe actually went through.
Installation
# any of these
cargo install ttl
brew install ttl
apk add ttl --repository=https://dl-cdn.alpinelinux.org/alpine/edge/testing
# Linux: give it raw sockets once, then run it without sudo
sudo setcap cap_net_raw+ep $(which ttl)The releases page also has prebuilt binaries for Linux x86_64/ARM64 and macOS. Since v0.20.0 there are also multi-arch container images on GHCR. On macOS and BSD you still need sudo ttl ....
Usage
ttl 8.8.8.8 # live TUI, like mtr
ttl 8.8.8.8 1.1.1.1 9.9.9.9 # several targets, Tab switches between them
ttl -p tcp --port 443 example.com # TCP probes, for when ICMP is filtered
ttl --flows 8 cloudflare.com # find ECMP paths
ttl --pmtud 1.1.1.1 # path MTU discovery
ttl --resolve-all google.com # trace every A record, not just the first oneEach hop in the TUI shows loss, latency stats, a sparkline, reverse DNS, ASN, GeoIP and the internet exchange (looked up from PeeringDB), so you don't need a separate whois step. Useful keys: p pauses, r resets stats, e exports JSON and ? shows help.
How it works
-p tcp --port 443: sends TCP SYN probes to a real service port. Firewalls that drop ICMP or UDP traceroute usually let these through, so you see the path your HTTPS traffic actually takes.--flows 8: probes with 8 different flow identifiers (Paris/Dublin traceroute). Load balancers hash on the 5-tuple, so a normal traceroute can mix hops from different paths together and invent loss that isn't there. Multi-flow probing lists each path separately. It also tells you whether a hop balances per flow or per packet.--pmtud: does a binary search for the largest packet that gets through. Use it when TLS handshakes hang over a VPN or tunnel and you suspect an MTU black hole.- ttl also detects NAT when a device rewrites source ports, warns about route flaps when the path changes mid-session, and reads MPLS labels from ICMP extensions. That last one helps explain the "hidden" hops inside a carrier network.
Example: before/after comparison
This is the part I'd actually use day to day. Record a baseline, record again after the change (or when the complaint comes in) and diff the two:
ttl 1.1.1.1 -c 100 --json > before.json
# ... ISP maintenance, BGP change, new firewall, whatever ...
ttl 1.1.1.1 -c 100 --json > after.json
ttl --diff before.json after.json-c 100: sends 100 probes per hop and then exits instead of running forever--json: writes the full result.--csvand--report(plain text, good for pasting into a ticket) also work.--diff: compares the two runsttl --replay before.json --animate: replays a saved session in the TUI, handy if you need to show the problem to someone later
Example: headless monitoring
ttl --daemon --prometheus :9090 1.1.1.1This runs without the TUI and exposes metrics on port 9090 for Prometheus to scrape. If you want to process the data yourself, --stream-json prints line-delimited JSON that you can pipe into jq or a log shipper. Both arrived in v0.20.0 (June 2026).
What's different from mtr
For a quick look, mtr is fine and it's already installed everywhere. ttl is worth it for:
- ASN, IX and GeoIP shown on each hop
- ECMP awareness, so fake loss on load-balanced paths stands out
- diffing and replaying saved traces
- a Prometheus mode, so you don't need a wrapper script around
mtr --jsonin cron
Honest take
ttl is still pre-1.0 and releases often, so expect flags to change now and then. Check the changelog before you build alerting on the Prometheus metric names. As an interactive replacement for mtr on your laptop or a jump host, it's ready to use now: cargo install, one setcap, done. The --diff workflow alone saves real time when you're arguing with an ISP about whether "nothing changed". I'd wait a bit longer before running daemon mode as a fleet-wide monitor.
Sources (verify before publishing):
$ ls ./see-also/
$ ./buy-me-a-coffee ☕ // found this useful? I write these in my spare time