A lightweight, standalone, and completely offline toolkit for secure data backup:
- BIP-39 Converter: Compress text into BIP-39 words using
zlib+ Base2048 encoding- Optional AES-256-CBC encryption with password protection (web only)
- Binary dump download (
.bin) for RFID/NFC writing - Base64 string export for CLI tools (e.g.,
rfid_op --write) - Base64 decoder modal for decoding base64 strings back to text
- Binary file upload for decoding RFID dumps directly
- QR Code Tool: Generate/decode standard QR codes for quick plaintext backups
- Steganography Tool: Hide text inside PNG/JPG images using LSB encoding
- Compression + optional AES-256-CBC encryption
All tools work 100% offline with zero external dependencies, perfect for air-gapped environments and paper/offline backups.
- Compression: The text is compressed using
zlibwith maximum compression level (9) to reduce size. - Encryption (Optional): If enabled, compressed data is encrypted using AES-256-CBC with:
- PBKDF2 key derivation (100,000 iterations, SHA-256)
- Random salt (16 bytes) and IV (16 bytes) for each encryption
- Direct byte encryption (no base64 overhead)
- Marker Byte: A prefix byte is prepended (
0x01= compressed only,0x02= compressed + encrypted) - Padding: Data is padded to a 4-byte boundary (RFID page alignment) with
0x00bytes - Base2048 Encoding: The resulting integer is converted into base-2048, mapping to the BIP-39 wordlist.
- Reconstruction: BIP-39 words/indices are converted back to a big integer, then to bytes.
- Marker Detection: First byte identifies format (
0x01or0x02) — automatic encryption detection. - Padding Strip: Trailing
0x00bytes (RFID alignment padding) are automatically stripped before processing. - Decryption (If Needed): If marker is
0x02, data is decrypted using the provided password. - Decompression: Remaining bytes are decompressed via
zlibto restore original text.
A standalone, responsive web interface in index.html with three independent tool modes. Just open the file in any browser — no server required.
- Compress & encode text into BIP-39 words
- Optional AES-256-CBC Encryption with password protection
- Toggle encryption on/off with checkbox
- PBKDF2 key derivation (100,000 iterations)
- Smart validation and automatic encryption detection on decode
- Password visibility toggle (eye icon)
- Real-time size statistics showing compression ratio and encryption overhead
- Output formats (all generated simultaneously):
- BIP-39 words (e.g.,
abandon ability above) - Space-separated indices (e.g.,
0 1 2) — best for RFID - Dash-separated indices (e.g.,
0-1-2) - Zero-padded dash indices (e.g.,
0000-0001-0002)
- BIP-39 words (e.g.,
- Binary & Base64 Export:
- 💾 Download Binary —
.binfile for RFID writing (with 4-byte padding) - 📋 Get Base64 — Base64 string for CLI tools (without padding)
- One-click copy to clipboard
- Compatible with tools like
rfid_op --write "base64string" - Cleaner format than binary files for remote/CLI workflows
- 💾 Download Binary —
- Three input methods (use one at a time):
- 🔓 Decode Base64 String (modal window)
- Paste base64 string from encode or external tools
- Automatic whitespace/newline cleanup
- Supports encrypted (marker
0x02) and unencrypted (marker0x01) data - Optional AES decryption with password
- Full-featured modal with same decoding logic as binary files
- Binary file upload: Upload
.binfiles directly (RFID dumps) - Text input: Paste BIP-39 words or indices in any supported format
- 🔓 Decode Base64 String (modal window)
- Automatic format detection: handles words, space/dash-separated indices, padded indices
- Automatic padding strip: RFID
0x00padding bytes are removed automatically - Automatic encryption detection: marker byte
0x02triggers decryption prompt - Shows decoded text size, character count, and word count
- Generate standard QR codes (no compression or special encoding)
- Decode QR codes from uploaded images
- Download as PNG, works with any QR scanner
- Hide text inside PNG/JPG images using LSB (Least Significant Bit) encoding
- Compression + optional AES-256-CBC encryption for hidden data
- Auto-converts JPG to PNG (lossless format required for LSB)
- Visual steganography — changes are invisible to the naked eye
- Capacity check shows how much text fits in the chosen image
- Download result as PNG
All modes:
- 100% Offline: No external requests, works air-gapped
- Zero Dependencies: All libraries embedded inline in
index.html - Single File: Just download and open — no install, no server
The BIP-39 Tool supports binary file download/upload AND base64 string export/import for seamless RFID/NFC workflows:
Byte 0: Marker byte
0x01 = compressed only (no encryption)
0x02 = compressed + AES-256-CBC encrypted
Byte 1–N: Compressed / encrypted data payload
Byte N+1–end: Padding 0x00 bytes to next 4-byte boundary (RFID page alignment)
Why 4-byte padding?
RFID/NFC tags (NTAG, MIFARE Ultralight) read and write in 4-byte pages. Padding ensures smooth read/write operations with any RFID tool. The decoder strips trailing 0x00 bytes automatically.
Base64 strings generated by the "Get Base64" button contain the same data WITHOUT padding:
- More compact than binary files
- Easy to copy/paste for CLI tools
- Compatible with tools like
rfid_op --write "base64string" - Automatic whitespace/newline cleanup on decode
- Enter your text in the BIP-39 Encode tab
- (Optional) Enable AES encryption and set a password
- Click Encode to BIP-39
- Choose your export format:
- 💾 Download Binary — for direct RFID writing tools (with padding)
- 📋 Get Base64 — for CLI tools or remote transmission (no padding)
# Convert to hex for writing
xxd -p bip39-rfid-*.bin | tr -d '\n' > payload.hex
# Write to NTAG216 starting at block 4
chameleon_cli_main.py hf mfu wrbl -b 4 -l <byte_count> -d $(cat payload.hex)# Copy base64 string from browser (Get Base64 button)
# Then use with CLI tools that accept base64:
rfid_op --write "AXicy8nPgUIAF4kESAAAAA=="
# Or decode manually:
echo "AXicy8nPgUIAF4kESAAAAA==" | base64 -d > payload.binOption 1: Binary File Upload
- Dump your RFID tag to a
.binfile:
chameleon_cli_main.py hf mfu dump -f rfid-dump.bin- Go to BIP-39 Decode tab
- Upload the
.binfile using "Load Binary File" - If data was encrypted (marker
0x02): enable decryption and enter your password - Click Decode back to Text
Option 2: Base64 String Decoder
- Read RFID data and convert to base64:
# Read from RFID and convert to base64
rfid_op --read # outputs base64 directly
# or
base64 -w0 rfid-dump.bin- Go to BIP-39 Decode tab
- Click "🔓 Decode Base64 String" button (opens modal)
- Paste the base64 string (whitespace/newlines automatically cleaned)
- If encrypted: enable AES decryption and enter password
- Click "Decode & Decrypt"
The decoder automatically:
- Detects binary vs. text vs. base64 input
- Reads the marker byte to determine format
- Strips RFID
0x00padding bytes (from binary files and base64) - Decrypts (if needed) and decompresses
| Tag | Usable bytes | ~Max plain text |
|---|---|---|
| MIFARE Ultralight | 48 B | ~80–100 chars |
| NTAG213 | 144 B | ~300–400 chars |
| NTAG215 | 504 B | ~1,200–1,500 chars |
| NTAG216 | 888 B | ~2,200–2,800 chars |
Compressed binary
.binfiles are significantly more compact than text formats (words/indices), making them the recommended format for RFID storage.
A separate QR Code Tool mode, completely independent from the BIP-39 encoder/decoder:
-
QR Encode: Generate standard QR codes from any plaintext
- No compression, no special encoding — standard QR format
- Works with ANY QR scanner (phone camera, apps, etc.)
- Error correction level H (high) for durability
- Download as PNG image
⚠️ Security Warning: QR codes store plaintext — anyone scanning it will see your data
-
QR Decode: Upload and decode QR code images
- File upload only (no camera access for privacy)
- Instant text extraction
- Copy decoded text with one click
- Generator Library: qrcodegen by Project Nayuki (MIT License)
- Decoder Library: jsQR by cozmo (Apache 2.0 License)
- 100% Offline: All libraries embedded inline
- Capacity Limit: Up to 1,273 characters (Version 40, ECC Level H, Byte mode)
- Cipher: AES-256-CBC (Web Crypto API — native browser)
- Key Derivation: PBKDF2 with 100,000 iterations, SHA-256
- Salt: 16 bytes (random per encryption)
- IV: 16 bytes (random per encryption)
- Marker:
0x01= unencrypted,0x02= encrypted - Overhead: ~37 bytes minimum (16 salt + 16 IV + 1 marker + AES block padding)
| Original text size | Overhead impact | Recommendation |
|---|---|---|
| < 20 characters | Very high (> 500%) | Consider if encryption is needed |
| 20–50 characters | Moderate (100–200%) | Acceptable for sensitive data |
| 50–200 characters | Low (30–60%) | Good balance |
| > 200 characters | Minimal (< 30%) | Excellent efficiency |
- Offline only: All encryption in-browser via Web Crypto API
- No storage: Passwords never stored, logged, or transmitted
- Non-deterministic: Random salt/IV → different ciphertext each time
- Deterministic (without encryption): Same text → same BIP-39 words
- Data flow:
Text → Compress → Encrypt → BIP-39(optimal compression-before-encryption order)
- LSB Encoding: Least Significant Bit steganography (industry standard)
- Compression: Zlib compression applied before hiding (fits 4× more text)
- Optional AES-256-CBC Encryption: Password-protect hidden data
- Format Support:
- Input: PNG or JPG (auto-converts JPG → PNG)
- Output: PNG only (lossless format required)
- Capacity Display: Shows bytes used vs. available
- Invisible Changes: Modifications undetectable to the human eye (±1 RGB value)
Byte 0: Marker byte (0x01 = compressed, 0x02 = compressed + encrypted)
Byte 1–4: Data length (32-bit big-endian)
Byte 5–N: Compressed / encrypted data payload
- Encoding rate: 3 bits per pixel (R, G, B channels — Alpha channel untouched)
- Capacity formula:
floor((width × height × 3) / 8) − 5 bytes - Example capacities:
- 800×600 image: ~180 KB
- 1920×1080 image: ~777 KB
- 4000×3000 image: ~4.5 MB
- PNG: Lossless — LSB preserved perfectly ✅
- JPG: Lossy — LSB destroyed on re-save ❌
- Solution: Tool auto-converts JPG → PNG on encode
⚠️ If you re-save the output as JPG, the hidden data is permanently destroyed
- Encode: Select image → Enter text → (Optional: enable encryption + password) → Click "Hide Text in Image" → Download PNG
- Decode: Upload stego PNG → (Optional: enter password) → Click "Extract Hidden Text"
The bip39_converter.py script provides the same BIP-39 encode/decode functionality from the command line (compression only — no encryption in CLI).
python bip39_converter.py# Encode
python bip39_converter.py --encode "my super secret password or private key"
# Decode
python bip39_converter.py --decode "fog alone couch below powder"Edit the configuration block at the bottom of bip39_converter.py:
# --- QUICK CONFIGURATION ---
TEXT_TO_ENCODE = """Your text goes here"""
WORDS_TO_DECODE = """"""The web decoder automatically detects the input format:
| Format | Example |
|---|---|
| BIP-39 words | fog alone couch below powder |
| Space-separated indices | 722 55 391 166 1353 |
| Dash-separated indices | 722-55-391-166-1353 |
| 4-digit zero-padded dash indices | 0722-0055-0391-0166-1353 |
| Raw binary file | Upload .bin via "Load Binary File" |
Python CLI:
- Offline: Zero external dependencies (stdlib only)
- No network: No requests of any kind
- Deterministic: Same text → same BIP-39 words
- Compression only: No encryption in CLI version
Web BIP-39 Tool:
- Offline: All libraries inline — zero external requests
- Optional AES-256-CBC Encryption: PBKDF2-based, Web Crypto API
- No storage: Passwords never stored or logged
- Auto-detection: Marker byte determines format automatically on decode
- Deterministic (without encryption): Same text → same words every time
- Non-deterministic (with encryption): Random salt/IV → different ciphertext each run
Web QR Code Tool:
- Offline: qrcodegen (MIT) + jsQR (Apache 2.0) embedded inline
- No camera: File upload only for decoding (privacy-first)
- Plaintext warning: QR codes store uncompressed plaintext
Web Steganography Tool:
- Offline: All processing in Canvas API — zero external requests
- Optional AES-256-CBC: Same encryption system as BIP-39 tool
- No metadata: No proprietary watermarks in output images
- Format security: PNG required (lossless); JPG auto-converted
- Detection warning: Resistant to casual inspection, not professional steganalysis tools
This project is open-source and licensed under the MIT License.
Contributions, bug reports, and feature suggestions are welcome! Feel free to fork, submit Pull Requests, or open Issues.