Example #1
0
 def test_ecdsa_verify(self):
     with open(os.path.join(fixtures_dir, 'message.txt'), 'rb') as f:
         original_data = f.read()
     with open(os.path.join(fixtures_dir, 'ecdsa_signature'), 'rb') as f:
         signature = f.read()
     public = asymmetric.load_public_key(os.path.join(fixtures_dir, 'keys/test-public-ec-named.key'))
     asymmetric.ecdsa_verify(public, signature, original_data, 'sha1')
Example #2
0
 def test_ecdsa_verify(self):
     with open(os.path.join(fixtures_dir, 'message.txt'), 'rb') as f:
         original_data = f.read()
     with open(os.path.join(fixtures_dir, 'ecdsa_signature'), 'rb') as f:
         signature = f.read()
     public = asymmetric.load_public_key(os.path.join(fixtures_dir, 'keys/test-public-ec-named.key'))
     asymmetric.ecdsa_verify(public, signature, original_data, 'sha1')
Example #3
0
    def test_ecdsa_sign(self):
        original_data = b'This is data to sign'
        private = asymmetric.load_private_key(os.path.join(fixtures_dir, 'keys/test-ec-named.key'))
        public = asymmetric.load_public_key(os.path.join(fixtures_dir, 'keys/test-ec-named.crt'))

        signature = asymmetric.ecdsa_sign(private, original_data, 'sha1')
        self.assertIsInstance(signature, byte_cls)

        asymmetric.ecdsa_verify(public, signature, original_data, 'sha1')
Example #4
0
    def test_ecdsa_sign(self):
        original_data = b'This is data to sign'
        private = asymmetric.load_private_key(os.path.join(fixtures_dir, 'keys/test-ec-named.key'))
        public = asymmetric.load_public_key(os.path.join(fixtures_dir, 'keys/test-ec-named.crt'))

        signature = asymmetric.ecdsa_sign(private, original_data, 'sha1')
        self.assertIsInstance(signature, byte_cls)

        asymmetric.ecdsa_verify(public, signature, original_data, 'sha1')
Example #5
0
    def test_ec_generate(self):
        public, private = asymmetric.generate_pair('ec', curve='secp256r1')

        self.assertEqual('ec', public.algorithm)
        self.assertEqual('secp256r1', public.asn1.curve[1])

        original_data = b'This is data to sign'
        signature = asymmetric.ecdsa_sign(private, original_data, 'sha1')
        self.assertIsInstance(signature, byte_cls)
        asymmetric.ecdsa_verify(public, signature, original_data, 'sha1')
Example #6
0
    def test_ec_generate(self):
        public, private = asymmetric.generate_pair('ec', curve='secp256r1')

        self.assertEqual('ec', public.algorithm)
        self.assertEqual('secp256r1', public.asn1.curve[1])

        original_data = b'This is data to sign'
        signature = asymmetric.ecdsa_sign(private, original_data, 'sha1')
        self.assertIsInstance(signature, byte_cls)
        asymmetric.ecdsa_verify(public, signature, original_data, 'sha1')
Example #7
0
 def test_ecdsa_verify_fail_each_byte(self):
     with open(os.path.join(fixtures_dir, 'message.txt'), 'rb') as f:
         original_data = f.read()
     with open(os.path.join(fixtures_dir, 'ecdsa_signature'), 'rb') as f:
         original_signature = f.read()
     public = asymmetric.load_public_key(os.path.join(fixtures_dir, 'keys/test-public-ec-named.key'))
     for i in range(0, len(original_signature)):
         if i == 0:
             signature = b'\xab' + original_signature[1:]
         elif i == len(original_signature) - 1:
             signature = original_signature[0:-1] + b'\xab'
         else:
             signature = original_signature[0:i] + b'\xab' + original_signature[i+1:]
         with self.assertRaises(errors.SignatureError):
             asymmetric.ecdsa_verify(public, signature, original_data + b'1', 'sha1')
