Use of Insufficient Cryptographic Key Lengths

High Risk Cryptographic Security
key-lengthencryption-keysrsa-keysaes-keyscryptographic-strengthbrute-force-attacksquantum-resistancekey-sizecomputational-security

What it is

A critical vulnerability where applications use cryptographic keys that are too short to provide adequate security against modern computational attacks. Insufficient key lengths make encrypted data vulnerable to brute force attacks, especially with advances in computing power and specialized hardware like GPUs and quantum computers.

# Python - VULNERABLE: SSL/TLS server with weak cryptographic configuration
import ssl
import socket
import threading
from cryptography import x509
from cryptography.x509.oid import NameOID
from cryptography.hazmat.primitives import hashes, serialization
from cryptography.hazmat.primitives.asymmetric import rsa
import datetime

class VulnerableSSLServer:
    def __init__(self, host='localhost', port=8443):
        self.host = host
        self.port = port
        self.cert_file = 'weak_server.crt'
        self.key_file = 'weak_server.key'
        
        # Generate weak certificate and key
        self.generate_weak_certificate()
    
    def generate_weak_certificate(self):
        """VULNERABLE: Generate certificate with weak RSA key"""
        # VULNERABLE: 1024-bit RSA key
        private_key = rsa.generate_private_key(
            public_exponent=65537,
            key_size=1024,  # WEAK: Should be 2048+ bits
        )
        
        # Create self-signed certificate
        subject = issuer = x509.Name([
            x509.NameAttribute(NameOID.COUNTRY_NAME, u"US"),
            x509.NameAttribute(NameOID.STATE_OR_PROVINCE_NAME, u"State"),
            x509.NameAttribute(NameOID.LOCALITY_NAME, u"City"),
            x509.NameAttribute(NameOID.ORGANIZATION_NAME, u"Test Org"),
            x509.NameAttribute(NameOID.COMMON_NAME, u"localhost"),
        ])
        
        cert = x509.CertificateBuilder().subject_name(
            subject
        ).issuer_name(
            issuer
        ).public_key(
            private_key.public_key()
        ).serial_number(
            x509.random_serial_number()
        ).not_valid_before(
            datetime.datetime.utcnow()
        ).not_valid_after(
            datetime.datetime.utcnow() + datetime.timedelta(days=365)
        ).sign(private_key, hashes.SHA256())
        
        # Save certificate and private key
        with open(self.cert_file, 'wb') as f:
            f.write(cert.public_bytes(serialization.Encoding.PEM))
        
        with open(self.key_file, 'wb') as f:
            f.write(private_key.private_bytes(
                encoding=serialization.Encoding.PEM,
                format=serialization.PrivateFormat.PKCS8,
                encryption_algorithm=serialization.NoEncryption()
            ))
    
    def create_weak_ssl_context(self):
        """VULNERABLE: SSL context with weak configuration"""
        context = ssl.SSLContext(ssl.PROTOCOL_TLS_SERVER)
        
        # VULNERABLE: Allow weak protocols and ciphers
        context.minimum_version = ssl.TLSVersion.TLSv1  # Allow TLS 1.0
        context.maximum_version = ssl.TLSVersion.TLSv1_2  # Don't use TLS 1.3
        
        # VULNERABLE: Allow weak cipher suites
        context.set_ciphers('ALL:!aNULL:!eNULL:!EXPORT:!DES:!RC4:!MD5:!PSK:!SRP:!CAMELLIA')
        
        # Load weak certificate
        context.load_cert_chain(self.cert_file, self.key_file)
        
        # VULNERABLE: Don't enforce strong security
        context.check_hostname = False
        context.verify_mode = ssl.CERT_NONE
        
        return context
    
    def handle_client(self, conn, addr):
        """Handle client connection with weak crypto"""
        try:
            print(f"Connected by {addr}")
            
            # Get cipher info
            cipher = conn.cipher()
            if cipher:
                print(f"Cipher: {cipher[0]}, Version: {cipher[1]}, Bits: {cipher[2]}")
            
            # Simple HTTP response
            response = (
                "HTTP/1.1 200 OK\r\n"
                "Content-Type: text/html\r\n"
                "Content-Length: 100\r\n"
                "\r\n"
                "<html><body><h1>Weak SSL Server</h1><p>Using weak cryptographic keys!</p></body></html>"
            )
            
            conn.send(response.encode())
            
        except Exception as e:
            print(f"Error handling client: {e}")
        finally:
            conn.close()
    
    def start_server(self):
        """Start the vulnerable SSL server"""
        context = self.create_weak_ssl_context()
        
        with socket.socket(socket.AF_INET, socket.SOCK_STREAM) as sock:
            sock.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
            sock.bind((self.host, self.port))
            sock.listen(5)
            
            print(f"Vulnerable SSL server listening on {self.host}:{self.port}")
            
            with context.wrap_socket(sock, server_side=True) as ssock:
                while True:
                    try:
                        conn, addr = ssock.accept()
                        client_thread = threading.Thread(
                            target=self.handle_client,
                            args=(conn, addr)
                        )
                        client_thread.start()
                    except KeyboardInterrupt:
                        break
                    except Exception as e:
                        print(f"Server error: {e}")

class VulnerableSSLClient:
    def __init__(self):
        pass
    
    def connect_with_weak_validation(self, host, port):
        """VULNERABLE: Client that accepts weak certificates"""
        # VULNERABLE: Create context that accepts weak crypto
        context = ssl.create_default_context()
        context.check_hostname = False
        context.verify_mode = ssl.CERT_NONE
        
        # VULNERABLE: Allow weak protocols
        context.minimum_version = ssl.TLSVersion.TLSv1
        
        # VULNERABLE: Allow weak ciphers
        context.set_ciphers('ALL')
        
        try:
            with socket.socket(socket.AF_INET, socket.SOCK_STREAM) as sock:
                with context.wrap_socket(sock, server_hostname=host) as ssock:
                    ssock.connect((host, port))
                    
                    print(f"Connected to {host}:{port}")
                    
                    # Get connection info
                    cipher = ssock.cipher()
                    if cipher:
                        print(f"Negotiated cipher: {cipher[0]}")
                        print(f"Protocol version: {cipher[1]}")
                        print(f"Key bits: {cipher[2]}")
                    
                    # Send HTTP request
                    request = "GET / HTTP/1.1\r\nHost: localhost\r\n\r\n"
                    ssock.send(request.encode())
                    
                    # Receive response
                    response = ssock.recv(1024).decode()
                    print(f"Response: {response[:100]}...")
                    
        except Exception as e:
            print(f"Client connection error: {e}")

# Vulnerable key generation utilities
class WeakKeyGeneration:
    @staticmethod
    def generate_weak_rsa_keys():
        """Generate multiple weak RSA keys"""
        weak_sizes = [512, 768, 1024]  # All weak
        
        for size in weak_sizes:
            print(f"Generating {size}-bit RSA key (WEAK)")
            
            private_key = rsa.generate_private_key(
                public_exponent=65537,
                key_size=size
            )
            
            # Save weak keys
            key_filename = f'weak_rsa_{size}.pem'
            with open(key_filename, 'wb') as f:
                f.write(private_key.private_bytes(
                    encoding=serialization.Encoding.PEM,
                    format=serialization.PrivateFormat.PKCS8,
                    encryption_algorithm=serialization.NoEncryption()
                ))
            
            print(f"Saved weak {size}-bit key to {key_filename}")
    
    @staticmethod
    def generate_weak_symmetric_keys():
        """Generate weak symmetric keys"""
        import os
        
        # Various weak key sizes
        weak_key_sizes = {
            'des': 8,      # 64-bit (56 effective)
            'aes128': 16,  # 128-bit (weak for long-term)
            'custom64': 8, # Custom 64-bit
        }
        
        for name, size in weak_key_sizes.items():
            key = os.urandom(size)
            print(f"Generated {name} key: {size} bytes ({size * 8} bits)")
            
            with open(f'weak_{name}_key.bin', 'wb') as f:
                f.write(key)

if __name__ == '__main__':
    # Generate weak keys
    print("Generating weak cryptographic keys...")
    WeakKeyGeneration.generate_weak_rsa_keys()
    WeakKeyGeneration.generate_weak_symmetric_keys()
    
    # Start vulnerable server (uncomment to run)
    # server = VulnerableSSLServer()
    # server.start_server()
# Python - SECURE: SSL/TLS server with strong cryptographic configuration
import ssl
import socket
import threading
import secrets
import os
from cryptography import x509
from cryptography.x509.oid import NameOID, ExtensionOID
from cryptography.hazmat.primitives import hashes, serialization
from cryptography.hazmat.primitives.asymmetric import rsa, ec
from cryptography.hazmat.primitives.ciphers.aead import AESGCM
import datetime
import ipaddress

