openssl_encrypt is designed with a Defense in Depth approach. This file is
the single source of truth for the project's security policy — supported
versions, source-code integrity, cryptographic standards, vulnerability
reporting, and advisories. It lives at the repository root (GitHub Security tab)
and is mirrored to the project wiki by the docs-sync jobs.
Our security model doesn't just focus on data confidentiality but emphasizes Metadata Integrity and Quantum Resistance. We believe in transparency; our cryptographic choices are documented to allow public audit and verification.
We take security seriously and provide security updates for the following versions:
| Version | Supported | End of Life |
|---|---|---|
| 1.4.x | ✅ | TBD |
| 1.3.x | ✅ | TBD |
| 1.2.x | ❌ | December 2025 |
| < 1.2 | ❌ | - |
Note: We provide extended security support for both the current major version (1.4.x) and the previous major version (1.3.x). End of life dates will be announced well in advance.
Core cryptographic/security source files are covered by a PGP-signed integrity manifest so tampering can be detected. The manifest is signed by a dedicated source-integrity key (separate from the vulnerability-reporting key below):
- Source-integrity signing key fingerprint:
D269D6A5 D6D7CE52 CE1FC71D C2DF2905 9ED65043 - Key type: Ed25519 (sign-only)
This fingerprint is published here as an out-of-band reference. To verify the
source independently, confirm this fingerprint through a channel other than the
repository, then follow docs/SOURCE_INTEGRITY.md:
gpg --verify openssl_encrypt/integrity/manifest.json.asc \
openssl_encrypt/integrity/manifest.jsonThe built-in
openssl-encrypt verify-integritycommand is a convenience tripwire, not cryptographic proof — the verifier ships in the same package it checks. Only manualgpgverification against an out-of-band fingerprint is authoritative.Note: the source-integrity signing key has been rotated from the development bootstrap key to the production key generated on a trusted machine (fingerprint above); confirm it out-of-band before trusting any verification result.
Production signing-key fingerprint — confirm this through an independent channel (this repo, the GitLab project page, the maintainer's web-of-trust) before trusting any verification result:
D269D6A5D6D7CE52CE1FC71DC2DF29059ED65043
A core requirement of this tool is the cryptographic binding of file metadata (the JSON header) to the encrypted payload, achieved through Authenticated Encryption with Associated Data (AEAD).
AEAD algorithms (full AAD binding) — the Base64-encoded metadata header is cryptographically bound to the ciphertext via Associated Data:
- AES-256-GCM: Standard hardware-accelerated AEAD with AAD binding
- ChaCha20-Poly1305: Software-efficient AEAD with AAD binding
- XChaCha20-Poly1305: Extended-nonce AEAD with AAD binding
- AES-256-SIV: Deterministic AEAD with AAD binding (nonce-misuse resistant)
- AES-GCM-SIV: Misuse-resistant AEAD with AAD binding
- AES-OCB3: OCB mode AEAD with AAD binding
Post-Quantum hybrid algorithms use AEAD ciphers for their symmetric layer:
ML-KEM (512/768/1024, with AES-GCM or ChaCha20-Poly1305), HQC (128/192/256),
MAYO (1/3/5), CROSS (128/192/256), and Kyber (512/768/1024, deprecated naming).
For these: metadata is created before encryption and passed as AAD; any
modification causes authentication failure, and no redundant encrypted_hash is
stored.
Non-AEAD algorithms (hash-based verification): Fernet (internal HMAC, no AAD
per spec) and Camellia (HMAC-SHA256). For these, encrypted_hash is stored in
metadata and verified by hash comparison rather than AAD.
Note on Fernet: Fernet is included for compatibility with the Python
cryptographyecosystem. Payload integrity is guaranteed, but the metadata header is not bound to the token via AAD; hash-based verification is used.
To protect against Cryptographically Relevant Quantum Computers (CRQC), the tool uses a hybrid KEM (Key Encapsulation Mechanism) layer.
- Supported algorithms: ML-KEM, HQC, CROSS, and MAYO.
- Mechanism: the PQC secret is fused with a hardened KDF output (Argon2id / RandomX) to derive the final session key.
To mitigate side-channel and padding-oracle attacks, openssl_encrypt
implements a strict generic error policy:
- Any failure (KDF mismatch, header corruption, or tag-verification failure)
returns an identical
Decryption Failederror. - We do not provide granular error messages that could leak information about the internal state of the cryptographic stack.
We appreciate responsible disclosure of security vulnerabilities. Do not open a public GitHub issue for a security report.
Preferred Method: Use GitHub's private security advisory feature
- Go to the repository's Security tab → "Report a vulnerability"
- Or open one directly: https://github.com/jahlives/openssl_encrypt/security/advisories/new
Alternative Method: Send an encrypted email
- Email: tobster@brain-force.ch
- Strongly recommended: use PGP encryption for sensitive details
- PGP Key Fingerprint:
C8E4 C58E 83AB B314 74C0 E108 0271 3C63 792B 8986 - Key Type: RSA 4096-bit (expires 2029-09-08)
- Download from
keys.openpgp.orgorgpg --recv-keys C8E4C58E83ABB31474C0E10802713C63792B8986
Include in your report: a description of the vulnerability, steps to reproduce, affected versions, potential impact, and any proof-of-concept code.
We are particularly interested in reports concerning:
- Bypassing the AEAD metadata binding
- Flaws in the KDF chain (Argon2id + RandomX fusion)
- Implementation errors in the PQC wrappers
- Initial Response: within 48 hours we acknowledge receipt
- Status Updates: every 7 days on our progress
- Resolution Timeline: we aim to resolve critical issues within 30 days
- Disclosure: we follow coordinated-disclosure practices
- Triage: verify and assess severity
- Fix Development: develop and test a fix
- Release: release a security patch for supported versions
- Announcement: publish a security advisory with proper credit
- CVE Assignment: critical vulnerabilities receive CVE identifiers
Accepted vulnerabilities are fixed in the next security release, documented in our advisories, and credited to the reporter (unless anonymity is preferred). Declined reports receive a detailed explanation and configuration guidance where relevant.
Severity: High (CVSSv3 8.1) · CWE-330 (Use of Insufficiently Random Values) Affected Versions: all versions using multi-round KDF configurations on format versions ≤ 6/8 (rounds > 1) Fixed In: secure chained salt derivation — Format Version 7 (v1.3.4, 1.3.x line) and Format Version 9 (v1.4.1, 1.4.x line); the two implementations are unified and equivalent.
Summary: in the affected format versions, each round's salt for multi-round KDFs was derived predictably from the base salt stored in plaintext metadata:
# VULNERABLE
round_salt = SHA256(base_salt + str(round_number).encode()).digest()[:16]Because base_salt is in plaintext metadata, an attacker with the encrypted
file could precompute all round salts, build per-round rainbow tables, and
parallelize cracking across rounds — so additional rounds did not increase
effective security as intended.
Affected components: Argon2 (id/i/d), PBKDF2, Scrypt, Balloon, HKDF, and the multi-round hash modes (BLAKE3, BLAKE2b, SHAKE-256).
Fix — secure chained salt derivation:
# SECURE
round_salt = base_salt if round_num == 0 else previous_output[:16]Each round now depends on the previous round's output, making precomputation impossible (round N requires rounds 0…N-1) and forcing sequential computation per password guess.
Mitigation:
- Upgrade to a fixed version (v1.3.4+ / v1.4.1+).
- Re-encrypt sensitive files that used multi-round KDF settings so they adopt the
fixed format. Check the format with
openssl_encrypt info -i file.enc. - Backward compatible: fixed releases still decrypt older format versions.
Disclosure: discovered during an internal security audit; fixed before any third-party disclosure. Credit: internal security review.
References: Format Version 9 Specification, Migration Guide.
We recognize and thank security researchers for responsible disclosure:
No vulnerabilities reported yet. Be the first!
- Keep your installation up to date
- Use strong passwords and passphrases
- Enable post-quantum encryption for long-term data protection
- Verify signatures when using the keyserver
- Use HSM plugins for production key management
- Run regular security audits of your encryption workflows
OpenSSL Encrypt includes multiple security layers:
- Post-Quantum Cryptography: ML-KEM and ML-DSA algorithms
- Cascade Encryption: multiple cipher layers for defense in depth
- Key Derivation: Argon2 for password-based keys
- Signature Verification: authenticated key distribution
- Format Versioning: forward-compatible security improvements
- HSM Support: hardware security module integration
For general security questions (not vulnerabilities), open a discussion on GitHub or contact us at tobster@brain-force.ch.