def test_ecdsa_p384_signverify():
    LOGGER.info(
        'Sign data with newly generated NIST P-384 key and verify result')
    setup_keys()
    ha = 'sha384'
    s = ecdsa.sign(pytest.p384, pytest.tbs_str)
    print('[{}]'.format(', '.join(hex(x) for x in list(s.signature))))

    # Preparing an algoroithm
    pubkey_alg = keys.PublicKeyAlgorithm({
        'algorithm':
        keys.PublicKeyAlgorithmId(pytest.p384.algorithm),
        'parameters':
        keys.ECDomainParameters(name='named', value=pytest.p384.curve)
    })

    # Preparing a PublicKeyInfo
    pubkey_asn1 = core.BitString.load(pytest.p384.pkey)
    pubkey_info = keys.PublicKeyInfo({
        'algorithm':
        pubkey_alg,
        'public_key':
        pubkey_asn1.cast(keys.ECPointBitString)
    })

    # Load a public key into the oscrypto engine to using it in the verify function
    public = load_public_key(pubkey_info)

    # Assert wrong text
    with pytest.raises(SignatureError):
        ecdsa_verify(public, s.signature, pytest.tbs_str_fail, ha)

    # Assert wrong key
    with pytest.raises(SignatureError):
        # Preparing a PublicKeyInfo
        pubkey_asn1 = core.BitString.load(pytest.p384_fail.pkey)
        pubkey_info = keys.PublicKeyInfo({
            'algorithm':
            pubkey_alg,
            'public_key':
            pubkey_asn1.cast(keys.ECPointBitString)
        })

        # Load a public key into the oscrypto engine to using it in the verify function
        public = load_public_key(pubkey_info)
        ecdsa_verify(public, s.signature, pytest.tbs_str, ha)
Example #9
0
 def test_ecdsa_verify_fail_each_byte(self):
     with open(os.path.join(fixtures_dir, 'message.txt'), 'rb') as f:
         original_data = f.read()
     with open(os.path.join(fixtures_dir, 'ecdsa_signature'), 'rb') as f:
         original_signature = f.read()
     public = asymmetric.load_public_key(
         os.path.join(fixtures_dir, 'keys/test-public-ec-named.key'))
     for i in range(0, len(original_signature)):
         if i == 0:
             signature = b'\xab' + original_signature[1:]
         elif i == len(original_signature) - 1:
             signature = original_signature[0:-1] + b'\xab'
         else:
             signature = original_signature[
                 0:i] + b'\xab' + original_signature[i + 1:]
         with self.assertRaises(errors.SignatureError):
             asymmetric.ecdsa_verify(public, signature,
                                     original_data + b'1', 'sha1')
Example #10
0
    def test_ec_generate(self):
        public, private = asymmetric.generate_pair('ec', curve='secp256r1')

        self.assertEqual('ec', public.algorithm)
        self.assertEqual('secp256r1', public.asn1.curve[1])

        original_data = b'This is data to sign'
        signature = asymmetric.ecdsa_sign(private, original_data, 'sha1')
        self.assertIsInstance(signature, byte_cls)
        asymmetric.ecdsa_verify(public, signature, original_data, 'sha1')

        raw_public = asymmetric.dump_public_key(public)
        asymmetric.load_public_key(raw_public)
        raw_private = asymmetric.dump_private_key(private, None)
        asymmetric.load_private_key(raw_private, None)

        self.assertIsInstance(private.fingerprint, byte_cls)
        self.assertIsInstance(public.fingerprint, byte_cls)
        self.assertEqual(private.fingerprint, public.fingerprint)
Example #11
0
    def test_ecdsa(self):
        # A key we generated earlier
        self.session.create_domain_parameters(KeyType.EC, {
            Attribute.EC_PARAMS: encode_named_curve_parameters('secp256r1'),
        }, local=True)\
            .generate_keypair()

        priv = self.session.get_key(key_type=KeyType.EC,
                                    object_class=ObjectClass.PRIVATE_KEY)

        signature = priv.sign(b'Data to sign', mechanism=Mechanism.ECDSA_SHA1)
        # Encode as ASN.1 for OpenSSL
        signature = encode_ecdsa_signature(signature)

        from oscrypto.asymmetric import load_public_key, ecdsa_verify

        pub = self.session.get_key(key_type=KeyType.EC,
                                   object_class=ObjectClass.PUBLIC_KEY)
        pub = load_public_key(encode_ec_public_key(pub))

        ecdsa_verify(pub, signature, b'Data to sign', 'sha1')
Example #12
0
def test_ecdsa_signverify(curve, hashname):
    key_object = objects.ECCKey(0xE100)
    pkey, _ = crypto.generate_pair(key_object, curve=curve)
    key_object_fail = objects.ECCKey(0xE101)
    pkey_fail, _ = crypto.generate_pair(key_object_fail, curve=curve)
    ha = hashname
    s = crypto.ecdsa_sign(key_object, tbs_str)
    print('[{}]'.format(', '.join(hex(x) for x in list(s.signature))))

    # Preparing a PublicKeyInfo
    pubkey_info = keys.PublicKeyInfo.load(pkey)

    # Load a public key into the oscrypto engine to using it in the verify function
    public = load_public_key(pubkey_info)

    ecdsa_verify(public, s.signature, tbs_str, ha)

    # Assert wrong text
    with pytest.raises(SignatureError):
        ecdsa_verify(public, s.signature, tbs_str_fail, ha)

    # Assert wrong key
    with pytest.raises(SignatureError):
        # Preparing a PublicKeyInfo
        pubkey_info = keys.PublicKeyInfo.load(pkey_fail)

        # Load a public key into the oscrypto engine to using it in the verify function
        public = load_public_key(pubkey_info)
        ecdsa_verify(public, s.signature, tbs_str, ha)
