1111from cryptography .hazmat ._oid import NameOID
1212from cryptography .hazmat .primitives import hashes
1313from cryptography .hazmat .primitives ._serialization import Encoding
14- from cryptography .hazmat .primitives .asymmetric import rsa , dsa
14+ from cryptography .hazmat .primitives .asymmetric import rsa
1515from cryptography .hazmat .primitives .asymmetric .ec import EllipticCurvePublicKey
1616from cryptography .x509 import Certificate
1717from django .conf import settings
7474)
7575from checks .tasks .tls .tls_constants import (
7676 CERT_SIGALG_GOOD ,
77- CERT_RSA_DSA_MIN_KEY_SIZE ,
7877 CERT_CURVES_GOOD ,
79- CERT_CURVE_MIN_KEY_SIZE ,
8078 CERT_EC_CURVES_GOOD ,
8179 CERT_EC_CURVES_PHASE_OUT ,
8280 MAIL_ALTERNATE_CONNLIMIT_HOST_SUBSTRS ,
81+ CERT_RSA_MIN_GOOD_KEY_SIZE ,
82+ CERT_RSA_MIN_PHASE_OUT_KEY_SIZE ,
8383 SIGNATURE_ALGORITHMS_BAD_HASH ,
8484 SIGNATURE_ALGORITHMS_PHASE_OUT_HASH ,
8585)
@@ -459,7 +459,7 @@ def check_pubkey(certificates: List[Certificate], mode: ChecksMode):
459459 """
460460 Check that all provided certificates meet NCSC requirements.
461461 """
462- # NCSC guidelines B3-3, B5-1
462+ # NCSC guidelines 3.3.2.x
463463 bad_pubkey = []
464464 phase_out_pubkey = []
465465 if mode == ChecksMode .WEB :
@@ -474,30 +474,32 @@ def check_pubkey(certificates: List[Certificate], mode: ChecksMode):
474474 for cert in certificates :
475475 common_name = get_common_name (cert )
476476 public_key = cert .public_key ()
477- public_key_type = type (public_key )
477+ key_type = type (public_key )
478478 key_size = public_key .key_size
479+ curve = getattr (public_key , "curve" , None )
479480
480- failed_key_type = ""
481- curve = ""
482- # Note that DH fields are checked in the key exchange already
483- # https://github.com/internetstandards/Internet.nl/pull/1218#issuecomment-1944496933
484- if public_key_type is rsa .RSAPublicKey and key_size < CERT_RSA_DSA_MIN_KEY_SIZE :
485- failed_key_type = public_key_type .__name__
486- elif public_key_type is dsa .DSAPublicKey and key_size < CERT_RSA_DSA_MIN_KEY_SIZE :
487- failed_key_type = public_key_type .__name__
488- elif public_key_type in CERT_CURVES_GOOD and key_size < CERT_CURVE_MIN_KEY_SIZE :
489- failed_key_type = public_key_type .__name__
490- elif public_key_type is EllipticCurvePublicKey and public_key .curve not in CERT_EC_CURVES_GOOD :
491- failed_key_type = public_key_type .__name__
492- if failed_key_type :
493- message = f"{ common_name } : { failed_key_type } -{ key_size } key_size"
494- if curve :
495- message += f", curve: { curve } "
496- if public_key .curve in CERT_EC_CURVES_PHASE_OUT :
497- phase_out_pubkey .append (message )
498- else :
499- bad_pubkey .append (message )
500- pubkey_score = pubkey_score_bad
481+ is_good = (
482+ (key_type is rsa .RSAPublicKey and key_size >= CERT_RSA_MIN_GOOD_KEY_SIZE )
483+ or (key_type in CERT_CURVES_GOOD )
484+ or (key_type is EllipticCurvePublicKey and curve in CERT_EC_CURVES_GOOD )
485+ )
486+
487+ if is_good :
488+ continue
489+
490+ message = f"{ common_name } : { key_type .__name__ } -{ key_size } "
491+ if curve :
492+ message += f", curve: { curve } "
493+
494+ is_phase_out = (curve in CERT_EC_CURVES_PHASE_OUT ) or (
495+ key_type is rsa .RSAPublicKey and key_size >= CERT_RSA_MIN_PHASE_OUT_KEY_SIZE
496+ )
497+
498+ if is_phase_out :
499+ phase_out_pubkey .append (message )
500+ else :
501+ bad_pubkey .append (message )
502+ pubkey_score = pubkey_score_bad
501503 return pubkey_score , bad_pubkey , phase_out_pubkey
502504
503505
0 commit comments