class SecureSSLServer:
    def __init__(self, host='localhost', port=8443):
        self.host = host
        self.port = port
        self.cert_file = 'secure_server.crt'
        self.key_file = 'secure_server.key'
        
        # Generate strong certificate and key
        self.generate_secure_certificate()
    
    def generate_secure_certificate(self, key_type='rsa', rsa_key_size=3072):
        """SECURE: Generate certificate with strong cryptographic keys"""
        if key_type == 'rsa':
            if rsa_key_size < 2048:
                raise ValueError("RSA key size must be at least 2048 bits")
            
            # SECURE: Generate strong RSA key (3072+ bits)
            private_key = rsa.generate_private_key(
                public_exponent=65537,
                key_size=rsa_key_size,
            )
            print(f"Generated {rsa_key_size}-bit RSA key")
            
        elif key_type == 'ecdsa':
            # SECURE: Use strong elliptic curve (P-384)
            private_key = ec.generate_private_key(ec.SECP384R1())
            print("Generated ECDSA key with P-384 curve")
        
        else:
            raise ValueError("Unsupported key type")
        
        # Create comprehensive certificate with security extensions
        subject = x509.Name([
            x509.NameAttribute(NameOID.COUNTRY_NAME, u"US"),
            x509.NameAttribute(NameOID.STATE_OR_PROVINCE_NAME, u"State"),
            x509.NameAttribute(NameOID.LOCALITY_NAME, u"City"),
            x509.NameAttribute(NameOID.ORGANIZATION_NAME, u"Secure Org"),
            x509.NameAttribute(NameOID.COMMON_NAME, self.host),
        ])
        
        # Create certificate with security best practices
        cert_builder = x509.CertificateBuilder().subject_name(
            subject
        ).issuer_name(
            subject  # Self-signed
        ).public_key(
            private_key.public_key()
        ).serial_number(
            x509.random_serial_number()
        ).not_valid_before(
            datetime.datetime.utcnow()
        ).not_valid_after(
            datetime.datetime.utcnow() + datetime.timedelta(days=365)
        )
        
        # Add security extensions
        cert_builder = cert_builder.add_extension(
            x509.SubjectAlternativeName([
                x509.DNSName(self.host),
                x509.DNSName("*." + self.host),
                x509.IPAddress(ipaddress.IPv4Address('127.0.0.1')),
            ]),
            critical=False,
        ).add_extension(
            x509.KeyUsage(
                digital_signature=True,
                key_encipherment=True,
                content_commitment=False,
                data_encipherment=False,
                key_agreement=False,
                key_cert_sign=True,
                crl_sign=False,
                encipher_only=False,
                decipher_only=False
            ),
            critical=True,
        ).add_extension(
            x509.ExtendedKeyUsage([
                x509.oid.ExtendedKeyUsageOID.SERVER_AUTH,
                x509.oid.ExtendedKeyUsageOID.CLIENT_AUTH,
            ]),
            critical=True,
        )
        
        # Sign with strong hash algorithm
        cert = cert_builder.sign(private_key, hashes.SHA256())
        
        # Save certificate and private key securely
        with open(self.cert_file, 'wb') as f:
            f.write(cert.public_bytes(serialization.Encoding.PEM))
        
        # Save private key with secure permissions
        with open(self.key_file, 'wb') as f:
            f.write(private_key.private_bytes(
                encoding=serialization.Encoding.PEM,
                format=serialization.PrivateFormat.PKCS8,
                encryption_algorithm=serialization.NoEncryption()
            ))
        
        # Set secure file permissions (Unix-like systems)
        try:
            os.chmod(self.key_file, 0o600)  # Read/write for owner only
            os.chmod(self.cert_file, 0o644)  # Read for all, write for owner
        except:
            pass  # Permissions not available on all systems
    
    def create_secure_ssl_context(self):
        """SECURE: SSL context with strong configuration"""
        context = ssl.SSLContext(ssl.PROTOCOL_TLS_SERVER)
        
        # SECURE: Require strong TLS versions only
        context.minimum_version = ssl.TLSVersion.TLSv1_2  # TLS 1.2 minimum
        context.maximum_version = ssl.TLSVersion.TLSv1_3  # TLS 1.3 preferred
        
        # SECURE: Configure strong cipher suites only
        # Prefer AEAD ciphers, strong key exchange, and forward secrecy
        strong_ciphers = ':'.join([
            'ECDHE+AESGCM',
            'ECDHE+CHACHA20',
            'DHE+AESGCM',
            'DHE+CHACHA20',
            '!aNULL',
            '!eNULL',
            '!EXPORT',
            '!DES',
            '!RC4',
            '!MD5',
            '!PSK',
            '!SRP',
            '!CAMELLIA',
            '!SEED'
        ])
        
        context.set_ciphers(strong_ciphers)
        
        # Load strong certificate
        context.load_cert_chain(self.cert_file, self.key_file)
        
        # SECURE: Enable security features
        context.check_hostname = False  # Self-signed cert
        context.verify_mode = ssl.CERT_NONE  # For demo - use CERT_REQUIRED in production
        
        # Enable perfect forward secrecy
        context.options |= ssl.OP_SINGLE_DH_USE
        context.options |= ssl.OP_SINGLE_ECDH_USE
        
        # Disable compression (CRIME attack prevention)
        context.options |= ssl.OP_NO_COMPRESSION
        
        # Set secure DH parameters
        try:
            context.load_dh_params('dhparam.pem')  # Generate with: openssl dhparam -out dhparam.pem 2048
        except:
            pass  # Will use default DH parameters
        
        return context
    
    def handle_client(self, conn, addr):
        """Handle client connection with security monitoring"""
        try:
            print(f"Secure connection from {addr}")
            
            # Get and validate cipher info
            cipher = conn.cipher()
            if cipher:
                cipher_name, tls_version, key_bits = cipher
                print(f"Negotiated cipher: {cipher_name}")
                print(f"TLS version: {tls_version}")
                print(f"Key strength: {key_bits} bits")
                
                # Validate minimum security requirements
                if key_bits < 128:
                    print("WARNING: Weak cipher negotiated!")
                    conn.close()
                    return
                
                if 'TLSv1.' not in tls_version or tls_version in ['TLSv1.0', 'TLSv1.1']:
                    print("WARNING: Weak TLS version!")
                    conn.close()
                    return
            
            # Get certificate information
            peer_cert = conn.getpeercert()
            if peer_cert:
                print(f"Client certificate: {peer_cert.get('subject', 'None')}")
            
            # Secure HTTP response with security headers
            response = (
                "HTTP/1.1 200 OK\r\n"
                "Content-Type: text/html\r\n"
                "Content-Length: 150\r\n"
                "Strict-Transport-Security: max-age=31536000; includeSubDomains\r\n"
                "X-Content-Type-Options: nosniff\r\n"
                "X-Frame-Options: DENY\r\n"
                "Content-Security-Policy: default-src 'self'\r\n"
                "\r\n"
                "<html><body><h1>Secure SSL Server</h1>"
                f"<p>Connected with {cipher_name} ({key_bits} bits)</p>"
                "<p>Using strong cryptographic keys!</p></body></html>"
            )
            
            conn.send(response.encode())
            
        except ssl.SSLError as e:
            print(f"SSL error: {e}")
        except Exception as e:
            print(f"Error handling client: {e}")
        finally:
            conn.close()
    
    def start_server(self):
        """Start the secure SSL server"""
        context = self.create_secure_ssl_context()
        
        with socket.socket(socket.AF_INET, socket.SOCK_STREAM) as sock:
            sock.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
            sock.bind((self.host, self.port))
            sock.listen(5)
            
            print(f"Secure SSL server listening on {self.host}:{self.port}")
            print("Using strong cryptographic configuration:")
            print("- TLS 1.2+ only")
            print("- Strong cipher suites")
            print("- Perfect Forward Secrecy")
            print("- 3072-bit RSA or ECDSA P-384")
            
            with context.wrap_socket(sock, server_side=True) as ssock:
                while True:
                    try:
                        conn, addr = ssock.accept()
                        client_thread = threading.Thread(
                            target=self.handle_client,
                            args=(conn, addr)
                        )
                        client_thread.daemon = True
                        client_thread.start()
                    except KeyboardInterrupt:
                        print("\nShutting down secure server...")
                        break
                    except Exception as e:
                        print(f"Server error: {e}")