from oscrypto import asymmetric
from asn1crypto import pem, keys
import os

from .. import config

root = os.path.dirname(os.path.dirname(os.path.dirname(__file__)))
assets = os.path.join(root, 'assets')

pc_path = os.path.join(assets, 'Package Control.sublime-package')
pc_sig_path = os.path.join(assets, 'Package Control.sublime-package.sig')

public_key_pem = config.read('signing')['public_key']
public_key = asymmetric.load_public_key(public_key_pem.encode('ascii'))
private_key_pem = config.read_secret('private_key')
private_key = asymmetric.load_private_key(private_key_pem.encode('ascii'),
                                          None)

with open(pc_sig_path, 'wb') as wf, open(pc_path, 'rb') as rf:
    pc_data = rf.read()
    sig = asymmetric.ecdsa_sign(private_key, pc_data, 'sha256')
    asymmetric.ecdsa_verify(public_key, sig, pc_data, 'sha256')
    wf.write(pem.armor('PACKAGE CONTROL SIGNATURE', sig))
    print('Signature written to %s' % pc_sig_path)
def validate_ocsp_response(cert, issuer, ocsp_request_obj, ocsp_response_objs,
                           current_time):
    #print(cert.ocsp_urls) # Just to see how many urls there are
    subject = cert['tbs_certificate']['subject'].native
    errors = {}
    warnings = {}
    lints_list = []
    count = 0
    lints = {}

    for (ocsp_url, ocsp_response_obj) in ocsp_response_objs:
        count += 1
        lints['domain'] = subject['common_name']
        lints['ocsp_url'] = ocsp_url
        lints['response_count'] = count
        #print(ocsp_response_obj.native)
        errors = {}
        warnings = {}
        if isinstance(ocsp_response_obj, urllib.error.HTTPError):
            errors['HTTPError'] = str(ocsp_response_obj)
            lints['errors'] = errors
            lints['warnings'] = warnings
            lints_list.append(lints)
            return lints_list

        if isinstance(ocsp_response_obj, ValueError):
            errors['ValueError'] = str(ocsp_response_obj)
            lints['errors'] = errors
            lints['warnings'] = warnings
            lints_list.append(lints)
            return lints_list

        if (ocsp_response_obj['response_status'].native == 'unauthorized'):
            errors['Unauthorized'] = 'Responder returned unauthorized'
            lints['errors'] = errors
            lints['warnings'] = warnings
            lints_list.append(lints)
            continue

        if (ocsp_response_obj['response_status'].native == 'malformed_request'
            ):
            errors['ResponseFailure'] = 'Responder returned malformed request'
            lints['errors'] = errors
            lints['warnings'] = warnings
            lints_list.append(lints)
            continue

        request_nonce = ocsp_request_obj.nonce_value
        #print (ocsp_response_obj.native)
        response_nonce = ocsp_response_obj.nonce_value
        if request_nonce and response_nonce and request_nonce.native != response_nonce.native:
            errors[
                'NonceVerificationFailure'] = 'Unable to verify OCSP response since the request and response nonces do not match'

        if ocsp_response_obj['response_status'].native != 'successful':
            errors['OCSPCheckFailure'] = 'OCSP check returned as failed'

        response_bytes = ocsp_response_obj['response_bytes']
        if response_bytes['response_type'].native != 'basic_ocsp_response':
            errors[
                'ResponseTypeFailure'] = 'OCSP response is not Basic OCSP Response'

        parsed_response = response_bytes['response'].parsed
        tbs_response = parsed_response['tbs_response_data']
        certificate_response = tbs_response['responses'][0]

        certificate_id = certificate_response['cert_id']
        algo = certificate_id['hash_algorithm']['algorithm'].native

        certificate_issuer_name_hash = certificate_id[
            'issuer_name_hash'].native
        certificate_issuer_key_hash = certificate_id['issuer_key_hash'].native
        certificate_serial_number = certificate_id['serial_number'].native

        certificate_issuer_name_hash_from_file = getattr(cert.issuer, algo)
        certificate_issuer_key_hash_from_file = getattr(
            issuer.public_key, algo)
        certificate_serial_number_from_file = cert.serial_number

        if certificate_serial_number != certificate_serial_number_from_file:
            errors['CertificateSerialMismatchFailure'] = \
            'OCSP response certificate serial number does not match request certificate serial number'

        if certificate_issuer_key_hash != certificate_issuer_key_hash_from_file:
            errors[
                'IssuerKeyMismatchFailure'] = 'OCSP response issuer key hash does not match request certificate issuer key hash'

        if certificate_issuer_name_hash != certificate_issuer_name_hash_from_file:
            errors['IssuerNameHashMismatchFailure'] = \
                'OCSP response issuer name hash does not match request certificate issuer name hash'

        this_update_time = certificate_response['this_update'].native
        if current_time < this_update_time:
            errors[
                'ThisUpdateTimeError'] = 'OCSP reponse update time is from the future'

        if "next_update" not in certificate_response or certificate_response[
                'next_update'].native is None:
            warnings[
                'NextUpdateTimeMissing'] = 'OCSP response does not contain next update time'
        else:
            next_update_time = certificate_response['next_update'].native
            if current_time > next_update_time:
                errors[
                    'NextUpdateTimeFailure'] = 'OCSP reponse next update time is in the past'

        registry = CertificateRegistry(trust_roots=[issuer])

        if tbs_response['responder_id'].name == 'by_key':
            key_identifier = tbs_response['responder_id'].native
            signing_cert = registry.retrieve_by_key_identifier(key_identifier)

        elif tbs_response['responder_id'].name == 'by_name':
            signing_certs = registry.retrieve_by_name(
                tbs_response['responder_id'].chosen, None)
            if signing_certs is not None and len(signing_certs) > 0:
                signing_cert = signing_certs[0]
            else:
                signing_cert = None

        if signing_cert is None:
            errors[
                'SigningCetificateNotFoundFailure'] = 'OCSP response signing certificate not found'
            lints['errors'] = errors
            lints['warnings'] = warnings
            lints_list.append(lints)
            continue

        if issuer.issuer_serial != signing_cert.issuer_serial:
            if signing_cert_issuer.issuer_serial != issuer.issuer_serial:
                errors[
                    'UnauthorizedSigningCertificateFailure'] = 'OCSP response signed by unauthorized certificate'

            extended_key_usage = signing_cert.extended_key_usage_value
            if 'ocsp_signing' not in extended_key_usage.native:
                errors['ExtendedKeyUsageExtensionValueFailure'] = \
                    'OCSP response signing certificate is not the issuing certificate and it does not have value "ocsp_signing"\
                    for the extended key usage extension'

        sig_algo = parsed_response['signature_algorithm'].signature_algo
        hash_algo = parsed_response['signature_algorithm'].hash_algo
        try:
            check_cert = asymmetric.load_certificate(signing_cert)
            if sig_algo == 'rsassa_pkcs1v15':
                asymmetric.rsa_pkcs1v15_verify(
                    check_cert, parsed_response['signature'].native,
                    tbs_response.dump(), hash_algo)
            elif sig_algo == 'dsa':
                asymmetric.dsa_verify(check_cert,
                                      parsed_response['signature'].native,
                                      tbs_response.dump(), hash_algo)
            elif sig_algo == 'ecdsa':
                asymmetric.ecdsa_verify(check_cert,
                                        parsed_response['signature'].native,
                                        tbs_response.dump(), hash_algo)
            else:
                errors[
                    'UnsupportedAlgorithmFailure'] = 'OCSP response signature uses unsupported algorithm'

        except (oscrypto.errors.SignatureError):
            errors[
                'SignatureVerificationFailure'] = 'OCSP response signature could not be verified'

        if certificate_response['cert_status'].name == 'revoked':
            revocation_data = certificate_response['cert_status'].chosen
            if revocation_data['revocation_reason'].native is None:
                errors[
                    'CertificateValidityFailure'] = 'Certificate revoked due to unknown reason'
            else:
                errors[
                    'CertificateValidityFailure'] = 'Certicate revoked due to ' + revocation_data[
                        'revocation_reason'].human_friendly

        if 'certs' in parsed_response and parsed_response[
                'certs'].native != None:
            #TODO Check for legit certs
            pass


#            print(parsed_response['certs'].native)

        if len(errors) == 0:
            errors['NoFailure'] = 'No errors in OCSP response'
        if len(warnings) == 0:
            warnings['NoWarning'] = 'No warnings in OCSP response'

        lints['errors'] = errors
        lints['warnings'] = warnings
        lints_list.append(lints)

    return lints_list