Security model
Routers verify release signatures before installing updates. This limits what a compromised distribution server can do, provided the signing key and the router’s trust store remain protected and verification works correctly. Signatures establish authenticity; they do not guarantee that signed software is free of defects.
What a compromise of this server gets an attacker
- Withholding. The attacker can stop serving updates. Routers keep their current version, and the time of their last successful check stops advancing, which the admin panel shows.
- Corruption. The attacker can serve damaged or altered files. Routers reject them at the signature check, before anything is unpacked.
- Replaying old releases. A valid signature alone does not establish freshness. Routers reject manifests older than one they already accepted, catalogues whose highest version is lower than one already seen, and manifests beyond the configured maximum age (90 days by default). These checks limit rollback and freezing; they cannot guarantee immediate discovery of every new release.
- Traffic observation. An attacker controlling the server can observe connecting IP addresses, device certificates and requested files. Shortening addresses in routine access logs reduces stored data, but does not prevent this observation or guarantee anonymity.
- Transport impersonation. Stealing the Ed25519 identity key permits impersonation in new optional key-exchange sessions. Stealing that key alone does not reveal earlier sessions, under the cryptographic assumptions and provided their session secrets were not exposed. An attacker controlling a running server may read active session secrets from memory.
An attacker can change this website and publish arbitrary files. Without the private SLH-DSA release-signing key, they cannot produce a valid signature for altered software. A correctly verifying router rejects it. The private signing key is intended to be kept offline, separately from this server; the public verification key is present on the server and routers.
Current GADNET routers download over HTTPS using a device certificate and verify release signatures locally. They do not use the optional application-level key exchange described below.
Controls
| Risk | Control |
|---|---|
| Broken access control | The pages of this site are public. Release files - manifests, bundles, reports, inventories and the key set - are served only to GADNET routers that present a device certificate with a valid fleet attestation. Publishing a release happens on the server's filesystem, never over HTTP. |
| Path traversal | Release-file requests are looked up in a verified catalogue of allowed paths, rather than joined directly to arbitrary filesystem paths. The site also serves its own static assets and separately signed key and policy catalogues through dedicated routes. |
| Cryptographic failures | HTTPS only, with HSTS. Optional key-exchange sessions use hybrid X25519 + ML-KEM-768, HKDF-SHA-384 and AES-256-GCM, with constant-time MAC comparison. |
| Injection | No database and no shell. OpenSSL is invoked with an argument list, never through a shell. Templates escape output automatically, and the site renders no user input beyond validated path segments. |
| XSS | The site contains no JavaScript, and its Content Security Policy is default-src 'none', allowing only the site's own styles, fonts and images. The one exception is the opt-in browser test on the connection test page: a single file from this server, run only when the visitor asks, under a policy of its own that adds script-src 'self' with connect-src 'none' and Trusted Types. Release files are served as downloads (Content-Disposition: attachment) with nosniff, so a browser never renders them as a page. |
| CSRF / session fixation | The public website has no administrative operations based on browser cookies or login sessions. Its pages contain no forms. Requests within optional key-exchange sessions use separate session authentication; they do not publish releases or change router settings. |
| Security misconfiguration | Without its identity key the server does not start; without the release public key it starts but publishes nothing. A channel that fails verification is withdrawn and the internal readiness check (/ready) reports it. Interactive API documentation is disabled, and the server header reveals no version. |
| Host-header injection | Requests whose Host is not the configured domain get 421. Absolute URLs are built from configuration, never from the request. |
| Denial of service | Per-IP request limits, with a lower limit for key exchange, cap request volume. Session and client tables, request body sizes and concurrent OpenSSL work are bounded. These measures reduce resource exhaustion; they do not guarantee availability during every denial-of-service attack. |
| Logging failures | The application access log records one structured entry per request. Control characters are neutralised and client addresses are shortened. Other components may record additional events; this does not guarantee that every log in the deployment contains only shortened addresses. |
| Information disclosure | Tracebacks are never returned. Validation errors name the offending field but never echo its value. A missing channel and a missing file return the same 404. |
Post-quantum protection
Release signatures use SLH-DSA-SHA2-128s, a post-quantum algorithm specified in FIPS 205. Authenticity still depends on protecting signing keys and on correct verification.
Optional sessions combine X25519 with ML-KEM-768 (FIPS 203) to protect session secrets against recording today for future quantum decryption, under the algorithms’ security assumptions. The Ed25519 transcript signature is classical: this is not fully post-quantum authentication. URLs and identifying metadata are not hidden.
Reporting a vulnerability
Contact details are in /.well-known/security.txt (RFC 9116). Please include enough detail to reproduce the problem. We confirm receipt, and we let you know when a fix ships and in which release.