class SecureSSLClient:
    def __init__(self):
        self.min_key_bits = 128  # Minimum acceptable key strength
        self.allowed_protocols = ['TLSv1.2', 'TLSv1.3']
    
    def create_secure_context(self):
        """Create secure SSL context for client"""
        context = ssl.create_default_context()
        
        # SECURE: Require strong protocols
        context.minimum_version = ssl.TLSVersion.TLSv1_2
        
        # SECURE: Use strong cipher suites
        strong_ciphers = ':'.join([
            'ECDHE+AESGCM',
            'ECDHE+CHACHA20',
            'DHE+AESGCM',
            'DHE+CHACHA20',
            '!aNULL',
            '!eNULL',
            '!EXPORT',
            '!DES',
            '!RC4',
            '!MD5'
        ])
        context.set_ciphers(strong_ciphers)
        
        # For demo with self-signed cert
        context.check_hostname = False
        context.verify_mode = ssl.CERT_NONE
        
        return context
    
    def connect_with_security_validation(self, host, port):
        """Connect with comprehensive security validation"""
        context = self.create_secure_context()
        
        try:
            with socket.socket(socket.AF_INET, socket.SOCK_STREAM) as sock:
                with context.wrap_socket(sock, server_hostname=host) as ssock:
                    ssock.connect((host, port))
                    
                    print(f"Securely connected to {host}:{port}")
                    
                    # Validate connection security
                    cipher = ssock.cipher()
                    if cipher:
                        cipher_name, tls_version, key_bits = cipher
                        
                        print(f"Cipher Suite: {cipher_name}")
                        print(f"Protocol: {tls_version}")
                        print(f"Key Strength: {key_bits} bits")
                        
                        # Security validation
                        if key_bits < self.min_key_bits:
                            raise ssl.SSLError(f"Insufficient key strength: {key_bits} bits")
                        
                        if tls_version not in self.allowed_protocols:
                            raise ssl.SSLError(f"Weak protocol: {tls_version}")
                        
                        # Check for perfect forward secrecy
                        if 'ECDHE' in cipher_name or 'DHE' in cipher_name:
                            print("✓ Perfect Forward Secrecy enabled")
                        else:
                            print("⚠ No Perfect Forward Secrecy")
                        
                        # Check for authenticated encryption
                        if 'GCM' in cipher_name or 'CHACHA20' in cipher_name:
                            print("✓ Authenticated encryption enabled")
                        else:
                            print("⚠ No authenticated encryption")
                    
                    # Send secure HTTP request
                    request = (
                        "GET / HTTP/1.1\r\n"
                        "Host: " + host + "\r\n"
                        "User-Agent: SecureClient/1.0\r\n"
                        "Connection: close\r\n"
                        "\r\n"
                    )
                    ssock.send(request.encode())
                    
                    # Receive response
                    response = ssock.recv(4096).decode()
                    print("\nServer Response:")
                    print(response.split('\r\n\r\n')[0])  # Headers only
                    
        except ssl.SSLError as e:
            print(f"SSL security validation failed: {e}")
        except Exception as e:
            print(f"Connection error: {e}")

# Secure key generation utilities
class SecureKeyGeneration:
    @staticmethod
    def generate_secure_rsa_keys():
        """Generate strong RSA keys with different security levels"""
        secure_sizes = [2048, 3072, 4096]  # All secure
        
        for size in secure_sizes:
            print(f"Generating {size}-bit RSA key (SECURE)")
            
            private_key = rsa.generate_private_key(
                public_exponent=65537,
                key_size=size
            )
            
            # Save secure keys
            key_filename = f'secure_rsa_{size}.pem'
            with open(key_filename, 'wb') as f:
                f.write(private_key.private_bytes(
                    encoding=serialization.Encoding.PEM,
                    format=serialization.PrivateFormat.PKCS8,
                    encryption_algorithm=serialization.NoEncryption()
                ))
            
            # Set secure permissions
            try:
                os.chmod(key_filename, 0o600)
            except:
                pass
            
            print(f"Saved secure {size}-bit key to {key_filename}")
    
    @staticmethod
    def generate_secure_elliptic_curve_keys():
        """Generate secure elliptic curve keys"""
        secure_curves = {
            'secp256r1': ec.SECP256R1(),
            'secp384r1': ec.SECP384R1(),
            'secp521r1': ec.SECP521R1(),
        }
        
        for curve_name, curve_obj in secure_curves.items():
            print(f"Generating ECDSA key with {curve_name} curve")
            
            private_key = ec.generate_private_key(curve_obj)
            
            key_filename = f'secure_ecdsa_{curve_name}.pem'
            with open(key_filename, 'wb') as f:
                f.write(private_key.private_bytes(
                    encoding=serialization.Encoding.PEM,
                    format=serialization.PrivateFormat.PKCS8,
                    encryption_algorithm=serialization.NoEncryption()
                ))
            
            try:
                os.chmod(key_filename, 0o600)
            except:
                pass
            
            print(f"Saved secure ECDSA key to {key_filename}")
    
    @staticmethod
    def generate_secure_symmetric_keys():
        """Generate strong symmetric keys"""
        secure_key_configs = {
            'aes256': 32,     # 256-bit AES
            'hmac_sha256': 32, # 256-bit HMAC key
            'chacha20': 32,   # 256-bit ChaCha20
        }
        
        for name, size in secure_key_configs.items():
            key = secrets.token_bytes(size)
            print(f"Generated {name} key: {size} bytes ({size * 8} bits)")
            
            key_filename = f'secure_{name}_key.bin'
            with open(key_filename, 'wb') as f:
                f.write(key)
            
            try:
                os.chmod(key_filename, 0o600)
            except:
                pass
    
    @staticmethod
    def demonstrate_aes_gcm():
        """Demonstrate AES-256-GCM authenticated encryption"""
        print("\nDemonstrating AES-256-GCM encryption:")
        
        # Generate 256-bit key
        key = secrets.token_bytes(32)
        
        # Create AES-GCM cipher
        aesgcm = AESGCM(key)
        
        # Encrypt data
        plaintext = b"Sensitive data requiring strong protection"
        nonce = secrets.token_bytes(12)  # 96-bit nonce
        ciphertext = aesgcm.encrypt(nonce, plaintext, None)
        
        print(f"Plaintext: {len(plaintext)} bytes")
        print(f"Ciphertext: {len(ciphertext)} bytes")
        print(f"Key size: {len(key) * 8} bits")
        print(f"Nonce size: {len(nonce) * 8} bits")
        
        # Decrypt to verify
        decrypted = aesgcm.decrypt(nonce, ciphertext, None)
        print(f"Decryption successful: {decrypted == plaintext}")

if __name__ == '__main__':
    print("Generating secure cryptographic keys...")
    
    # Generate all types of secure keys
    SecureKeyGeneration.generate_secure_rsa_keys()
    SecureKeyGeneration.generate_secure_elliptic_curve_keys()
    SecureKeyGeneration.generate_secure_symmetric_keys()
    SecureKeyGeneration.demonstrate_aes_gcm()
    
    print("\nStarting secure SSL server demonstration...")
    
    # Create server with different key types
    print("\n1. Creating server with 3072-bit RSA key:")
    server_rsa = SecureSSLServer()
    
    print("\n2. Creating server with ECDSA P-384 key:")
    server_ecdsa = SecureSSLServer()
    server_ecdsa.cert_file = 'secure_ecdsa_server.crt'
    server_ecdsa.key_file = 'secure_ecdsa_server.key'
    server_ecdsa.generate_secure_certificate(key_type='ecdsa')
    
    # Uncomment to start server:
    # server_rsa.start_server()
    
    print("\nSecure SSL configuration complete!")
    print("All keys use cryptographically strong parameters:")
    print("- RSA: 2048+ bits (3072+ recommended)")
    print("- ECDSA: P-256, P-384, or P-521 curves")
    print("- AES: 256-bit keys with GCM mode")
    print("- TLS: Version 1.2+ with strong cipher suites")

💡 Why This Fix Works

The vulnerable implementation uses weak cryptographic keys (1024-bit RSA, weak symmetric keys), allows weak TLS protocols and cipher suites, and has poor security configurations. The secure version uses strong key sizes (3072-bit RSA minimum, P-384 ECDSA), enforces TLS 1.2+, uses authenticated encryption, implements perfect forward secrecy, and includes comprehensive security validation.

Why it happens

Using RSA keys shorter than 2048 bits, such as 1024-bit or 512-bit keys. These shorter keys can be factored using modern computational methods and are considered cryptographically broken. Even 2048-bit RSA is approaching its end of life and should be replaced with 3072-bit or 4096-bit keys.

Root causes

RSA Keys Below 2048 Bits

Using RSA keys shorter than 2048 bits, such as 1024-bit or 512-bit keys. These shorter keys can be factored using modern computational methods and are considered cryptographically broken. Even 2048-bit RSA is approaching its end of life and should be replaced with 3072-bit or 4096-bit keys.

Preview example – JAVA
// Java - VULNERABLE: Generating weak RSA keys
import java.security.KeyPair;
import java.security.KeyPairGenerator;
import java.security.NoSuchAlgorithmException;
import java.security.PrivateKey;
import java.security.PublicKey;
import javax.crypto.Cipher;

