- Full Windows parity (VirtualLock + VirtualProtect in secure_alloc.rs / memory_guard.py)
- Status: Fully Implemented
- Is it correctly wired into production paths? Yes
- Reachability: production
- Evidence: meow_decoder/memory_guard.py, crypto_core/src/secure_alloc.rs
- Any remaining weakness, stub, or incomplete integration? None observed in these paths.
- Mandatory ML-DSA manifest signing + full PQ ratchet beacon (ML-KEM-1024 integrated into ratchet path)
- Status: Fully Implemented
- Is it correctly wired into production paths? Yes
- Reachability: production
- Evidence: Mandatory signing in meow_decoder/manifest_signing.py; encoder fail-closed on missing ML-DSA backend in meow_decoder/encode.py; decoder enforces signature by default in meow_decoder/decode_gif.py. PQ ratchet beacon logic exists in meow_decoder/ratchet.py and meow_decoder/ratchet.py. Encoder now passes
receiver_pq_public_key(ML-KEM-1024 keys only, 1568 bytes) toEncoderRatchetin meow_decoder/encode.py; decoder now constructs aPQBeaconKeyPairfrom theHybridKeyPairand passes it asreceiver_pq_keypairtoDecoderRatchetvia_ratchet_paramsin meow_decoder/decode_gif.py. - Any remaining weakness, stub, or incomplete integration? Signing can be disabled via
MEOW_MANIFEST_SIGNING=off, which weakens mandatory enforcement (meow_decoder/decode_gif.py). PQ ratchet beacons are silently skipped for ML-KEM-768 keys (1184 bytes) since the beacon implementation is ML-KEM-1024-only; paranoid mode (--paranoid) is required for PQ ratchet beacons.
- On-screen randomized keyboard + mouse-gesture password auth (full working implementation)
- Status: Fully Implemented
- Is it correctly wired into production paths? Yes
- Reachability: production
- Evidence: Randomized on-screen keyboard and mouse-gesture implementation in meow_decoder/secure_keyboard.py; CLI password modes invoking secure keyboard and mouse gesture in meow_decoder/encode.py.
- Any remaining weakness, stub, or incomplete integration? None observed.
- Active tamper detection + silent poisoning (fail-closed, no side-effect leaks)
- Status: Fully Implemented
- Is it correctly wired into production paths? Yes (PyInstaller runtime)
- Reachability: production (packed binary), optional in non-packed runs
- Evidence: Poison output path in meow_decoder/tamper_detection.py; runtime hook aborts on tamper detection in scripts/pyinstaller_runtime_hook.py.
- Any remaining weakness, stub, or incomplete integration? Tamper protections are activated automatically only in the PyInstaller runtime hook; non-packed executions rely on manual invocation.
- Adversarial carrier generation + stego algorithm rotation (integrated into encode path)
- Status: Partially Implemented
- Is it correctly wired into production paths? Yes, but only when stego is enabled and set to PARANOID level
- Reachability: production (optional path)
- Evidence: Rotation schedule and adversarial embed in meow_decoder/stego_advanced.py; encode path applies stego pipeline in meow_decoder/encode.py.
- Any remaining weakness, stub, or incomplete integration? Rotation and adversarial embedding only occur at PARANOID level; default stego levels do not invoke adversarial noise.
- Shamir-style multi-GIF split redundancy (threshold secret sharing with CLI workflow)
- Status: Fully Implemented
- Is it correctly wired into production paths? Yes
- Reachability: production
- Evidence: Shamir split implementation in meow_decoder/shamir_split.py; CLI flags and split-to-files integration in meow_decoder/encode.py.
- Any remaining weakness, stub, or incomplete integration? None observed.
- Portable single-executable mode + isolation checks (PyInstaller single binary + env safety)
- Status: Fully Implemented
- Is it correctly wired into production paths? Yes for PyInstaller builds; optional for non-packed runs
- Reachability: production (packed binary), optional in standard Python runs
- Evidence: PyInstaller runtime hook and env safety inclusion in meow_decoder.spec; runtime hook enforces env safety and tamper checks in scripts/pyinstaller_runtime_hook.py; strict isolation path in meow_decoder/main.py.
- Any remaining weakness, stub, or incomplete integration? Non-packed runs do not automatically enable env_safety unless
MEOW_STRICT_ISOLATION=1is set.
- Expanded formal verification (Verus proofs for timing/expiry/tamper/secure_alloc) + public bounty program in README
- Status: Partially Implemented
- Is it correctly wired into production paths? Formal artifacts are present; no runtime wiring needed
- Reachability: docs-only for proofs; policy is public
- Evidence: Formal methods overview in formal/README.md; Verus guarded-buffer proofs in crypto_core/src/verus_guarded_buffer.rs; timing uniformity notes in crypto_core/src/verus_kdf_proofs.rs. Public bounty program in README.md and SECURITY.md.
- Any remaining weakness, stub, or incomplete integration? Verus AEAD proofs are explicitly described as stubs in crypto_core/src/lib.rs, and SECURITY_INVARIANTS confirms AEAD proofs are not Verus-proven (docs/SECURITY_INVARIANTS.md). No Verus proofs for expiry or tamper were located (NOT FOUND).
-
AES-GCM nonce generation and reuse prevention
- Status: Mixed
- Findings: Observed random nonce generation in production encrypt path, not deterministic HKDF nonces as described in protocol docs. Observed per-process reuse guard.
- Severity: Medium
- Evidence / reachability: Random nonces in production encryption meow_decoder/crypto.py; deterministic NonceGenerator exists but is not referenced in production meow_decoder/nonce.py; protocol doc claims deterministic HKDF-derived nonce docs/PROTOCOL.md.
-
Argon2id usage and domain separation
- Status: Implemented
- Findings: Observed Argon2id parameters from presets and handle-based derivation; observed domain separation constants for HMAC and keyfile mixing.
- Severity: Low
- Evidence / reachability: Presets and parameters in meow_decoder/crypto.py; canonical AAD layout and domain separation constants in meow_decoder/crypto.py; handle-based derivation in meow_decoder/crypto.py.
-
Ratchet forward secrecy (including PQ beacon integration)
- Status: Implemented
- Findings: Ratchet supports asymmetric rekey and PQ hybrid fold with ML-KEM-1024. Production CLI now wires ML-KEM-1024 key material into both
EncoderRatchetandDecoderRatchetwhen paranoid PQ mode is used. - Severity: Low
- Evidence / reachability: PQ beacon logic in meow_decoder/ratchet.py and meow_decoder/ratchet.py; encoder now passes
receiver_pq_public_keytoEncoderRatchetmeow_decoder/encode.py; decoder now passesreceiver_pq_keypair(asPQBeaconKeyPair) toDecoderRatchetvia_ratchet_paramsmeow_decoder/decode_gif.py.
-
Manifest signing, AAD binding, and HMAC verification
- Status: Implemented
- Findings: Observed canonical AAD construction includes mode byte and optional PQ/FS fields; observed HMAC verified in decode before decryption; observed signing enforced by default and fail-closed.
- Severity: Low
- Evidence / reachability: AAD construction in meow_decoder/crypto.py; HMAC verification in decode path meow_decoder/decode_gif.py; signing enforcement in meow_decoder/encode.py and meow_decoder/decode_gif.py.
-
Zeroization and memory wiping reliability
- Status: Implemented (best-effort in Python, stronger in Rust)
- Findings: Observed secure_zero_memory invoked for sensitive buffers; observed ratchet finalize zeroizes and drops handles.
- Severity: Medium
- Evidence / reachability: Python zeroization in meow_decoder/crypto.py; ratchet state zeroization in meow_decoder/ratchet.py and meow_decoder/ratchet.py; Verus guarded-buffer proofs in crypto_core/src/verus_guarded_buffer.rs.
-
Constant-time guarantees across decode paths
- Status: Implemented (best-effort)
- Findings: Observed constant-time compare via Rust backend, with timing equalization on HMAC checks.
- Severity: Medium
- Evidence / reachability: constant_time_compare in meow_decoder/constant_time.py; equalize_timing in meow_decoder/constant_time.py; HMAC verification uses constant_time_compare and equalize_timing in meow_decoder/crypto.py and meow_decoder/decode_gif.py.
-
Side-channel leaks (timing, cache, branch prediction)
- Status: Partially mitigated
- Findings: Assumption that Rust backend provides constant-time primitives; observed equalize_timing used to reduce timing variance but no formal side-channel guarantees are provided.
- Severity: Medium
- Evidence / reachability: equalize_timing in meow_decoder/constant_time.py; timing uniformity notes in crypto_core/src/verus_kdf_proofs.rs.
-
Adversarial carrier generation and stego algorithm rotation
- Status: Implemented (Paranoid mode only)
- Findings: Observed rotation schedule and adversarial carrier embedding used when stealth level is PARANOID.
- Severity: Low
- Evidence / reachability: rotation and adversarial embed in meow_decoder/stego_advanced.py; encode path calls stego pipeline in meow_decoder/encode.py.
-
Statistical indistinguishability (single vs dual mode, inter-file correlation)
- Status: Best-effort
- Findings: Observed adversarial carrier module explicitly documents limitations; no evidence of formal indistinguishability proof.
- Severity: Medium
- Evidence / reachability: limitations and threat model in meow_decoder/adversarial_carrier.py.
-
Fixed-size padding, fixed QR parameters, decorrelation
- Status: Partially implemented
- Findings: Observed length padding at encryption; QR parameters are configurable rather than fixed.
- Severity: Low
- Evidence / reachability: length padding in production encrypt path meow_decoder/crypto.py; QR parameters configured in encoder meow_decoder/encode.py.
-
Resistance to common steganalysis techniques
- Status: Best-effort
- Findings: Observed adversarial carrier noise targets chi-square and LSB steganalysis but explicitly notes detection is still possible.
- Severity: Medium
- Evidence / reachability: adversarial carrier threat model and limitations meow_decoder/adversarial_carrier.py.
-
Finding: PQ ratchet beacons are now wired into production CLI paths. (FIXED)
- Severity: Resolved
- Evidence: Encoder passes ML-KEM-1024 public key as
receiver_pq_public_keytoEncoderRatchetmeow_decoder/encode.py; decoder convertsHybridKeyPairtoPQBeaconKeyPairand passes asreceiver_pq_keypairin_ratchet_paramstoDecoderRatchetmeow_decoder/decode_gif.py. Keys are only wired for ML-KEM-1024 (1568-byte public key, paranoid mode); ML-KEM-768 silently skips PQ beacons.
-
Finding: Protocol documentation claims deterministic HKDF nonces, but production encryption uses random nonces.
- Severity: Medium
- Evidence / reachability: protocol nonce derivation docs/PROTOCOL.md; random nonce generation in production encryption meow_decoder/crypto.py.
-
Finding: Environment safety checks are enforced only in PyInstaller runtime hook or when
MEOW_STRICT_ISOLATION=1is set.- Severity: Medium
- Evidence / reachability: runtime hook scripts/pyinstaller_runtime_hook.py; optional strict isolation path in meow_decoder/main.py.
-
Finding: Manifest signing can be disabled via environment policy, weakening mandatory guarantees.
- Severity: Medium
- Evidence / reachability: policy toggle in meow_decoder/decode_gif.py.
-
Overclaim/inconsistency: README states post-quantum is default while threat model says PQ requires explicit opt-in.
- Quote: "ML-KEM-768 (default, Signal PQXDH)" in README.md
- Counter-evidence: "not default; requires explicit opt-in" in docs/THREAT_MODEL.md
- Corrected wording (prose): Post-quantum features are available but only enabled when the user sets
--pq(and--paranoidfor ML-KEM-1024), not by default.
-
Overclaim/inconsistency: Protocol spec mandates deterministic HKDF nonces, while production encryption uses random nonces.
- Quote: "Nonce: 12 bytes deterministic via HKDF" in docs/PROTOCOL.md
- Counter-evidence: random nonce generation in meow_decoder/crypto.py
- Corrected wording (prose): Production encryption currently uses random 96-bit nonces with a reuse guard; deterministic HKDF nonces are implemented in nonce.py but not used in the main encrypt path.
-
Overclaim/inconsistency: Formal verification claims vs implementation notes.
- Quote: "Verus ... Complete" in formal/README.md
- Counter-evidence: "Verus proofs are stubs" for AEAD in crypto_core/src/lib.rs and SECURITY_INVARIANTS notes AEAD proofs are not Verus-proven docs/SECURITY_INVARIANTS.md
- Corrected wording (prose): Verus proofs are complete for guarded-buffer memory safety; AEAD proofs are not machine-checked and are enforced via type system and tests.
- Overall security score out of 10 (conservative): 7.7/10
- Is the current implementation ready for high-stakes use? No, not without resolving the nonce-specification mismatch between code and documentation.
- Remaining Critical/High issues that must be addressed before release:
- Medium: Protocol documentation claims deterministic HKDF nonces, but production encryption uses random nonces (docs/PROTOCOL.md, meow_decoder/crypto.py).
- Resolved issues:
- FIXED (was High): PQ ratchet beacons now wired into production encode/decode flows: encoder passes ML-KEM-1024 key via
receiver_pq_public_key, decoder constructsPQBeaconKeyPairand passes viareceiver_pq_keypairin_ratchet_params.
- FIXED (was High): PQ ratchet beacons now wired into production encode/decode flows: encoder passes ML-KEM-1024 key via
- One-sentence recommendation before release: Align nonce derivation behavior between code and protocol documentation (either document that random nonces are intentional or wire in the existing deterministic
NonceGenerator).