Skip to content

NullWire v0.3.0

Latest

Choose a tag to compare

@yunomiwell yunomiwell released this 16 Jul 18:36
a6eddbb

NullWire v0.3.0

The v0.3 milestone — the app now always locks, mobile receiving became dependable, and the mesh got much harder to abuse.

Highlights

  • Mandatory PIN/passphrase app lock, all platforms — every install now seals its local data (keys, messages, state) in an encrypted vault behind your PIN/passphrase. Existing installs migrate automatically on first unlock — same identity, no data loss. The old unencrypted-at-rest path is gone on desktop, iOS, and Android.
  • "Can send but can't receive" fixed — onboarding now verifies that the on-chain handle's key actually belongs to this device. A handle already registered under a different key fails clearly with "handle taken — choose another" instead of a false success that silently broke receiving.
  • Opt-in cover traffic on mobile — iOS and Android can now emit desktop-style cover packets (fixed-size and mix-routed, the same shape on the wire as real sends). Deliberately modest scope: foreground-only (battery), default off, and it obscures real-send timing within a session — it does not make you anonymous.
  • Gateways fail closed on unauthenticated mailbox polls — draining a mailbox now requires the owner-signed auth token by default, closing an unauthenticated denial-of-delivery hole.
  • Post-quantum group chats (experimental) — MLS groups gain an optional PQ-hybrid X-Wing ciphersuite (ML-KEM-768 + X25519), feature-gated and default off. Production groups remain on the classical MLS suite for now.

Desktop

  • Mandatory app lock: first run enrolls a PIN/passphrase; any legacy on-disk state is migrated into the encrypted vault, and the messaging engine only starts after unlock.
  • Lock screen fix: the keypad's outer columns and delete key rendered fine but ignored clicks — every key is now clickable (keyboard entry unchanged).

Mobile (iOS + Android)

  • Registration key-verify (the receive fix above) on both platforms.
  • iOS: receiving now arms immediately on unlock — previously a freshly launched-and-unlocked app didn't poll until you backgrounded it once.
  • The foreground-poll preference now survives restarts on both platforms (it used to reset every launch).
  • Mix-routed mailbox fetch (experimental) is now self-testing: it only switches on after one successful live round-trip, and if it later fails the app falls back to the direct fetch the same tick — the direct path stays armed as the safety net. The self-test is time-bounded and rides your configured delay profile.
  • A crafted or corrupt group message is now caught and dropped instead of panicking the group-receive path — it's panic-guarded like every other entry point.
  • Android settings parity with iOS: optional erase-after-repeated-failed-unlocks, mix-routed-fetch toggle, cover-traffic toggle.
  • iOS polish: unread badge clears when you open a thread, groups open at the newest message, thread-row layout tightened.
  • Onboarding copy now reads "post-quantum private messenger." We removed wording that promised more than the network delivers today: the app is private (post-quantum end-to-end encryption; servers never read your messages), and network anonymity — hiding who talks to whom — only grows as genuinely independent operators run relays. Run one: github.com/yunomiwell/nullwire-node.

Mesh & relays

  • Mailbox polls enforce owner-signed auth by default (operators: emergency rollback via NULLWIRE_MAILBOX_AUTH_ENFORCE=0; takes effect on redeploy).
  • Proof-of-work anti-spam gates on unauthenticated deposits — mailbox, attachment-blob, and pairing-reply paths — so a crafted flood has to pay for every packet instead of cheaply evicting legitimate queued messages. Staged rollout: clients already emit proofs; enforcement flips fleet-wide after.
  • Push wakes can be coalesced and jittered (opt-in, per-gateway) so push providers see at most one wake per window instead of a per-message arrival stream; client poll cadence is jittered too.
  • New /version endpoint plus a fleet-check script — wire-version skew between nodes gets caught before it breaks receiving.
  • Client-configurable entry (NULLWIRE_BRIDGE, Tor-bridge-style line): a client can be handed an entry address + operator key out of band instead of depending on baked-in addresses that a censor may have enumerated.
  • Downgrade-guard groundwork: once a node has reached a peer over TLS, it refuses plaintext fallback to that peer. Honest caveat: inter-node links are still plaintext HTTP today — this guard activates as the mesh TLS rollout lands.
  • Handle registry (devnet): owner-key recovery is now announce-then-rotate — a 7-day timelock, the incoming key must co-sign, and the current owner can veto. Legacy handle records upgrade in place on first write.
  • New public threat-model doc: a per-adversary matrix of what each adversary class can and cannot see. Our public claims are now also machine-checked in CI against a governed allowlist.

Fixes

  • Attachment fetches bound their response reads (robustness against a misbehaving gateway).
  • Numerous reliability and test-suite fixes across crypto, node, and mobile FFI.

Verify

releases.json and checksums.sha256 are minisign-signed (*.minisig); the auto-updater verifies the manifest against the build-time-baked public key before trusting any field.

Unaudited. No third-party security audit yet. Devnet, not mainnet. Single operator today; the per-message anonymity set is small (k≈1–2). NullWire is already private — the network becomes more than that only as independent operators join. Run a relay: github.com/yunomiwell/nullwire-node.