public class WeakRSAKeys {
    
    public KeyPair generateWeakRSAKey() throws NoSuchAlgorithmException {
        KeyPairGenerator keyGen = KeyPairGenerator.getInstance("RSA");
        
        // VULNERABLE: 1024-bit RSA key is cryptographically weak
        keyGen.initialize(1024); // Should be at least 2048, preferably 3072+
        
        return keyGen.generateKeyPair();
    }
    
    public KeyPair generateVeryWeakRSAKey() throws NoSuchAlgorithmException {
        KeyPairGenerator keyGen = KeyPairGenerator.getInstance("RSA");
        
        // EXTREMELY VULNERABLE: 512-bit RSA can be broken in hours
        keyGen.initialize(512);
        
        return keyGen.generateKeyPair();
    }
    
    public byte[] encryptWithWeakKey(String plaintext) throws Exception {
        // Generate weak key
        KeyPair keyPair = generateWeakRSAKey();
        PublicKey publicKey = keyPair.getPublic();
        
        // Encrypt with weak key
        Cipher cipher = Cipher.getInstance("RSA");
        cipher.init(Cipher.ENCRYPT_MODE, publicKey);
        
        return cipher.doFinal(plaintext.getBytes());
    }
    
    // VULNERABLE: Using default key size (often weak)
    public KeyPair generateDefaultRSAKey() throws NoSuchAlgorithmException {
        KeyPairGenerator keyGen = KeyPairGenerator.getInstance("RSA");
        
        // VULNERABLE: Relying on default key size (implementation dependent)
        // Default might be 1024 bits or even less
        return keyGen.generateKeyPair();
    }
    
    // VULNERABLE: Legacy SSL/TLS key generation
    public KeyPair generateSSLKey() throws NoSuchAlgorithmException {
        KeyPairGenerator keyGen = KeyPairGenerator.getInstance("RSA");
        
        // VULNERABLE: Many legacy systems still use 1024-bit for SSL
        keyGen.initialize(1024);
        
        return keyGen.generateKeyPair();
    }
}

AES Keys Shorter Than 256 Bits

Using AES with 128-bit keys instead of 256-bit keys, or using other symmetric encryption algorithms with insufficient key lengths. While AES-128 is currently considered secure against classical computers, AES-256 provides better long-term security and quantum resistance.

Preview example – PYTHON
# Python - VULNERABLE: Weak symmetric encryption key lengths
import os
from cryptography.hazmat.primitives.ciphers import Cipher, algorithms, modes
from cryptography.hazmat.backends import default_backend

class WeakSymmetricEncryption:
    
    def generate_weak_aes_key(self):
        """VULNERABLE: AES-128 may not provide sufficient long-term security"""
        # 16 bytes = 128 bits (minimum AES key size)
        return os.urandom(16)  # Should use 32 bytes (256 bits) for better security
    
    def generate_very_weak_key(self):
        """EXTREMELY VULNERABLE: Custom key length that's too short"""
        # 8 bytes = 64 bits - completely insecure
        return os.urandom(8)
    
    def encrypt_with_weak_aes(self, plaintext, key=None):
        """VULNERABLE: Using AES with potentially weak key"""
        if key is None:
            key = self.generate_weak_aes_key()  # 128-bit key
        
        # Generate random IV
        iv = os.urandom(16)
        
        # VULNERABLE: AES-128 instead of AES-256
        cipher = Cipher(
            algorithms.AES(key),  # 128-bit key
            modes.CBC(iv),
            backend=default_backend()
        )
        
        encryptor = cipher.encryptor()
        
        # Add padding manually (simplified)
        padding_length = 16 - (len(plaintext) % 16)
        padded_plaintext = plaintext + bytes([padding_length] * padding_length)
        
        ciphertext = encryptor.update(padded_plaintext) + encryptor.finalize()
        
        return iv + ciphertext
    
    def use_deprecated_algorithm(self, plaintext):
        """VULNERABLE: Using DES with 56-bit effective key length"""
        from cryptography.hazmat.primitives.ciphers import algorithms as crypto_algorithms
        
        # EXTREMELY VULNERABLE: DES uses 56-bit effective key (8 bytes with parity)
        key = os.urandom(8)  # DES key
        iv = os.urandom(8)   # DES IV
        
        # This is cryptographically broken
        cipher = Cipher(
            crypto_algorithms.TripleDES(key + key + key),  # Weak 3DES
            modes.CBC(iv),
            backend=default_backend()
        )
        
        encryptor = cipher.encryptor()
        
        # Pad to 8-byte boundary
        padding_length = 8 - (len(plaintext) % 8)
        padded_plaintext = plaintext + bytes([padding_length] * padding_length)
        
        return encryptor.update(padded_plaintext) + encryptor.finalize()
    
    def weak_key_derivation(self, password, salt):
        """VULNERABLE: Key derivation with insufficient output length"""
        import hashlib
        
        # VULNERABLE: Deriving only 128-bit key from password
        key_material = hashlib.pbkdf2_hmac('sha256', password.encode(), salt, 100000, 16)
        return key_material  # Only 16 bytes = 128 bits
    
    def generate_hmac_key_weak(self):
        """VULNERABLE: HMAC key shorter than hash output"""
        # VULNERABLE: HMAC key should be at least as long as hash output
        # SHA-256 outputs 32 bytes, so key should be 32+ bytes
        return os.urandom(16)  # Only 16 bytes for SHA-256 HMAC

Elliptic Curve Keys with Insufficient Bits

Using elliptic curve keys with insufficient bit lengths, such as secp160r1 or secp192r1, instead of stronger curves like secp256r1, secp384r1, or modern curves like Curve25519. Weak curves can be broken using advanced mathematical attacks.

Preview example – JAVASCRIPT
// Node.js - VULNERABLE: Weak elliptic curve key generation
const crypto = require('crypto');
const { generateKeyPairSync } = require('crypto');

class WeakECCKeys {
    
    generateWeakECKey() {
        // VULNERABLE: secp192r1 provides only ~96 bits of security
        const { publicKey, privateKey } = generateKeyPairSync('ec', {
            namedCurve: 'secp192r1', // WEAK: Only 192-bit curve
            publicKeyEncoding: {
                type: 'spki',
                format: 'pem'
            },
            privateKeyEncoding: {
                type: 'pkcs8',
                format: 'pem'
            }
        });
        
        return { publicKey, privateKey };
    }
    
    generateVeryWeakECKey() {
        // EXTREMELY VULNERABLE: secp160r1 is cryptographically broken
        const { publicKey, privateKey } = generateKeyPairSync('ec', {
            namedCurve: 'secp160r1', // BROKEN: Only 160-bit curve
            publicKeyEncoding: {
                type: 'spki',
                format: 'pem'
            },
            privateKeyEncoding: {
                type: 'pkcs8',
                format: 'pem'
            }
        });
        
        return { publicKey, privateKey };
    }
    
    // VULNERABLE: Using prime192v1 (same as secp192r1)
    generateLegacyECKey() {
        const { publicKey, privateKey } = generateKeyPairSync('ec', {
            namedCurve: 'prime192v1', // WEAK: Legacy 192-bit curve
            publicKeyEncoding: {
                type: 'spki',
                format: 'pem'
            },
            privateKeyEncoding: {
                type: 'pkcs8',
                format: 'pem'
            }
        });
        
        return { publicKey, privateKey };
    }
    
    signWithWeakKey(data) {
        const { privateKey } = this.generateWeakECKey();
        
        // VULNERABLE: Signature using weak EC key
        const sign = crypto.createSign('SHA256');
        sign.update(data);
        sign.end();
        
        return sign.sign(privateKey);
    }
    
    // VULNERABLE: ECDH with weak curve
    performWeakECDH() {
        // Generate two weak key pairs
        const alice = generateKeyPairSync('ec', {
            namedCurve: 'secp192r1' // WEAK
        });
        
        const bob = generateKeyPairSync('ec', {
            namedCurve: 'secp192r1' // WEAK
        });
        
        // Perform ECDH with weak keys
        const aliceSharedSecret = crypto.diffieHellman({
            privateKey: alice.privateKey,
            publicKey: bob.publicKey
        });
        
        return aliceSharedSecret; // Shared secret has weak security level
    }
    
    // VULNERABLE: Custom curve with weak parameters
    useCustomWeakCurve() {
        // This would involve defining a custom curve with weak parameters
        // Most implementations don't allow this, but some legacy systems might
        throw new Error('Custom weak curves are implementation-dependent');
    }
}

Legacy Cryptographic Protocols with Short Keys

Using legacy cryptographic protocols that inherently use short keys, such as WEP (40-bit or 104-bit), early SSL/TLS versions with export-grade ciphers, or legacy SSH configurations that allow weak key exchange algorithms.

