Security architecture

This page explains how Bugbane protects the data it collects. It describes Bugbane 0.2.3. Everything here can be checked in the source code — the encryption lives in the crypto module, and the design goals in THREAT_MODELING.md.

In short:

  • Acquisitions are always encrypted.
  • The decryption key lives in your device’s security hardware and never touches the app’s storage in the clear.
  • An optional acquisition password adds a second, independent layer against non-consensual forensic extraction.
  • Exports are encrypted with a one-time passphrase. Your data never leaves the device otherwise.
  • Indicator updates go through a privacy relay, so the update server never sees your IP address.

What Bugbane defends against #

The threat model considers, among others:

  1. Spyware on the device itself. If the device is compromised at the root level, whatever Bugbane stores could be read. Also, the spyware could have already removed its tracks, or could know that Bugbane is in use and interfere with its results.
  2. Physical access and forensic extraction. Someone who takes the device — or uses a non-consensual forensic tool on it — should not be able to read your acquisitions.
  3. A hostile network. Acquisition happens over the device’s own Wireless Debugging. Other parties on the same network can know when you turn on Wireless Debugging. Never do so on a public, shared, or untrusted network. Bugbane also warns about vulnerable Android versions when applicable, and pushes you to disable Developer Options after each session.
  4. The update infrastructure. Downloading indicators should not reveal who is using the app, and a compromised source should have limited power (see limitations).

How acquisitions are stored #

Each acquisition is a single file: a standard ZIP archive wrapped inside an age encryption envelope. The archive is encrypted while it is being written, artifact by artifact: plaintext is never cached to disk, not even temporarily. If the acquisition is interrupted, what exists on disk is still encrypted.

One thing intentionally stays readable without unlocking anything: a small metadata file with the acquisition’s name, date, and status. It lets the app show your list of acquisitions without asking you to authenticate — but it also means someone with the device can see that acquisitions exist and when they were made. Their content is what the encryption protects.

The acquisition key #

Each installation generates one acquisition identity: an X25519 key pair.

  • The public key is stored in the clear. This is what encrypts new acquisitions — and it is why acquiring never asks you to authenticate.
  • The private key is what decrypts them. It is wrapped by a key kept in Android’s security hardware — a secure element (StrongBox) where available, otherwise the TEE — and unlocking it requires confirming your screen lock.

This split matters: an acquisition can always be written, even right after a reboot, but reading, analyzing, exporting, or sharing one always requires your credential.

The acquisition password #

The getting started guide shows where to set it. Technically, the password seals the acquisition identity with Argon2id (the memory-hard parameters recommended by RFC 9106, sized for mobile: 64 MiB, 3 iterations) plus ChaCha20-Poly1305 — inside the hardware-backed layer, not instead of it.

What it adds: forensic extraction tools work by extracting key material and brute-forcing short PINs. If that succeeds against your device, the password is still in the way — and cracking a long random password through Argon2id is not practical. This is why the app encourages the password on devices without a secure element, and treats it as optional where StrongBox already raises the bar.

The trade-off is real: there is no recovery. Bugbane never stores the password, so forgetting it means the acquisitions already on the device stay sealed forever. Removing the screen lock has a similar effect: Android permanently invalidates the hardware-backed key (changing the screen lock does not), and the acquisitions already on the device become unreadable.

Export and Share #

When you export or share an acquisition, Bugbane does not decrypt and re-encrypt your data. It unwraps the archive’s file key with your acquisition identity, re-wraps that key to a passphrase (age’s scrypt recipient), and copies the encrypted payload byte for byte. Concretely:

  • The exported file is a standard .zip.age — anyone with the passphrase and the age tool can open it. This is what makes analysis with MVT possible.
  • The passphrase is 32 random alphanumeric characters, generated on the spot and shown once. Bugbane does not keep it.
  • Share streams the archive directly to the app you choose (Signal, email, …); nothing is staged on disk, and only the chosen app gets access, so, depending on the receiving app, this can work even when disk space is low.

Send the passphrase through a different channel than the archive. If both travel together, the encryption protects nothing.

The ADB key #

Pairing with Wireless Debugging creates an RSA-2048 ADB identity. Its private key is wrapped by the same hardware-backed keystore before being stored, so a copy of the app’s files is not enough to impersonate the pairing. A forensic tool that can extract the key has no use for it: extracting it already requires more privileges than the key itself grants.

Indicator updates #

Bugbane periodically downloads updated Indicators of Compromise from update.bugbane.org. It never contacts that server directly: requests travel through an Oblivious HTTP relay (RFC 9458). The relay sees your IP but not the request; the server sees the request but not your IP. Neither party alone can tell who is updating spyware indicators — information that is itself sensitive. Updates are downloaded as compact deltas and verified by hash against the expected result. The current relay provider is oblivious.network, which deploys its relays on the Fastly CDN. Any network provider will see a connection to relay.oblivious.network, the same SNI name shared among all tenants, so in theory it cannot directly distinguish Bugbane traffic from that of other services using the same provider.

Known limitations #

  • Bugbane is experimental and has not yet received an independent security audit — see risks and warnings.
  • Indicator bundles are fetched over HTTPS/OHTTP and hash-checked, but end-to-end signature verification of the indicator feed is not implemented yet. It is planned. Until then, a compromise of the update infrastructure could serve altered indicators.
  • Using Bugbane is detectable on the device. Features like hiding the app are not implemented.

Verify what you install #

Builds are reproducible, and F-Droid independently verifies them. If you install the APK directly, check the signing certificate first.