mrambossekandClaude Fable 5 3c9af04e6f
server-release / image (push) Successful in 15s
server-test / test (push) Successful in 32s
server-release / release (push) Successful in 33s
grant: replace the rate check with a token bucket
The live throughput test found it: a 3-second run delivered 104 packets and
stopped after 50 milliseconds.

The rate check exempted the first 50 ms entirely, meaning to be lenient at
startup. The effect was the opposite. A sender could dump an unbounded burst
into that free window, and the instant the check switched on it compared those
bytes against 50 ms worth of allowance and refused everything until real time
caught up. Every short test passed — downtrain sends 50 packets, big_send seven
— and every sustained send died about fifty milliseconds in.

A token bucket (allowance = burst + rate x elapsed) has no such cliff; it is
smooth from t=0. The burst is 100 ms of the allowed rate, floored at one
ordinary datagram so a single packet is never refused outright. The floor is
deliberately one datagram: at 8 kbps a 64 KB floor would be sixty-four seconds'
worth, which is precisely the instant dump the ceiling exists to prevent. The
existing rate test caught that when I first tried it, and it was right.

Second half of the same bug: callers treated any refusal as terminal. TryAllow
now says why, so a sender can pace through a transient "too fast just now" and
still stop dead on a spent budget or an expired grant.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-08-01 14:10:30 +02:00

echolot — measure, don't guess

Echolot

Free software for detecting and debugging local network issues from an Android phone — built for people who actually know what a neighbor table is.

Most "wifi analyzer" apps show you signal bars. Echolot aims at the layer where home and office networks actually break: duplicate DHCP servers, broken IPv6 RAs, MTU black holes, NAT64 weirdness, multicast that dies at the AP, DNS that answers differently than it should. It records what it observed, separates observation from interpretation, and exports the whole run so you can argue with it later.

Status: pre-release. The capability prober runs on real hardware; the production app and the probe server are not built yet.

Repository layout

docs/              design docs — the contract for everything below
echolot-prober/    capability prober: validates the no-root feasibility matrix on real devices

The Go probe server and the production app land here as siblings.

Design docs

The three specs are draft-complete and reviewed; treat them as the contract.

Doc What it defines
docs/feature-catalog-and-feasibility.md Full feature list + the no-root feasibility matrix
docs/measurement-schema.md Archived/exportable measurement JSON (observation vs finding, two-clock rule, anonymization)
docs/probe-protocol.md Client↔server wire protocol (pinned TLS control plane, binary UDP data plane, STUN, canary DNS)
docs/build-status.md Running log of decisions and next steps

Privilege tiers

Every result records which tier produced it:

  • app — no root, no special setup. The bulk of the functionality.
  • shizuku — ADB-shell privileges via wireless pairing, no root. Shipped in v1.
  • root — future optional module.

Licensing

Part License Why
All code (app, prober, server) GPL-3.0-or-later The value here is the platform-API research; copyleft keeps derivative apps free
docs/ (the specs) CC-BY-4.0 A wire protocol and a measurement format should be implementable by anyone, without license anxiety

Full texts: LICENSE (GPLv3) and docs/LICENSE (CC BY 4.0). Sources carry SPDX-License-Identifier headers.

If you want to build a compatible server or client, the protocol and schema docs are deliberately permissive — go ahead.

Building

See echolot-prober/README.md. Short version, from echolot-prober/:

echo "sdk.dir=/path/to/Android/sdk" > local.properties
./gradlew :app:assembleDebug
S
Description
No description provided
Readme GPL-3.0
1.3 MiB
2026-08-02 14:58:41 +02:00
Languages
Kotlin 61.6%
Go 36.2%
HTML 1%
Shell 0.5%
Python 0.4%
Other 0.2%