Preview example – CSHARP
// C# - VULNERABLE: Legacy SSL/TLS and cryptographic configurations
using System;
using System.Net;
using System.Net.Security;
using System.Security.Authentication;
using System.Security.Cryptography;
using System.Text;

public class LegacyCryptoProtocols
{
    // VULNERABLE: Allowing weak SSL/TLS protocols
    public void ConfigureWeakSSL()
    {
        // VULNERABLE: Enabling weak TLS versions and export ciphers
        ServicePointManager.SecurityProtocol = 
            SecurityProtocolType.Ssl3 |           // BROKEN
            SecurityProtocolType.Tls |            // TLS 1.0 - WEAK
            SecurityProtocolType.Tls11;           // TLS 1.1 - WEAK
        
        // This allows servers to negotiate weak ciphers with short keys
    }
    
    // VULNERABLE: Using RSA for key exchange with short keys
    public byte[] WeakRSAKeyExchange()
    {
        using (var rsa = RSA.Create())
        {
            // VULNERABLE: Short RSA key for key exchange
            rsa.KeySize = 1024; // Should be 2048+ for RSA
            
            // Generate random session key
            var sessionKey = new byte[16]; // 128-bit session key
            using (var rng = RandomNumberGenerator.Create())
            {
                rng.GetBytes(sessionKey);
            }
            
            // Encrypt session key with weak RSA key
            return rsa.Encrypt(sessionKey, RSAEncryptionPadding.Pkcs1);
        }
    }
    
    // VULNERABLE: DH key exchange with short keys
    public class WeakDiffieHellman
    {
        // VULNERABLE: Small prime for DH (512 bits)
        private static readonly byte[] WeakPrime = 
        {
            0xDA, 0x58, 0x3C, 0x16, 0xD9, 0x85, 0x22, 0x89,
            0xD0, 0xE4, 0xAF, 0x75, 0x6F, 0x4C, 0xCA, 0x92,
            0xDD, 0x4B, 0xE5, 0x33, 0xB8, 0x04, 0xFB, 0x0F,
            0xED, 0x94, 0xEF, 0x9C, 0x8A, 0x44, 0x03, 0xED,
            0x57, 0x46, 0x50, 0xD3, 0x69, 0x99, 0xDB, 0x29,
            0xD7, 0x76, 0x27, 0x6B, 0xA2, 0xD3, 0xD4, 0x12,
            0xE2, 0x18, 0xF4, 0xDD, 0x1E, 0x08, 0x4C, 0xF6,
            0xD8, 0x00, 0x3E, 0x7C, 0x47, 0x74, 0xE8, 0x33
        };
        
        public byte[] GenerateWeakDHKey()
        {
            // VULNERABLE: Using small prime (512 bits) for DH
            // Modern DH should use at least 2048-bit primes
            
            using (var rng = RandomNumberGenerator.Create())
            {
                var privateKey = new byte[64]; // 512-bit private key
                rng.GetBytes(privateKey);
                
                // In real implementation, this would compute g^x mod p
                // where p is the weak prime above
                
                return privateKey; // Simplified for example
            }
        }
    }
    
    // VULNERABLE: Symmetric encryption with export-grade key lengths
    public byte[] ExportGradeEncryption(string plaintext)
    {
        // VULNERABLE: 40-bit RC4 (export grade)
        var key = new byte[5]; // 40 bits
        using (var rng = RandomNumberGenerator.Create())
        {
            rng.GetBytes(key);
        }
        
        // This is cryptographically broken
        // RC4 with 40-bit key can be broken in seconds
        
        var data = Encoding.UTF8.GetBytes(plaintext);
        var encrypted = new byte[data.Length];
        
        // Simplified RC4-like encryption (for illustration)
        for (int i = 0; i < data.Length; i++)
        {
            encrypted[i] = (byte)(data[i] ^ key[i % key.Length]);
        }
        
        return encrypted;
    }
    
    // VULNERABLE: Legacy MAC with short keys
    public byte[] WeakMAC(byte[] data)
    {
        // VULNERABLE: HMAC with short key
        var key = new byte[8]; // Only 64 bits
        using (var rng = RandomNumberGenerator.Create())
        {
            rng.GetBytes(key);
        }
        
        using (var hmac = new HMACSHA256(key))
        {
            return hmac.ComputeHash(data);
        }
    }
    
    // VULNERABLE: Password-based encryption with weak key derivation
    public byte[] WeakPasswordBasedEncryption(string password, byte[] data)
    {
        var salt = new byte[8]; // Small salt
        using (var rng = RandomNumberGenerator.Create())
        {
            rng.GetBytes(salt);
        }
        
        // VULNERABLE: Derive only 64-bit key from password
        using (var pbkdf2 = new Rfc2898DeriveBytes(password, salt, 1000))
        {
            var key = pbkdf2.GetBytes(8); // Only 8 bytes = 64 bits
            
            // Use weak key for encryption
            var encrypted = new byte[data.Length];
            for (int i = 0; i < data.Length; i++)
            {
                encrypted[i] = (byte)(data[i] ^ key[i % key.Length]);
            }
            
            return encrypted;
        }
    }
}

Fixes

1

Use RSA Keys of 3072 Bits or Higher

Generate RSA keys with at least 3072 bits for new applications, and migrate existing 1024-bit keys to 2048 bits minimum (preferably 3072 or 4096 bits). Consider transitioning to elliptic curve cryptography for better performance with equivalent security.

View implementation – JAVA
// Java - SECURE: Strong RSA key generation
import java.security.KeyPair;
import java.security.KeyPairGenerator;
import java.security.NoSuchAlgorithmException;
import java.security.SecureRandom;
import java.security.spec.RSAKeyGenParameterSpec;
import java.math.BigInteger;

public class SecureRSAKeys {
    
    // Recommended key sizes based on security requirements
    public static final int RSA_KEY_SIZE_STANDARD = 3072;  // Good until ~2030
    public static final int RSA_KEY_SIZE_HIGH = 4096;      // Long-term security
    
    public KeyPair generateSecureRSAKey() throws NoSuchAlgorithmException {
        return generateSecureRSAKey(RSA_KEY_SIZE_STANDARD);
    }
    
    public KeyPair generateSecureRSAKey(int keySize) throws NoSuchAlgorithmException {
        if (keySize < 2048) {
            throw new IllegalArgumentException("RSA key size must be at least 2048 bits");
        }
        
        KeyPairGenerator keyGen = KeyPairGenerator.getInstance("RSA");
        
        // Use secure random and proper key size
        SecureRandom secureRandom = new SecureRandom();
        keyGen.initialize(keySize, secureRandom);
        
        return keyGen.generateKeyPair();
    }
    
    public KeyPair generateHighSecurityRSAKey() throws Exception {
        KeyPairGenerator keyGen = KeyPairGenerator.getInstance("RSA");
        
        // Use RSA key generation parameters for maximum security
        RSAKeyGenParameterSpec spec = new RSAKeyGenParameterSpec(
            RSA_KEY_SIZE_HIGH,
            BigInteger.valueOf(65537) // Standard public exponent
        );
        
        keyGen.initialize(spec, new SecureRandom());
        
        return keyGen.generateKeyPair();
    }
    
    // Key size validation
    public boolean isKeySecure(KeyPair keyPair) {
        if (keyPair.getPublic().getAlgorithm().equals("RSA")) {
            // Get key size from public key
            java.security.interfaces.RSAPublicKey rsaPublicKey = 
                (java.security.interfaces.RSAPublicKey) keyPair.getPublic();
            
            int keySize = rsaPublicKey.getModulus().bitLength();
            
            return keySize >= 2048; // Minimum acceptable
        }
        
        return false;
    }
    
    // Secure RSA encryption with proper padding
    public byte[] encryptWithSecureKey(String plaintext) throws Exception {
        KeyPair keyPair = generateSecureRSAKey();
        
        javax.crypto.Cipher cipher = javax.crypto.Cipher.getInstance("RSA/ECB/OAEPSHA256AndMGF1Padding");
        cipher.init(javax.crypto.Cipher.ENCRYPT_MODE, keyPair.getPublic());
        
        return cipher.doFinal(plaintext.getBytes());
    }
    
    // Key upgrade utility
    public KeyPair upgradeWeakKey(KeyPair oldKeyPair) throws Exception {
        if (isKeySecure(oldKeyPair)) {
            return oldKeyPair; // Already secure
        }
        
        System.out.println("Upgrading weak RSA key to secure key size");
        return generateSecureRSAKey(RSA_KEY_SIZE_STANDARD);
    }
    
    // Generate keys for different use cases
    public KeyPair generateSigningKey() throws NoSuchAlgorithmException {
        // For digital signatures, use high security
        return generateSecureRSAKey(RSA_KEY_SIZE_HIGH);
    }
    
