CWE-328: Use of Weak Hash
Overview
Weak cryptographic hashes (MD5, SHA-1) are broken and vulnerable to collision attacks, enabling attackers to forge signatures, create malicious files with same hash, and crack hashed passwords. Modern applications must use SHA-256+ for integrity and bcrypt/Argon2 for passwords.
OWASP Classification
A04:2025 - Cryptographic Failures
Risk
High: Weak hashes enable collision attacks (two inputs producing same hash), rainbow table attacks on passwords, forged digital signatures, compromised file integrity verification, and fast brute-force cracking of password hashes due to speed of MD5/SHA-1.
Remediation Steps
Core principle: Use appropriate cryptographic hashes; never use fast hashes for passwords or security-critical derivations.
Locate the weak hash usage in your code
- Review the flaw details to identify the specific file, line number, and code pattern using weak hashing
- Identify which weak hash is in use: MD5, SHA-1, or plain SHA-256 for passwords
- Determine the purpose: password storage, file integrity, digital signatures, HMAC, checksums
- Trace the data flow to understand what is being hashed and how the hash is used
Use strong hashes for different purposes (Primary Defense)
- For Passwords:
- Use bcrypt (cost factor 12+), Argon2id (memory-hard), or PBKDF2-HMAC-SHA256 (600k+ iterations)
- NEVER use MD5, SHA-1, or plain SHA-256 for passwords (too fast, enables brute-force)
- For Integrity/Checksums:
- Use SHA-256, SHA-384, SHA-512, SHA-3 (Keccak), BLAKE2, or BLAKE3
- NOT MD5 or SHA-1 (vulnerable to collision attacks)
- For HMAC/Signatures:
- Use HMAC-SHA256 or stronger (HMAC-SHA384, HMAC-SHA512)
- Avoid HMAC-MD5 for new designs; MD5 is deprecated even though HMAC-MD5 is not affected by plain MD5 collision attacks in the same way
Understand hash use cases and select appropriately
- Passwords: Use slow, adaptive hashing (Argon2id, bcrypt, scrypt, or PBKDF2 when required for FIPS-aligned environments)
- File integrity: Use collision-resistant hash (SHA-256 for checksums, file verification)
- Message authentication: Use HMAC with strong hash (HMAC-SHA256 for API signatures, JWT)
- Digital signatures: Use SHA-256+ with RSA/ECDSA (SHA-256, SHA-384 for signing documents)
Migrate from weak hashes
- Re-hash on user login (transparent upgrade): On successful login with old hash, re-hash password with bcrypt and update database
- Force password reset for immediate migration: For critical systems, require all users to reset passwords
- Use dual-hash during transition period: Support both old and new hash formats during migration
- Update all hash generation code: Replace all MD5/SHA-1 calls with appropriate strong alternatives
Configure appropriate work factors
- bcrypt: choose the highest cost factor that meets your authentication latency target; cost 12+ is a common baseline
- Argon2id: follow current password-storage guidance, starting at least at OWASP's minimum settings and tuning memory/time cost on production-class hardware
- PBKDF2-HMAC-SHA256: use 600,000+ iterations where PBKDF2 is required
- Adjust based on performance requirements: test login time and tune for your production environment
Test the hash migration thoroughly
- Verify weak hashes are no longer used (grep for MD5, SHA1 in codebase)
- Test password verification with new hash algorithm (login should work)
- Test migration path for existing users (old passwords should upgrade on login)
- Verify file integrity checks use strong hashes (SHA-256+)
- Performance test: ensure acceptable login times with new work factors
- Re-scan with security scanner to confirm the issue is resolved
Common Vulnerable Patterns
- MD5 for password hashing
- SHA-1 for digital signatures
- Plain SHA-256 for passwords (too fast)
- md5() or sha1() without salt
- Fast hashes for password storage