Last updated: September 14, 2026
Your backups belong to you, and must stay yours even without us. The format of .sigbak archives is public, and a small open-source program decrypts them on a computer with your backup key. If Sigillarium were to disappear, your documents would remain readable.
pip install cryptographypython sigbak_decrypt.py backup.sigbak my-documents
The program asks for your backup key at the keyboard (it is not shown on screen), then extracts each document into the folder. It checks the integrity of each one: a damaged document is reported and skipped, the others are extracted. The program only reads the archive and sends nothing over the Internet.
Exit code: 0 if the archive is intact, 1 if documents are missing or the archive is incomplete, 2 on error (wrong key, invalid file).
This section is for people who want to check the format or write their own reader.
0123456789ABCDEFGHJKMNPQRSTVWXYZ, in groups of 4: the 128 bits followed by 2 zero bits give 26 symbols (most significant bit first), then 2 check symbols.c = (Σ (i+1) × s[i]) mod 1021 for i from 0 to 25, written on 10 bits (c >> 5, then c & 31).O as 0 and I, L as 1; reject if the length, a character, the check or the 2 padding bits are wrong.okm = HKDF-SHA256(key, header salt, "Sigillarium archive v1", 64) (RFC 5869)
encryption_key = okm[0..32]
check_key = okm[32..64]
| Bytes | Content |
|---|---|
| 0–5 | SIGBAK (ASCII) |
| 6 | format version: 1 |
| 7 | key derivation: 1 = HKDF-SHA256 |
| 8–39 | random salt (32 bytes) |
| 40–55 | key check: HMAC-SHA256(check_key, bytes 0–39), truncated to 16 bytes |
After the header, until the end of the file: type (1 byte) · ciphertext length L, tag included (4 bytes, big-endian) · nonce (12 bytes) · AES-256-GCM (encryption_key), ciphertext followed by the 16-byte tag.
Associated data of the record at index n (0 for the first): header (56) ‖ n (4, big-endian) ‖ type (1) ‖ L (4, big-endian). A record that is moved, removed or taken from another archive therefore fails authentication.
| Type | Name | Decrypted content |
|---|---|---|
0x01 | INFO | JSON: {"createdAt": "<ISO 8601 UTC>"} |
0x02 | META | JSON: document metadata |
0x03 | DATA | document bytes |
0x7F | END | JSON: {"entries": <number of documents>} |
Sequence: INFO, then (META, DATA) for each document, then END.
name, fileType (MIME type), createdAt, modifiedAt (or null), description (or null), tags, sha256 (of the DATA bytes), size, and metadata (optional). A reader ignores unknown fields, and must never use name as a file path as is.
archive_v1_sample.sigbak — 1,078 bytes, SHA-256 01b1eb4ac4aca12d32f0a482d76ec5dc5ec1b2f90e64ad64fcc16b1b8c478dbb. Key: 000G-40R4-0M30-E209-185G-R38E-1W73 (bytes 00 to 0F). It contains photo.jpg (300 bytes) and a document named ../note.txt, a deliberately hostile name that a correct reader must not use as a path.