    public KeyPair generateEncryptionKey() throws NoSuchAlgorithmException {
        // For encryption, standard security is acceptable
        return generateSecureRSAKey(RSA_KEY_SIZE_STANDARD);
    }
}
2

Use AES-256 and Strong Symmetric Keys

Always use AES with 256-bit keys for symmetric encryption. Generate cryptographically secure random keys, and use proper key derivation functions when deriving keys from passwords. Consider post-quantum cryptographic algorithms for long-term data protection.

View implementation – PYTHON
# Python - SECURE: Strong symmetric encryption with AES-256
import os
import secrets
from cryptography.hazmat.primitives.ciphers.aead import AESGCM
from cryptography.hazmat.primitives.kdf.pbkdf2 import PBKDF2HMAC
from cryptography.hazmat.primitives.kdf.scrypt import Scrypt
from cryptography.hazmat.primitives import hashes
from cryptography.hazmat.backends import default_backend

class SecureSymmetricEncryption:
    
    # Recommended key sizes
    AES_KEY_SIZE = 32      # 256 bits
    HMAC_KEY_SIZE = 32     # 256 bits (same as hash output)
    SALT_SIZE = 32         # 256 bits
    NONCE_SIZE = 12        # 96 bits for AES-GCM
    
    def generate_secure_aes_key(self):
        """Generate cryptographically secure 256-bit AES key"""
        return secrets.token_bytes(self.AES_KEY_SIZE)
    
    def generate_secure_hmac_key(self):
        """Generate secure HMAC key (at least as long as hash output)"""
        return secrets.token_bytes(self.HMAC_KEY_SIZE)
    
    def encrypt_with_aes_gcm(self, plaintext, key=None, associated_data=None):
        """Encrypt using AES-256-GCM (authenticated encryption)"""
        if key is None:
            key = self.generate_secure_aes_key()
        
        if len(key) != self.AES_KEY_SIZE:
            raise ValueError(f"AES key must be {self.AES_KEY_SIZE} bytes (256 bits)")
        
        # Generate random nonce
        nonce = secrets.token_bytes(self.NONCE_SIZE)
        
        # Use AES-GCM for authenticated encryption
        aesgcm = AESGCM(key)
        ciphertext = aesgcm.encrypt(nonce, plaintext, associated_data)
        
        return {
            'ciphertext': ciphertext,
            'nonce': nonce,
            'key': key
        }
    
    def decrypt_with_aes_gcm(self, encrypted_data, associated_data=None):
        """Decrypt AES-256-GCM ciphertext"""
        aesgcm = AESGCM(encrypted_data['key'])
        
        try:
            plaintext = aesgcm.decrypt(
                encrypted_data['nonce'],
                encrypted_data['ciphertext'],
                associated_data
            )
            return plaintext
        except Exception as e:
            raise ValueError(f"Decryption failed: {e}")
    
    def derive_key_from_password_pbkdf2(self, password, salt=None, iterations=600000):
        """Derive 256-bit key from password using PBKDF2"""
        if salt is None:
            salt = secrets.token_bytes(self.SALT_SIZE)
        
        if iterations < 100000:
            raise ValueError("PBKDF2 iterations must be at least 100,000")
        
        kdf = PBKDF2HMAC(
            algorithm=hashes.SHA256(),
            length=self.AES_KEY_SIZE,  # 32 bytes = 256 bits
            salt=salt,
            iterations=iterations,
            backend=default_backend()
        )
        
        key = kdf.derive(password.encode('utf-8'))
        
        return {
            'key': key,
            'salt': salt,
            'iterations': iterations,
            'algorithm': 'PBKDF2-SHA256'
        }
    
    def derive_key_from_password_scrypt(self, password, salt=None, n=32768, r=8, p=1):
        """Derive 256-bit key from password using scrypt (more secure)"""
        if salt is None:
            salt = secrets.token_bytes(self.SALT_SIZE)
        
        # Validate scrypt parameters
        if n < 16384:
            raise ValueError("Scrypt N parameter should be at least 16384")
        if r < 8:
            raise ValueError("Scrypt r parameter should be at least 8")
        
        kdf = Scrypt(
            algorithm=hashes.SHA256(),
            length=self.AES_KEY_SIZE,  # 32 bytes = 256 bits
            salt=salt,
            n=n,
            r=r,
            p=p,
            backend=default_backend()
        )
        
        key = kdf.derive(password.encode('utf-8'))
        
        return {
            'key': key,
            'salt': salt,
            'n': n,
            'r': r,
            'p': p,
            'algorithm': 'scrypt-SHA256'
        }
    
    def secure_hmac_generation(self, data, key=None):
        """Generate HMAC with secure key length"""
        import hmac
        import hashlib
        
        if key is None:
            key = self.generate_secure_hmac_key()
        
        if len(key) < 32:  # SHA-256 output length
            raise ValueError("HMAC key should be at least 32 bytes for SHA-256")
        
        return hmac.new(key, data, hashlib.sha256).digest()
    
    def encrypt_file_securely(self, file_path, output_path, password=None):
        """Encrypt file with strong encryption"""
        with open(file_path, 'rb') as f:
            plaintext = f.read()
        
        if password:
            # Derive key from password
            key_data = self.derive_key_from_password_scrypt(password)
            key = key_data['key']
        else:
            # Generate random key
            key = self.generate_secure_aes_key()
            key_data = {'key': key, 'random': True}
        
        # Encrypt data
        encrypted = self.encrypt_with_aes_gcm(plaintext, key)
        
        # Save encrypted file with metadata
        with open(output_path, 'wb') as f:
            # Write salt if password-derived
            if 'salt' in key_data:
                f.write(len(key_data['salt']).to_bytes(4, 'big'))
                f.write(key_data['salt'])
                f.write(key_data['iterations'].to_bytes(4, 'big'))
            else:
                f.write((0).to_bytes(4, 'big'))  # No salt
            
            # Write nonce
            f.write(len(encrypted['nonce']).to_bytes(4, 'big'))
            f.write(encrypted['nonce'])
            
            # Write ciphertext
            f.write(encrypted['ciphertext'])
        
        return key_data
    
    def validate_key_strength(self, key, key_type='AES'):
        """Validate that key meets security requirements"""
        if key_type == 'AES':
            if len(key) < 16:
                return False, "AES key too short (minimum 128 bits)"
            elif len(key) < 32:
                return False, "AES key should be 256 bits for optimal security"
            else:
                return True, "AES key length is secure"
        
        elif key_type == 'HMAC':
            if len(key) < 32:  # SHA-256 output length
                return False, "HMAC key should be at least 32 bytes for SHA-256"
            else:
                return True, "HMAC key length is secure"
        
        return False, "Unknown key type"
    
    def generate_key_bundle(self):
        """Generate a complete set of secure keys"""
        return {
            'encryption_key': self.generate_secure_aes_key(),
            'signing_key': self.generate_secure_hmac_key(),
            'kdf_salt': secrets.token_bytes(self.SALT_SIZE),
            'created_at': secrets.token_bytes(8).hex(),  # Timestamp placeholder
            'key_version': 1
        }

# Example usage
if __name__ == '__main__':
    crypto = SecureSymmetricEncryption()
    
    # Generate secure keys
    aes_key = crypto.generate_secure_aes_key()
    print(f"Generated AES-256 key: {len(aes_key)} bytes")
    
    # Encrypt data
    plaintext = b"This is sensitive data that needs strong protection"
    encrypted = crypto.encrypt_with_aes_gcm(plaintext)
    
    print(f"Encrypted {len(plaintext)} bytes to {len(encrypted['ciphertext'])} bytes")
    
    # Decrypt data
    decrypted = crypto.decrypt_with_aes_gcm(encrypted)
    print(f"Decryption successful: {decrypted == plaintext}")
    
    # Key derivation from password
    password = "strong_password_123!@#"
    key_data = crypto.derive_key_from_password_scrypt(password)
    print(f"Derived key from password: {len(key_data['key'])} bytes")
    
    # Validate key strength
    is_secure, message = crypto.validate_key_strength(aes_key, 'AES')
    print(f"Key security validation: {is_secure} - {message}")
3

Use Strong Elliptic Curves

Use well-vetted elliptic curves with adequate security levels: P-256 (secp256r1) for 128-bit security, P-384 for 192-bit security, or modern curves like Curve25519 and Ed25519. Avoid curves smaller than 256 bits and legacy curves with known weaknesses.

View implementation – JAVASCRIPT
// Node.js - SECURE: Strong elliptic curve cryptography
const crypto = require('crypto');
const { generateKeyPairSync, createSign, createVerify, diffieHellman } = require('crypto');

class SecureEllipticCurves {
    
