Please do not open a public issue for a suspected vulnerability. Report it
privately through GitHub's Report a vulnerability button on this repository
(Security → Advisories), or by email to the maintainer listed in Cargo.toml.
You will get an acknowledgement within a few days and a fix or a written
assessment before any public disclosure. Data-corruption bugs, memory-safety
bugs in the unsafe surface, and crash-consistency violations all count.
ZeroDB is an embedded storage engine, not a security boundary. It assumes the database file is written only by trusted processes on a trusted filesystem, the same assumption LMDB makes.
What it promises
- Crash consistency. A power loss or
SIGKILLat any point leaves the file at some previously committed transaction, never a torn state: two double-buffered meta pages carry a mandatory CRC32C, and data pages are flushed before the meta that references them (SPEC 06). This is exercised continuously by a fault-injecting write backend and aSIGKILLharness (ADR-0008). - Memory safety and freedom from panics for every legal sequence of API
calls, verified by differential fuzzing against LMDB,
mirion the core, andloomon the reader table. - Single-writer, many-reader MVCC isolation within one process. Readers never block the writer or each other; a reader always sees one committed snapshot.
- Environment/transaction pairing is checked. Using a database handle with a transaction from a different environment panics with heed's message instead of touching the wrong file.
What it does not promise
- Safety against a hostile or corrupt database file. The meta CRC detects
accidental tearing, not tampering; it is unkeyed. A first-release hardening
pass made the open path and the read path refuse out-of-range page
references, zero-child branch pages, and hostile free-page lists with typed
errors, and added a fuzz target that feeds arbitrary bytes to
open. That work is a best effort, not a guarantee: a crafted file can still be able to cause a panic or an out-of-memory in the offlinezerodb-tools. Runzerodb-tools checkon files you trust or in a sandbox. - Cross-process access. One process per environment; there is no lock file and no reader table shared between processes (D-001). Opening the same environment from two processes is undefined.
- Encryption at rest, or protection from a local user with write access to
the environment directory. Files are created with mode
0600. - Bounded memory for a write transaction. All dirty pages of a write
transaction are held in RAM until commit, and a single value may be up to
4 GiB. There is no
MDB_TXN_FULLequivalent. - Anything about the C LMDB fork.
zerodb-tools migrate-from-lmdb(an opt-in build feature) parses an LMDB file with the C library; any LMDB memory-safety issue is in scope for that one command and no other part of the engine.
Only the latest release on the 0.x line receives fixes. Releases are git
tags with GitHub release notes (ADR-0013); a fix ships as the next patch tag.
unsafe is confined to the memory map and the unchecked page-field readers
behind a validated-view contract (zerodb-core::page::raw, zerodb-io), one
pwritev and one flock FFI call, the differential oracle's LMDB FFI, and the
few pointer-shaped constructs heed's own API forces on the adapter. Every block
carries a // SAFETY: comment; the policy is in CLAUDE.md.