    // Recommended curves with their security levels
    static CURVES = {
        'secp256r1': { bits: 256, security: 128, description: 'NIST P-256 (recommended)' },
        'secp384r1': { bits: 384, security: 192, description: 'NIST P-384 (high security)' },
        'secp521r1': { bits: 521, security: 256, description: 'NIST P-521 (maximum security)' },
        'prime256v1': { bits: 256, security: 128, description: 'Same as secp256r1' }
    };
    
    constructor() {
        this.defaultCurve = 'secp256r1'; // Good balance of security and performance
        this.highSecurityCurve = 'secp384r1'; // For high-security applications
    }
    
    generateSecureECKey(curveName = this.defaultCurve) {
        // Validate curve security
        if (!this.isCurveSecure(curveName)) {
            throw new Error(`Curve ${curveName} does not meet security requirements`);
        }
        
        const { publicKey, privateKey } = generateKeyPairSync('ec', {
            namedCurve: curveName,
            publicKeyEncoding: {
                type: 'spki',
                format: 'pem'
            },
            privateKeyEncoding: {
                type: 'pkcs8',
                format: 'pem'
            }
        });
        
        return {
            publicKey,
            privateKey,
            curve: curveName,
            securityLevel: SecureEllipticCurves.CURVES[curveName].security
        };
    }
    
    generateHighSecurityECKey() {
        // Use P-384 for high security requirements
        return this.generateSecureECKey(this.highSecurityCurve);
    }
    
    generateMaxSecurityECKey() {
        // Use P-521 for maximum security
        return this.generateSecureECKey('secp521r1');
    }
    
    // Modern curve support (when available)
    generateCurve25519Key() {
        try {
            // X25519 for ECDH
            const { publicKey, privateKey } = generateKeyPairSync('x25519', {
                publicKeyEncoding: {
                    type: 'spki',
                    format: 'pem'
                },
                privateKeyEncoding: {
                    type: 'pkcs8',
                    format: 'pem'
                }
            });
            
            return {
                publicKey,
                privateKey,
                curve: 'X25519',
                securityLevel: 128,
                type: 'ECDH'
            };
        } catch (error) {
            throw new Error('X25519 not supported in this Node.js version');
        }
    }
    
    generateEd25519Key() {
        try {
            // Ed25519 for digital signatures
            const { publicKey, privateKey } = generateKeyPairSync('ed25519', {
                publicKeyEncoding: {
                    type: 'spki',
                    format: 'pem'
                },
                privateKeyEncoding: {
                    type: 'pkcs8',
                    format: 'pem'
                }
            });
            
            return {
                publicKey,
                privateKey,
                curve: 'Ed25519',
                securityLevel: 128,
                type: 'Signature'
            };
        } catch (error) {
            throw new Error('Ed25519 not supported in this Node.js version');
        }
    }
    
    isCurveSecure(curveName) {
        const curve = SecureEllipticCurves.CURVES[curveName];
        if (!curve) {
            console.warn(`Unknown curve: ${curveName}`);
            return false;
        }
        
        // Require at least 256-bit curves (128-bit security)
        return curve.bits >= 256;
    }
    
    signWithSecureCurve(data, privateKey) {
        const sign = createSign('SHA256');
        sign.update(data);
        sign.end();
        
        return sign.sign(privateKey);
    }
    
    verifyWithSecureCurve(data, signature, publicKey) {
        const verify = createVerify('SHA256');
        verify.update(data);
        verify.end();
        
        return verify.verify(publicKey, signature);
    }
    
    performSecureECDH(privateKey, publicKey) {
        // Perform ECDH key agreement with secure curves
        try {
            const sharedSecret = diffieHellman({
                privateKey: privateKey,
                publicKey: publicKey
            });
            
            return sharedSecret;
        } catch (error) {
            throw new Error(`ECDH failed: ${error.message}`);
        }
    }
    
    deriveKeyFromECDH(sharedSecret, keyLength = 32, info = '') {
        // Derive symmetric key from ECDH shared secret using HKDF
        const hkdf = crypto.createHmac('sha256', '');
        
        // Simplified HKDF (use proper HKDF library in production)
        const okm = crypto.createHmac('sha256', sharedSecret)
            .update(info)
            .digest();
        
        return okm.slice(0, keyLength);
    }
    
    validateKeyPair(keyPair) {
        try {
            // Test signing and verification
            const testData = 'test message for key validation';
            const signature = this.signWithSecureCurve(testData, keyPair.privateKey);
            const isValid = this.verifyWithSecureCurve(testData, signature, keyPair.publicKey);
            
            return {
                valid: isValid,
                curve: keyPair.curve,
                securityLevel: keyPair.securityLevel
            };
        } catch (error) {
            return {
                valid: false,
                error: error.message
            };
        }
    }
    
    // Migration utility for upgrading weak curves
    upgradeWeakCurve(oldKeyPair, targetSecurityLevel = 128) {
        const requiredCurve = targetSecurityLevel >= 192 ? 'secp384r1' : 'secp256r1';
        
        console.log(`Upgrading key to ${requiredCurve} for ${targetSecurityLevel}-bit security`);
        return this.generateSecureECKey(requiredCurve);
    }
    
    // Generate keys for different use cases
    generateSigningKeys() {
        // For digital signatures
        try {
            return this.generateEd25519Key(); // Preferred for signatures
        } catch {
            return this.generateSecureECKey('secp256r1'); // Fallback
        }
    }
    
    generateKeyExchangeKeys() {
        // For key exchange (ECDH)
        try {
            return this.generateCurve25519Key(); // Preferred for ECDH
        } catch {
            return this.generateSecureECKey('secp256r1'); // Fallback
        }
    }
}

// Example usage
const ecc = new SecureEllipticCurves();

// Generate secure EC key pair
const keyPair = ecc.generateSecureECKey();
console.log(`Generated EC key with curve: ${keyPair.curve}`);
console.log(`Security level: ${keyPair.securityLevel} bits`);

// Generate high-security key pair
const highSecKeyPair = ecc.generateHighSecurityECKey();
console.log(`High-security key curve: ${highSecKeyPair.curve}`);

// Test modern curves if available
try {
    const ed25519Keys = ecc.generateEd25519Key();
    console.log('Ed25519 keys generated successfully');
} catch (error) {
    console.log('Ed25519 not available, using fallback');
}

// Validate key pair
const validation = ecc.validateKeyPair(keyPair);
console.log(`Key validation: ${validation.valid}`);

// Demonstrate ECDH
const alice = ecc.generateSecureECKey();
const bob = ecc.generateSecureECKey();

const aliceSecret = ecc.performSecureECDH(alice.privateKey, bob.publicKey);
const bobSecret = ecc.performSecureECDH(bob.privateKey, alice.publicKey);

console.log(`ECDH shared secrets match: ${aliceSecret.equals(bobSecret)}`);

module.exports = SecureEllipticCurves;
4

Upgrade Legacy Protocols and Configurations

Disable weak SSL/TLS versions, upgrade to TLS 1.2 minimum (preferably TLS 1.3), use strong cipher suites, and implement proper key exchange algorithms. Replace legacy protocols with modern, quantum-resistant alternatives where possible.

View implementation – CSHARP
// C# - SECURE: Modern TLS configuration and strong cryptographic protocols
using System;
using System.Net;
using System.Net.Security;
using System.Security.Authentication;
using System.Security.Cryptography;
using System.Text;
using Microsoft.AspNetCore.Builder;
using Microsoft.Extensions.DependencyInjection;

public class SecureProtocolConfiguration
{
    // Configure secure TLS settings
    public static void ConfigureSecureSSL()
    {
        // SECURE: Enable only strong TLS versions
        ServicePointManager.SecurityProtocol = 
            SecurityProtocolType.Tls12 |    // TLS 1.2 (minimum)
            SecurityProtocolType.Tls13;     // TLS 1.3 (preferred)
        
        // Disable weak protocols completely
        ServicePointManager.SecurityProtocol &= 
            ~(SecurityProtocolType.Ssl3 |
              SecurityProtocolType.Tls |
              SecurityProtocolType.Tls11);
    }
    
    // ASP.NET Core HTTPS configuration
    public static void ConfigureSecureHttps(IServiceCollection services)
    {
        services.Configure<HttpsRedirectionOptions>(options =>
        {
            options.RedirectStatusCode = StatusCodes.Status308PermanentRedirect;
            options.HttpsPort = 443;
        });
        
        services.AddHsts(options =>
        {
            options.Preload = true;
            options.IncludeSubDomains = true;
            options.MaxAge = TimeSpan.FromDays(365);
        });
    }
    
    // Secure RSA key generation with proper sizes
    public class SecureRSAProvider
    {
        private const int MINIMUM_KEY_SIZE = 2048;
        private const int RECOMMENDED_KEY_SIZE = 3072;
        private const int HIGH_SECURITY_KEY_SIZE = 4096;
        
        public RSA CreateSecureRSA(SecurityLevel securityLevel = SecurityLevel.Recommended)
        {
            var rsa = RSA.Create();
            
            int keySize = securityLevel switch
            {
                SecurityLevel.Minimum => MINIMUM_KEY_SIZE,
                SecurityLevel.Recommended => RECOMMENDED_KEY_SIZE,
                SecurityLevel.High => HIGH_SECURITY_KEY_SIZE,
                _ => RECOMMENDED_KEY_SIZE
            };
            
            rsa.KeySize = keySize;
            
            Console.WriteLine($"Generated RSA key with {keySize} bits");
            return rsa;
        }
        
        public enum SecurityLevel
        {
            Minimum,      // 2048 bits
            Recommended,  // 3072 bits  
            High         // 4096 bits
        }
    }
    
    // Secure Diffie-Hellman implementation
    public class SecureDiffieHellman
    {
        private const int MINIMUM_KEY_SIZE = 2048;
        private const int RECOMMENDED_KEY_SIZE = 3072;
        
        public ECDiffieHellman CreateSecureECDH()
        {
            var ecdh = ECDiffieHellman.Create();
            
            // Use secure curves
            try
            {
                ecdh.GenerateKey(ECCurve.NamedCurves.nistP384); // 384-bit curve
                Console.WriteLine("Generated ECDH key with P-384 curve");
            }
            catch
            {
                ecdh.GenerateKey(ECCurve.NamedCurves.nistP256); // Fallback to P-256
                Console.WriteLine("Generated ECDH key with P-256 curve");
            }
            
            return ecdh;
        }
        
        public byte[] DeriveKeyMaterial(ECDiffieHellman ecdh, ECDiffieHellmanPublicKey otherPartyPublicKey, int keyLength = 32)
        {
            // Derive key material using secure hash algorithm
            return ecdh.DeriveKeyMaterial(otherPartyPublicKey);
        }
    }
    
    // Secure symmetric encryption with proper key sizes
    public class SecureSymmetricCrypto
    {
        private const int AES_KEY_SIZE_BITS = 256;
        private const int AES_KEY_SIZE_BYTES = AES_KEY_SIZE_BITS / 8;
        private const int HMAC_KEY_SIZE = 32; // 256 bits
        
        public Aes CreateSecureAES()
        {
            var aes = Aes.Create();
            aes.KeySize = AES_KEY_SIZE_BITS; // Force 256-bit keys
            aes.Mode = CipherMode.GCM;       // Use authenticated encryption
            
            return aes;
        }
        
        public byte[] GenerateSecureKey()
        {
            using (var rng = RandomNumberGenerator.Create())
            {
                var key = new byte[AES_KEY_SIZE_BYTES];
                rng.GetBytes(key);
                return key;
            }
        }
        
        public byte[] GenerateSecureHMACKey()
        {
            using (var rng = RandomNumberGenerator.Create())
            {
                var key = new byte[HMAC_KEY_SIZE];
                rng.GetBytes(key);
                return key;
            }
        }
        
        public EncryptionResult EncryptWithAESGCM(byte[] plaintext, byte[] key, byte[] associatedData = null)
        {
            if (key.Length != AES_KEY_SIZE_BYTES)
            {
                throw new ArgumentException($"Key must be {AES_KEY_SIZE_BYTES} bytes (256 bits)");
            }
            
            using (var aes = new AesGcm(key))
            {
                var nonce = new byte[12]; // 96-bit nonce
                var ciphertext = new byte[plaintext.Length];
                var tag = new byte[16]; // 128-bit authentication tag
                
                using (var rng = RandomNumberGenerator.Create())
                {
                    rng.GetBytes(nonce);
                }
                
                aes.Encrypt(nonce, plaintext, ciphertext, tag, associatedData);
                
                return new EncryptionResult
                {
                    Ciphertext = ciphertext,
                    Nonce = nonce,
                    Tag = tag
                };
            }
        }
        
        public class EncryptionResult
        {
            public byte[] Ciphertext { get; set; }
            public byte[] Nonce { get; set; }
            public byte[] Tag { get; set; }
        }
    }
    
    // Password-based key derivation with secure parameters
    public class SecureKeyDerivation
    {
        private const int MINIMUM_ITERATIONS = 100000;
        private const int RECOMMENDED_ITERATIONS = 600000;
        private const int SALT_SIZE = 32;
        private const int KEY_SIZE = 32; // 256 bits
        
        public KeyDerivationResult DeriveKeyFromPassword(string password, byte[] salt = null, int iterations = RECOMMENDED_ITERATIONS)
        {
            if (iterations < MINIMUM_ITERATIONS)
            {
                throw new ArgumentException($"Iterations must be at least {MINIMUM_ITERATIONS}");
            }
            
            if (salt == null)
            {
                salt = new byte[SALT_SIZE];
                using (var rng = RandomNumberGenerator.Create())
                {
                    rng.GetBytes(salt);
                }
            }
            
            using (var pbkdf2 = new Rfc2898DeriveBytes(password, salt, iterations, HashAlgorithmName.SHA256))
            {
                var key = pbkdf2.GetBytes(KEY_SIZE);
                
                return new KeyDerivationResult
                {
                    Key = key,
                    Salt = salt,
                    Iterations = iterations,
                    Algorithm = "PBKDF2-SHA256"
                };
            }
        }
        
        public class KeyDerivationResult
        {
            public byte[] Key { get; set; }
            public byte[] Salt { get; set; }
            public int Iterations { get; set; }
            public string Algorithm { get; set; }
        }
    }
    
    // Key validation utilities
    public static class KeyValidator
    {
        public static ValidationResult ValidateRSAKey(RSA rsa)
        {
            var keySize = rsa.KeySize;
            
            if (keySize < 2048)
            {
                return new ValidationResult
                {
                    IsValid = false,
                    Message = $"RSA key size {keySize} is too small (minimum 2048 bits)"
                };
            }
            else if (keySize < 3072)
            {
                return new ValidationResult
                {
                    IsValid = true,
                    Message = $"RSA key size {keySize} meets minimum requirements but 3072+ recommended",
                    WarningLevel = true
                };
            }
            else
            {
                return new ValidationResult
                {
                    IsValid = true,
                    Message = $"RSA key size {keySize} provides strong security"
                };
            }
        }
        
        public static ValidationResult ValidateAESKey(byte[] key)
        {
            var keyBits = key.Length * 8;
            
            if (keyBits < 128)
            {
                return new ValidationResult
                {
                    IsValid = false,
                    Message = $"AES key size {keyBits} bits is too small (minimum 128 bits)"
                };
            }
            else if (keyBits < 256)
            {
                return new ValidationResult
                {
                    IsValid = true,
                    Message = $"AES key size {keyBits} bits is acceptable but 256 bits recommended",
                    WarningLevel = true
                };
            }
            else
            {
                return new ValidationResult
                {
                    IsValid = true,
                    Message = $"AES key size {keyBits} bits provides strong security"
                };
            }
        }
        
        public class ValidationResult
        {
            public bool IsValid { get; set; }
            public string Message { get; set; }
            public bool WarningLevel { get; set; }
        }
    }
}

// Example usage
public class Program
{
    public static void Main()
    {
        // Configure secure protocols
        SecureProtocolConfiguration.ConfigureSecureSSL();
        
        // Generate secure RSA keys
        var rsaProvider = new SecureProtocolConfiguration.SecureRSAProvider();
        using (var rsa = rsaProvider.CreateSecureRSA(SecureProtocolConfiguration.SecureRSAProvider.SecurityLevel.High))
        {
            var validation = SecureProtocolConfiguration.KeyValidator.ValidateRSAKey(rsa);
            Console.WriteLine($"RSA key validation: {validation.Message}");
        }
        
        // Generate secure symmetric keys
        var symCrypto = new SecureProtocolConfiguration.SecureSymmetricCrypto();
        var aesKey = symCrypto.GenerateSecureKey();
        
        var aesValidation = SecureProtocolConfiguration.KeyValidator.ValidateAESKey(aesKey);
        Console.WriteLine($"AES key validation: {aesValidation.Message}");
        
        // Demonstrate secure encryption
        var plaintext = Encoding.UTF8.GetBytes("Sensitive data requiring strong protection");
        var encrypted = symCrypto.EncryptWithAESGCM(plaintext, aesKey);
        
        Console.WriteLine($"Encrypted {plaintext.Length} bytes with AES-256-GCM");
        
        // Generate ECDH keys
        var dhProvider = new SecureProtocolConfiguration.SecureDiffieHellman();
        using (var ecdh = dhProvider.CreateSecureECDH())
        {
            Console.WriteLine("ECDH key pair generated with secure curve");
        }
    }
}

Detect This Vulnerability in Your Code

Sourcery automatically identifies use of insufficient cryptographic key lengths and many other security issues in your codebase.