def test_basic(self): # test the default view response = self.client.get( reverse('default', kwargs={'serial': self.ca.serial})) self.assertEqual(response.status_code, 200) crl = crypto.load_crl(crypto.FILETYPE_ASN1, response.content) self.assertEqual(response['Content-Type'], 'application/pkix-crl') self.assertIsNone(crl.get_revoked()) # revoke a certificate cert = Certificate.objects.get(serial=self.cert.serial) cert.revoke() # fetch again - we should see a cached response response = self.client.get( reverse('default', kwargs={'serial': self.ca.serial})) self.assertEqual(response.status_code, 200) self.assertEqual(response['Content-Type'], 'application/pkix-crl') crl = crypto.load_crl(crypto.FILETYPE_ASN1, response.content) self.assertIsNone(crl.get_revoked()) # clear the cache and fetch again cache.clear() response = self.client.get( reverse('default', kwargs={'serial': self.ca.serial})) self.assertEqual(response.status_code, 200) self.assertEqual(response['Content-Type'], 'application/pkix-crl') crl = crypto.load_crl(crypto.FILETYPE_ASN1, response.content) self.assertEqual(len(crl.get_revoked()), 1)
def test_revoked(self): cert = Certificate.objects.get(serial=self.cert.serial) cert.revoke() stdout, stderr = self.cmd('dump_crl', stdout=BytesIO(), stderr=BytesIO()) self.assertEqual(stderr, b'') crl = crypto.load_crl(crypto.FILETYPE_PEM, stdout) revoked = crl.get_revoked() self.assertEqual(len(revoked), 1) self.assertIsNone(revoked[0].get_reason()) self.assertSerial(revoked[0], cert) # try all possible reasons for readable_reason, byte_reason in [ (b'Unspecified', b'unspecified'), (b'Key Compromise', b'keyCompromise'), (b'CA Compromise', b'CACompromise'), (b'Affiliation Changed', b'affiliationChanged'), (b'Superseded', b'superseded'), (b'Cessation Of Operation', b'cessationOfOperation'), (b'Certificate Hold', b'certificateHold'), ]: cert.revoked_reason = byte_reason.decode('utf-8') cert.save() stdout, stderr = self.cmd('dump_crl', stdout=BytesIO(), stderr=BytesIO()) crl = crypto.load_crl(crypto.FILETYPE_PEM, stdout) revoked = crl.get_revoked() self.assertEqual(len(revoked), 1) self.assertEqual(revoked[0].get_reason(), readable_reason) self.assertSerial(revoked[0], cert)
def get_crl_object(cert_crl): if cert_crl==None: return else: logger.debug('cert_crl--is %s'%(cert_crl)) cert_crl_url=re.findall("[http|https][\w|\W]*(?:\.crl)",cert_crl) logger.debug('cert_crl url--is %s'%(cert_crl_url)) req = urllib2.Request(cert_crl_url[0]) req.add_header('User-Agent','Mozilla/5.0') try: response = urllib2.urlopen(req, timeout=3) except: logger.debug('cert_crl error--') return fp = response.read() try: try: try: crl_object = crypto.load_crl(crypto.FILETYPE_PEM, fp) except Exception,e: crl_object = crypto.load_crl(crypto.FILETYPE_ASN1, fp) except Exception,e: crl_object = crypto.load_crl(crypto.FILETYPE_TXT, fp) except Exception, e: crl_object = None if crl_object is None: return else: return crl_object
def saveCRL(filename, rawCRL): crl = ("-----BEGIN X509 CRL-----\n" + re.sub("(.{64})", "\\1\n", rawCRL, 0, re.DOTALL) + "\n-----END X509 CRL-----\n") crypto.load_crl(crypto.FILETYPE_PEM, crl) with open(filename, "w") as crlFile: crlFile.write(crl)
def try_openssl_module(filename, format): from OpenSSL import crypto types = { FILETYPE_PEM: crypto.FILETYPE_PEM, FILETYPE_DER: crypto.FILETYPE_ASN1 } if filename == '-': crl = crypto.load_crl(types[format], sys.stdin.buffer.read()) else: with open(filename, 'rb') as f: crl = crypto.load_crl(types[format], f.read()) return set(int(r.get_serial(), 16) for r in crl.get_revoked())
def get_pck_crl(self, target, dec=None): self.clear_errors() if ( target != 'processor' and target != 'platform' ): self.error('Invalid argument') return None url= self._geturl('pckcrl') if self.ApiVersion<3: url+= "?ca={:s}".format(target) else: url+= "?ca={:s}&encoding=der".format(target) response= self._get_request(url, False) if response.status_code != 200: self.error(response.status_code) return None # Verify expected headers if not response.headers['Request-ID']: self.error("Response missing Request-ID header") return None if not response.headers['SGX-PCK-CRL-Issuer-Chain']: self.error("Response missing SGX-PCK-CRL-Issuer-Chain header") return None # Validate the CRL chain= parse.unquote( response.headers['SGX-PCK-CRL-Issuer-Chain'] ) chain_pems= self.parse_chain_pem(chain) pychain= self.pems_to_pycerts(chain_pems) pychain= self.sort_pycert_chain(pychain) if pychain is None: return None crl= response.content if self.ApiVersion<3: crl_str= str(crl, dec) pycrl= crypto.load_crl(crypto.FILETYPE_PEM, crl) else: crl_str= binascii.hexlify(crl).decode(dec) pycrl= crypto.load_crl(crypto.FILETYPE_ASN1, crl) if not self.verify_crl_trust(pychain, pycrl): self.error("Could not validate certificate using trust chain") return None return [crl_str, response.headers['SGX-PCK-CRL-Issuer-Chain']]
def test_and_update_crls(temp_dir, current_crls_dir, logger): crl_dir = Path(temp_dir) crl_files = list(crl_dir.glob('*.crl')) for crl_file_path in crl_files[:]: with open(crl_file_path, 'rb') as crl_file: try: logger.info("Testing CRL file {}".format(crl_file_path)) crypto.load_crl(crypto.FILETYPE_ASN1, crl_file.read()) shutil.copy2(crl_file_path, current_crls_dir) except crypto.Error: logger.error( "Could not load CRL file {}".format(crl_file_path) + "; Removing file...") if os.path.isfile(crl_file_path): os.remove(crl_file_path)
def _prepare_revoked(self): ca = self._create_ca() crl = crypto.load_crl(crypto.FILETYPE_PEM, ca.crl) self.assertIsNone(crl.get_revoked()) cert = self._create_cert(ca=ca) cert.revoke() return (ca, cert)
def get_state(username): user_crt = os.path.join(LEAF_PATH, f'{username}.crt') if not os.path.exists(user_crt): return 'none', 0 with open(user_crt, 'r') as f: cert = c.load_certificate(c.FILETYPE_PEM, f.read()) serial = format(cert.get_serial_number(), 'x') with open(ROOT_CRL, 'r') as f: crl = ''.join(f.readlines()) crl_obj = c.load_crl(c.FILETYPE_PEM, crl) revoked_list = crl_obj.get_revoked() revoked_list = [] if not revoked_list else revoked_list for rvk in revoked_list: rvk_serial = rvk.get_serial().decode() if rvk_serial == serial: return 'revoked', 0 expire = datetime.strptime( cert.get_notAfter().decode('utf-8'), '%Y%m%d%H%M%SZ', ) if expire < datetime.now(): return 'expired', expire elif expire < datetime.now() - timedelta(days=10): return 'warn', expire return 'ok', expire
def verify_chain(self, trusted_certs=None, crl_path=None): #<UT> #Certificate revocation check if crl_path: crl_file = os.path.join(crl_path, self.get_issuer()) if os.path.isfile(crl_file): with open(crl_file, 'r') as f: crl_obj = crypto.load_crl(crypto.FILETYPE_PEM, f.read()) revoked_certs = crl_obj.get_revoked() for rc in revoked_certs: serial = int(rc.get_serial(), 16) # conversion from hex to dec if serial == self.get_serial_number(): raise GidRevoked( "Certificate with serial number 0x%s for %s has been revoked by %s." % (rc.get_serial(), self.get_subject(), self.get_issuer())) # do the normal certificate verification stuff trusted_root = Certificate.verify_chain(self, trusted_certs) if self.parent: # make sure the parent's hrn is a prefix of the child's hrn if not hrn_authfor_hrn(self.parent.get_hrn(), self.get_hrn()): raise GidParentHrn( "This cert HRN %s isn't in the namespace for parent HRN %s" % (self.get_hrn(), self.parent.get_hrn())) # Parent must also be an authority (of some type) to sign a GID # There are multiple types of authority - accept them all here if not self.parent.get_type().find('authority') == 0: raise GidInvalidParentHrn( "This cert %s's parent %s is not an authority (is a %s)" % (self.get_hrn(), self.parent.get_hrn(), self.parent.get_type())) # Then recurse up the chain - ensure the parent is a trusted # root or is in the namespace of a trusted root self.parent.verify_chain(trusted_certs) else: # make sure that the trusted root's hrn is a prefix of the child's trusted_gid = GID(string=trusted_root.save_to_string()) trusted_type = trusted_gid.get_type() trusted_hrn = trusted_gid.get_hrn() #if trusted_type == 'authority': # trusted_hrn = trusted_hrn[:trusted_hrn.rindex('.')] cur_hrn = self.get_hrn() if not hrn_authfor_hrn(trusted_hrn, cur_hrn): raise GidParentHrn( "Trusted root with HRN %s isn't a namespace authority for this cert: %s" % (trusted_hrn, cur_hrn)) # There are multiple types of authority - accept them all here if not trusted_type.find('authority') == 0: raise GidInvalidParentHrn( "This cert %s's trusted root signer %s is not an authority (is a %s)" % (self.get_hrn(), trusted_hrn, trusted_type)) return
def revoke(): commonName = (request.params.get('cn'), ) revoked = crypto.Revoked() cur = conn.cursor() cur.execute('SELECT crl from crl') crlresp = cur.fetchone() if crlresp is None: crl = crypto.CRL() else: crl = crypto.load_crl(crypto.FILETYPE_PEM, crlresp[0]) cur.execute("""SELECT ROWID, serial FROM certs WHERE domain = ? and revoked = 0""", commonName) resp = cur.fetchone() if resp is None: return("Cannot find cert in database \n") row_id = (resp[0], ) serial = resp[1] revoked.set_serial(hex(serial).replace('0x', '')) revoked.set_rev_date(datetime.utcnow().strftime('%Y%m%d%H%M%SZ')) revoked.set_reason('unspecified') crl.add_revoked(revoked) crl_out = (crl.export(caCert, caKey), ) if crlresp is None: cur.execute('INSERT INTO crl VALUES(?)', crl_out) else: cur.execute('UPDATE crl SET crl=? where ROWID = 1', crl_out) cur.execute("UPDATE certs SET revoked=1 WHERE ROWID = ?", row_id) conn.commit() cur.close() return("Certificate revoked\n")
def test_crl(self): ca, cert = self._prepare_revoked() crl = crypto.load_crl(crypto.FILETYPE_PEM, ca.crl) revoked_list = crl.get_revoked() self.assertIsNotNone(revoked_list) self.assertEqual(len(revoked_list), 1) self.assertEqual(int(revoked_list[0].get_serial()), cert.serial_number)
def validate_certificate(self, certificate: str, chain: str, crl: str = None) -> None: """ Tests if a certificate has been signed by the chain, is not revoked and has not yet been expired. :param certificate: the certificate to test as string :param chain: the certificate chain file content as string :param crl: the certificate revocation list file content as string :raises: InvalidCertificateException if the certificate is invalid :return: None """ # root and intermediary certificate need to be split cas = pem.parse(chain.encode()) store = X509Store() for ca in cas: store.add_cert(self._to_cert(str(ca))) cert = self._to_cert(certificate) if crl: parsed_crl = load_crl(FILETYPE_PEM, crl) store.set_flags(X509StoreFlags.CRL_CHECK) store.add_crl(parsed_crl) ctx = X509StoreContext(store, cert) err_msg = 'Certificate is invalid' try: result = ctx.verify_certificate() if result is not None: raise InvalidCertificateException(err_msg) except Exception as e: raise InvalidCertificateException('%s: %s' % (err_msg, str(e)))
def test_crl_view(self): ca = self._create_ca() response = self.client.get(reverse('x509:crl', args=[ca.pk])) self.assertEqual(response.status_code, 200) crl = crypto.load_crl(crypto.FILETYPE_PEM, response.content) revoked_list = crl.get_revoked() self.assertIsNone(revoked_list)
def load_crl(): try: pem = open(config.root + '.crl', 'rt').read() root_crl = crypto.load_crl(crypto.FILETYPE_PEM, pem) except IOError: root_crl = None return root_crl
def load_certificates(self): # root => issuer== commom name rootCerts = () trustedCerts = () crlList = () dirname = ["../security/CCCerts/", "../security/CRL/"] for filename in listdir(dirname[0]): try: cert_info = open(dirname[0] + filename, 'rb').read() except IOError: print("IO Exception while reading file : {:s} {:s}".format( dirname[0], filename)) exit(10) else: if ".cer" in filename: try: if "0012" in filename or "0013" in filename or "0015" in filename: certAuth = load_certificate( FILETYPE_PEM, cert_info) elif "Raiz" in filename: root = load_certificate(FILETYPE_ASN1, cert_info) else: certAuth = load_certificate( FILETYPE_ASN1, cert_info) except: print( "Exception while loading certificate from file : {:s} {:s}" .format(dirname[0], filename)) exit(10) else: trustedCerts = trustedCerts + (certAuth, ) elif ".crt" in filename: try: if "ca_ecc" in filename: root = load_certificate(FILETYPE_PEM, cert_info) elif "-self" in filename: root = load_certificate(FILETYPE_PEM, cert_info) else: root = load_certificate(FILETYPE_ASN1, cert_info) except: print( "Exception while loading certificate from file : {:s} {:s}" .format(dirname[0], filename)) exit(10) else: rootCerts = rootCerts + (root, ) # print("Loaded Root certificates : {:d} out of {:d} ".format(len(rootCerts), len(listdir(dirname[0])))) # print("Loaded Authentication certificates: {:d} out of {:d} ".format(len(trustedCerts), len(listdir(dirname[0])))) for filename in listdir(dirname[1]): try: crl_info = open(dirname[1] + "/" + filename, 'rb').read() except IOError: print("IO Exception while reading file : {:s} {:s}".format( dirname[0], filename)) else: if ".crl" in filename: crls = load_crl(FILETYPE_ASN1, crl_info) crlList = crlList + (crls, ) # print("Certificate revocation lists loaded: {:d} out of {:d} ".format(len(crlList), len(listdir(dirname[1])))) return rootCerts, trustedCerts, crlList
def _download_http_crl(endpoint, key_identifier): """ :param endpoint: url della crl :param key_identifier: chiave identificativa dell'issuer del certificato :return: """ crl_dest = make_crl_store_path(endpoint, key_identifier) + ".crl" crl_meta_dest = make_crl_store_path(endpoint, key_identifier) + ".txt" try: r = requests.get(endpoint) if r.status_code == 200: try: crl = crypto.load_crl(crypto.FILETYPE_PEM, r.content) except: crl_x509 = x509.load_der_x509_crl(r.content, default_backend()) crl = crypto.CRL.from_cryptography(crl_x509) with open(crl_dest, 'w') as f: f.write(crypto.dump_crl(crypto.FILETYPE_PEM, crl).decode()) with open(crl_meta_dest, 'w') as f: f.write(endpoint) else: LOG.error('Errore durante il download della CRL con endpoint = {}'. format(endpoint), extra=set_client_ip()) except Exception as e: LOG.error( 'Eccezione durante il download della CRL con key_identifier = {}'. format(key_identifier), extra=set_client_ip()) LOG.error("Exception: {}".format(str(e)), extra=set_client_ip())
def test_010_check_serialagainstcrl(self): """ CAhandler.check_serial_against_crl with a serial number already in CRL""" # crl = crypto.load_crl(crypto.FILETYPE_PEM, open('ca/sub-ca-crl.pem').read()) with open('ca/sub-ca-crl.pem', 'r') as fso: crl = crypto.load_crl(crypto.FILETYPE_PEM, fso.read()) self.assertTrue( self.cahandler.check_serial_against_crl(crl, '5d0e9535'))
def _parse_crl_cert(self, crl_dir_path): if not crl_dir_path: raise ValueError("No capath provided to CRL check.") try: files = [join(crl_dir_path, f) for f in listdir( crl_dir_path) if isfile(join(crl_dir_path, f))] except Exception: raise ValueError("Wrong or empty capath provided to CRL check.") crl_checklist = [] for f in files: fs = None try: fs = open(f, "r").read() crl = crypto.load_crl(crypto.FILETYPE_PEM, fs) revoked = crl.get_revoked() if not revoked: continue for r in revoked: try: r_serial = int(r.get_serial(), 16) crl_checklist.append(r_serial) except Exception: pass except Exception: # Directory can have other files also pass if crl_checklist: return crl_checklist else: raise ValueError("No valid CRL found at capath")
def test_openssl(): codeur_bundle = SSLCABundle('c:/private/tranquilit-codeur.crt') codeur = codeur_bundle.certificates()[0] trusted_ca = SSLCABundle(certifi.where()) print codeur_bundle.certificate_chain(codeur) codeur.verify_signature_with(codeur_bundle) print trusted_ca.certificate_chain(codeur) for ca in codeur_bundle.certificate_chain(codeur): print ca.crl_urls() for ca in trusted_ca.certificates(): print ca.crl_urls() store = crypto.X509Store() store.set_flags( ( crypto.X509StoreFlags.CRL_CHECK | crypto.X509StoreFlags.CB_ISSUER_CHECK )) for cert in trusted_ca.certificates(): store.add_cert(cert.as_X509()) # load all the crl... issuer = trusted_ca.is_known_issuer(codeur) crl = requests.get('http://crl.usertrust.com/UTN-USERFirst-Object.crl').content crlcert = crypto.load_crl(crypto.FILETYPE_ASN1,crl) store.add_crl(crlcert) store_ctx = crypto.X509StoreContext(store,cert.as_X509()) try: print store_ctx.verify_certificate() except Exception as e: print e
def verify_cert(): """ Check that the user cert is valid. things to check/return not revoked Expiry time warn if less than 21 days """ if os.path.exists(os.path.expanduser('~/.rpmfusion.upn')): print('Kerberos configured, cert ignored') return my_cert = _open_cert() valid_until = my_cert.get_notAfter()[:8].decode() dateFmt = '%Y%m%d' delta = datetime.datetime.now() + datetime.timedelta(days=21) warn = datetime.datetime.strftime(delta, dateFmt) print('cert expires: %s-%s-%s' % (valid_until[:4], valid_until[4:6], valid_until[6:8])) if valid_until < warn: print('WARNING: Your cert expires soon.') if hasattr(crypto, 'load_crl'): crl_url = "https://admin.fedoraproject.org/ca/crl.pem" raw_crl = requests.get(crl_url).content crl = crypto.load_crl(crypto.FILETYPE_PEM, raw_crl) revoked = crl.get_revoked() serial_no = my_cert.get_serial_number() if serial_no in [int(cert.get_serial(), 16) for cert in revoked]: print('WARNING: Your cert appears in the revocation list.') print(' ' + crl_url)
def _parse_crl_cert(self, crl_dir_path): if not crl_dir_path: raise ValueError("No capath provided to CRL check.") try: files = [ join(crl_dir_path, f) for f in listdir(crl_dir_path) if isfile(join(crl_dir_path, f)) ] except Exception: raise ValueError("Wrong or empty capath provided to CRL check.") crl_checklist = [] for f in files: fs = None try: fs = open(f, "r").read() crl = crypto.load_crl(crypto.FILETYPE_PEM, fs) revoked = crl.get_revoked() if not revoked: continue for r in revoked: try: r_serial = int(r.get_serial(), 16) crl_checklist.append(r_serial) except Exception: pass except Exception: # Directory can have other files also pass if crl_checklist: return crl_checklist else: raise ValueError("No valid CRL found at capath")
def test_basic(self): stdout, stderr = self.cmd('dump_crl', stdout=BytesIO(), stderr=BytesIO()) self.assertEqual(stderr, b'') crl = crypto.load_crl(crypto.FILETYPE_PEM, stdout) self.assertIsNone(crl.get_revoked())
def load_crl(): try: pem = open(config.root+'.crl', 'rt').read() root_crl = crypto.load_crl(crypto.FILETYPE_PEM, pem) except IOError: root_crl = None return root_crl
def verify(chain, reference_time=None, crls=None, **kwargs): """ Validates a certificate chain. `chain` is a list of paths to certificates forming a chain. `reference_time` is a reference time of validation in seconds since the epoch. `crls` is a list of paths to CRLs. `kwargs` are other, unexpected arguments. The returned result is a list containing a single error code returned by pyOpenSSL. """ chain = list(chain) try: for i, certificate_path in enumerate(chain): with open(certificate_path) as input_file: chain[i] = input_file.read().encode() store = crypto.X509Store() intermediates = [] store.load_locations(Pyopenssl.TRUST_STORE_FILE) endpoint = crypto.load_certificate(crypto.FILETYPE_PEM, chain[0]) if len(chain) > 1: for certificate_content in chain[1:]: intermediates.append( crypto.load_certificate(crypto.FILETYPE_PEM, certificate_content)) if reference_time: store.set_time(datetime.datetime.fromtimestamp(reference_time)) if crls: for crl in crls: with open(crl) as input_file: store.add_crl( crypto.load_crl(type=crypto.FILETYPE_PEM, buffer="".join( input_file.readlines()))) store.set_flags(crypto.X509StoreFlags.CRL_CHECK) result = 0 try: crypto.X509StoreContext( store=store, certificate=endpoint, chain=intermediates if len(intermediates) > 0 else None).verify_certificate() except crypto.X509StoreContextError as error: result = int(error.args[0][0]) except Exception: result = -1 return [result]
def _load_crl(self): crl_path = self._get_crl_path() try: with open(crl_path) as crl: self.crl = crypto.load_crl(crypto.FILETYPE_PEM, crl.read()) except IOError as err: self.logger.warning(str(err)) self.crl = None
def crl_files_to_objects(self, files): path = os.path.join(self.dir, "crls") obj_list = [] for file in files: with open(os.path.join(path, file), 'rb') as f: obj_list.append(crypto.load_crl(crypto.FILETYPE_ASN1, f.read())) return obj_list
def parse_crl(self, crlraw): self.logger.debug("crypto.load_crl().get_revoked()") revoked_certs = crypto.load_crl(crypto.FILETYPE_ASN1, crlraw).get_revoked() if revoked_certs != None: self.analyze_revoked_certificates(revoked_certs) else: self.logger.debug("No revoked certs!") return
def load_ca(self): rootCerts = () trustedCerts = () crlList = () certdir, crldir = "./certs/", "./CRL/" for filename in listdir(certdir): try: cert_info = open(certdir + filename, 'rb').read() except IOError: print("IO Exception while reading file : {:s} {:s}".format( certdir, filename)) exit(10) else: if ".cer" in filename: try: if any(i in filename for i in ["0012", "0013", "0015"]): certAuth = load_certificate( FILETYPE_PEM, cert_info) elif "Root" in filename: root = load_certificate(FILETYPE_PEM, cert_info) else: certAuth = load_certificate( FILETYPE_ASN1, cert_info) except: print( "Exception while loading certificate from file : {:s} {:s}" .format(certdir, filename)) exit(10) else: trustedCerts = trustedCerts + (certAuth, ) elif ".crt" in filename: try: if "ca_ecc" in filename or "-self" in filename: root = load_certificate(FILETYPE_PEM, cert_info) else: root = load_certificate(FILETYPE_ASN1, cert_info) except: print( "Exception while loading certificate from file : {:s} {:s}" .format(certdir, filename)) exit(10) else: rootCerts = rootCerts + (root, ) print("Loaded Root certificates") print("Loaded Authentication certificates") for filename in listdir(crldir): try: crl_info = open(crldir + "/" + filename, 'rb').read() except IOError: print("IO Exception while reading file : {:s} {:s}".format( certdir, filename)) else: if ".crl" in filename: crls = load_crl(FILETYPE_ASN1, crl_info) crlList = crlList + (crls, ) return rootCerts, trustedCerts, crlList
def test_02_sign_cert(self): cacon = LocalCAConnector("localCA", {"cacert": "...", "cakey": "..."}) # set the parameters: cwd = os.getcwd() cacon.set_config({"cakey": CAKEY, "cacert": CACERT, "openssl.cnf": OPENSSLCNF, "WorkingDir": cwd + "/" + WORKINGDIR}) cert = cacon.sign_request(REQUEST, {"CSRDir": "", "CertificateDir": "", "WorkingDir": cwd + "/" + WORKINGDIR}) serial = cert.get_serial_number() self.assertEqual("{0!r}".format(cert.get_issuer()), "<X509Name object " "'/C=DE/ST=Hessen/O=privacyidea/CN=CA001'>") self.assertEqual("{0!r}".format(cert.get_subject()), "<X509Name object " "'/C=DE/ST=Hessen/O=privacyidea/CN=requester" ".localdomain'>") # Revoke certificate r = cacon.revoke_cert(cert) serial_hex = int_to_hex(serial) self.assertEqual(r, serial_hex) # Create the CRL r = cacon.create_crl() self.assertEqual(r, "crl.pem") # Check if the serial number is contained in the CRL! filename = os.path.join(cwd, WORKINGDIR, "crl.pem") f = open(filename) buff = f.read() f.close() crl = crypto.load_crl(crypto.FILETYPE_PEM, buff) revoked_certs = crl.get_revoked() found_revoked_cert = False for revoked_cert in revoked_certs: s = to_unicode(revoked_cert.get_serial()) if s == serial_hex: found_revoked_cert = True break self.assertTrue(found_revoked_cert) # Create the CRL and check the overlap period. But no need to create # a new CRL. r = cacon.create_crl(check_validity=True) self.assertEqual(r, None) # Now we overlap at any cost! cacon.set_config({"cakey": CAKEY, "cacert": CACERT, "openssl.cnf": OPENSSLCNF, "WorkingDir": cwd + "/" + WORKINGDIR, ATTR.CRL_OVERLAP_PERIOD: 1000}) r = cacon.create_crl(check_validity=True) self.assertEqual(r, "crl.pem")
def test_crl_view(self): ca, cert = self._prepare_revoked() response = self.client.get(reverse('x509:crl', args=[ca.pk])) self.assertEqual(response.status_code, 200) crl = crypto.load_crl(crypto.FILETYPE_PEM, response.content) revoked_list = crl.get_revoked() self.assertIsNotNone(revoked_list) self.assertEqual(len(revoked_list), 1) self.assertEqual(int(revoked_list[0].get_serial()), cert.serial_number)
def _load_crl(self, crl_location): with open(crl_location, "rb") as crl_file: try: return crypto.load_crl(crypto.FILETYPE_ASN1, crl_file.read()) except crypto.Error: self._log( "Could not load CRL at location {}".format(crl_location), level=logging.WARNING, )
def _load_crl_from_file(self, filepath): try: crl_file = open(filepath, 'r') crl = crypto.load_crl(crypto.FILETYPE_PEM, crl_file.read()) crl_file.close() except IOError: # Create new CRL file if it doesn't exist crl = crypto.CRL() return crl
def test_voms_revoked_cert(self, m_ctx): d = fakes.user_data["dteam"] m_ctx.return_value.__enter__.return_value.retrieve.return_value = d self.m_crl.return_value = crypto.load_crl(crypto.FILETYPE_PEM, fakes.ca_crl) self.assertRaises(exception.CertificateRevoked, voms.VOMS, fakes.user_proxies["dteam"], fakes.user_cert)
def _load_crl(self): crl_path = self._get_crl_path() try: with open(crl_path) as crl: self.crl = crypto.load_crl( crypto.FILETYPE_PEM, crl.read() ) except IOError as err: self.logger.warning(str(err)) self.crl = None
def check_crl(cert, location): f = file(location, "r").read() revoked_serials = (crypto.load_crl(crypto.FILETYPE_PEM, f)).get_revoked() for serial in revoked_serials: if serial.get_serial() == cert.get_serial_number(): print "[!] Certificate found on revocation list:" print "[+] Serial:\t\t", serial.get_serial() print "[+] Reason:\t\t", serial.get_reason() rev_date = datetime.datetime.strptime(serial.get_rev_date(), "%Y%m%d%H%M%SZ") print "[+] Date Revoked:\t", rev_date.strftime("%B %d, %Y") return True return False
def get_crl(): cur = conn.cursor() cur.execute('SELECT crl from crl where ROWID = 1') resp = cur.fetchone() if resp is None: return('No crl present, you must first generate one!\n') else: crl = crypto.load_crl(crypto.FILETYPE_PEM, resp[0]) response.content_type = 'application/pkix-crl' if request.params.get('format') == 'pem': response.content_type = 'text/plain' return crl.export(caCert, caKey) return crl.export(caCert, caKey, crypto.FILETYPE_ASN1)
def setUp(self): super(TestVOMS, self).setUp() crl_patcher = mock.patch("keystone_voms.voms.VOMS._load_crl") self.m_crl = crl_patcher.start() self.m_crl.return_value = crypto.load_crl(crypto.FILETYPE_PEM, fakes.ca_empty_crl) self.addCleanup(crl_patcher.stop) ca_patcher = mock.patch("keystone_voms.voms.VOMS._load_ca") self.m_ca = ca_patcher.start() self.m_ca.return_value = crypto.load_certificate(crypto.FILETYPE_PEM, fakes.ca) self.addCleanup(ca_patcher.stop)
def test_file(self): path = os.path.join(ca_settings.CA_DIR, 'crl-test.crl') stdout, stderr = self.cmd('dump_crl', path, stdout=BytesIO(), stderr=BytesIO()) self.assertEqual(stdout, b'') self.assertEqual(stderr, b'') with open(path, 'rb') as stream: crl = crypto.load_crl(crypto.FILETYPE_PEM, stream.read()) self.assertIsNone(crl.get_revoked()) # test an output path that doesn't exist path = os.path.join(ca_settings.CA_DIR, 'test', 'crl-test.crl') with self.assertRaises(CommandError): self.cmd('dump_crl', path, stdout=BytesIO(), stderr=BytesIO())
def verify_chain(self, trusted_certs = None, crl_path=None): #<UT> #Certificate revocation check if crl_path: crl_file = os.path.join(crl_path, self.get_issuer()) if os.path.isfile(crl_file): with open(crl_file, 'r') as f: crl_obj = crypto.load_crl(crypto.FILETYPE_PEM, f.read()) revoked_certs = crl_obj.get_revoked() for rc in revoked_certs: serial = int(rc.get_serial(), 16) # conversion from hex to dec if serial == self.get_serial_number(): raise GidRevoked("Certificate with serial number 0x%s for %s has been revoked by %s." % (rc.get_serial(), self.get_subject(), self.get_issuer())) # do the normal certificate verification stuff trusted_root = Certificate.verify_chain(self, trusted_certs) if self.parent: # make sure the parent's hrn is a prefix of the child's hrn if not hrn_authfor_hrn(self.parent.get_hrn(), self.get_hrn()): raise GidParentHrn("This cert HRN %s isn't in the namespace for parent HRN %s" % (self.get_hrn(), self.parent.get_hrn())) # Parent must also be an authority (of some type) to sign a GID # There are multiple types of authority - accept them all here if not self.parent.get_type().find('authority') == 0: raise GidInvalidParentHrn("This cert %s's parent %s is not an authority (is a %s)" % (self.get_hrn(), self.parent.get_hrn(), self.parent.get_type())) # Then recurse up the chain - ensure the parent is a trusted # root or is in the namespace of a trusted root self.parent.verify_chain(trusted_certs) else: # make sure that the trusted root's hrn is a prefix of the child's trusted_gid = GID(string=trusted_root.save_to_string()) trusted_type = trusted_gid.get_type() trusted_hrn = trusted_gid.get_hrn() #if trusted_type == 'authority': # trusted_hrn = trusted_hrn[:trusted_hrn.rindex('.')] cur_hrn = self.get_hrn() if not hrn_authfor_hrn(trusted_hrn, cur_hrn): raise GidParentHrn("Trusted root with HRN %s isn't a namespace authority for this cert: %s" % (trusted_hrn, cur_hrn)) # There are multiple types of authority - accept them all here if not trusted_type.find('authority') == 0: raise GidInvalidParentHrn("This cert %s's trusted root signer %s is not an authority (is a %s)" % (self.get_hrn(), trusted_hrn, trusted_type)) return
def __init__(self, url, values): context = SSL.Context(modes[values["mode"]]) context.set_options(SSL.OP_NO_SSLv2) # =====[ Set list of ciphers to use ]===== if "ciphers" in values: context.set_cipher_list(values["ciphers"]) # =====[ Rehydrate public key certificate if given ]===== if "pub_str" in values: pub_file = open(values["pub_str"], "rb") pub_str = pub_file.read() pub_file.close() self.pub_cert = crypto.load_certificate(crypto.FILETYPE_PEM, pub_str) # =====[ If no pub key certificate, look for other options ]===== else: context.set_verify(SSL.VERIFY_PEER | SSL.VERIFY_FAIL_IF_NO_PEER_CERT, self.verify_callback) self.pub_cert = None # =====[ set certificat paths specified by user or default certificate paths if non specified ]===== if "cacert" in values: context.load_verify_locations(values["cacert"]) else: context.set_default_verify_paths() # =====[ Set grace period for expired certificates ]===== if "num_days" in values: self.num_days = values["num_days"] else: self.num_days = None # =====[ Load and set CRL ]===== if "crl_str" in values: crl_file = open(values["crl_str"], "rb") crl_str = crl_file.read() crl_file.close() self.crl = crypto.load_crl(crypto.FILETYPE_PEM, crl_str) else: self.crl = None # =====[ Save context and socket ]===== self.context = context self.sock = socket.socket()
def check_revoked_cert(ssl_socket, crl_file): """ Determine if the server certificate has been revoked or not. :param ssl_socket: Secure SSL socket :type ssl_socket: socket :param crl_file: Certificate Revocation List file :type crl_file: str """ f = open(crl_file, 'r') crl = crypto.load_crl(OpenSSL.SSL.FILETYPE_PEM, f.read()) revs = crl.get_revoked() servcert = ssl_socket.get_peer_certificate() servserial = servcert.get_serial_number() for rev in revs: if servserial == long(rev.get_serial(), 16): raise RiakError( "Server certificate has been revoked")
def check_revocation(self): if self.x509 == None: return ext_nb = self.x509.get_extension_count() for ext_in in range(0, ext_nb): ext = self.x509.get_extension(ext_in) if ext.get_short_name() == 'crlDistributionPoints': url = re.match('.*(http.*crl)', ext.get_data()).group(1) if url == None: return crl_file = urllib.urlretrieve(url)[0] crl = crypto.load_crl(crypto.FILETYPE_ASN1, open(crl_file).read()) serial = hex(self.x509.get_serial_number())[2:][:-1].upper() for revoked in crl.get_revoked(): if serial == revoked.get_serial(): self.revoked = True logger.error('Certificate %s with serial %s has been revoked!' \ %(self.cn, serial)) return
def crl_verify(cert_path): """ Attempts to verify a certificate using CRL. :param cert_path: :return: True if certificate is valid, False otherwise :raise Exception: If certificate does not have CRL """ with open(cert_path, 'rt') as c: cert = x509.load_pem_x509_certificate(c.read(), default_backend()) distribution_points = cert.extensions.get_extension_for_oid(x509.OID_CRL_DISTRIBUTION_POINTS).value for p in distribution_points: point = p.full_name[0].value response = requests.get(point) crl = crypto.load_crl(crypto.FILETYPE_ASN1, response.content) # TODO this should be switched to cryptography when support exists revoked = crl.get_revoked() for r in revoked: if cert.serial == r.get_serial(): return return True
def revoke_certificates(certificates): try: with open(settings.CERT_CA_FILE) as ca_file: ca = crypto.load_certificate(crypto.FILETYPE_PEM, ca_file.read()) with open(settings.CERT_CA_KEY_FILE) as ca_key_file: ca_key = crypto.load_privatekey(crypto.FILETYPE_PEM, ca_key_file.read()) except IOError as e: log.error(e) raise with open(settings.CERT_REVOKE_FILE, 'r') as f: crl = crypto.load_crl(crypto.FILETYPE_PEM, f.read()) for cert in certificates: x509 = crypto.load_certificate(crypto.FILETYPE_PEM, cert) revoked = crypto.Revoked() revoked.set_rev_date(asn1_general_time_format(datetime.now())) revoked.set_serial(hex(x509.get_serial_number())[2:]) crl.add_revoked(revoked) crl_text = crl.export(ca, ca_key) with open(settings.CERT_REVOKE_FILE, 'w') as f: f.write(crl_text)
def _return_revoked_serials(self, crlfile): try: serials = [] crltext = open(crlfile, 'r').read() crl = crypto.load_crl(crypto.FILETYPE_PEM, crltext) revs = crl.get_revoked() for revoked in revs: serials.append(str(revoked.get_serial())) return serials except (ImportError, AttributeError), e: call = '/usr/bin/openssl crl -text -noout -in %s' % crlfile call = shlex.split(call) serials = [] (res,err) = subprocess.Popen(call, stdout=subprocess.PIPE).communicate() for line in res.split('\n'): if line.find('Serial Number:') == -1: continue (crap, serial) = line.split(':') serial = serial.strip() serial = int(serial, 16) serials.append(serial) return serials
def _get_crl_next_update(filename): """ Read the CRL file and return the next update as datetime :param filename: :return: """ dt = None f = open(filename) crl_buff = f.read() f.close() crl_obj = crypto.load_crl(crypto.FILETYPE_PEM, crl_buff) # Get "Next Update" of CRL # Unfortunately pyOpenSSL does not support this. so we dump the # CRL and parse the text :-/ # We do not want to add dependency to pyasn1 crl_text = crypto.dump_crl(crypto.FILETYPE_TEXT, crl_obj) for line in crl_text.split("\n"): if "Next Update: " in line: key, value = line.split(":", 1) date = value.strip() dt = datetime.datetime.strptime(date, "%b %d %X %Y %Z") break return dt
def parse_crl(): rev_list = [] with open(arguments["--crl"]) as f: pem = f.read() crl = load_crl(FILETYPE_PEM, pem) revoked = crl.get_revoked() for r in revoked: rev_list.append(r.get_serial().decode("utf-8")) with open(arguments["--index"], "r") as index: certifs = index.readlines() for cert in certifs: cert = cert.split("\t") if cert[3] in rev_list and not arguments["--missing"]: print(u"Revoked certificate found !") if cert[0] != "R": print(u"Not revoked in index.txt file") print(u"CN : {0}".format(print_cn(cert))) print(u"Revoked {0}\n".format(decode_date(cert[2]))) elif cert[0] == "R" and arguments["--missing"]: if cert[3] not in rev_list: print(u"Missing revoked certificate found !") print(u"CN : {0}".format(print_cn(cert))) print(u"Revoked {0}\n".format(decode_date(cert[2])))
def setUp(self): super(VomsTokenService, self).setUp() self.config([dirs.tests_conf('keystone_voms.conf')]) self.tenant_name = default_fixtures.TENANTS[0]['name'] self.tenant_id = default_fixtures.TENANTS[0]['id'] CONF.voms.voms_policy = dirs.tests_conf("voms.json") self.aux_tenant_name = default_fixtures.TENANTS[1]['name'] context_patcher = mock.patch("keystone_voms.voms.VOMSContext", PatchedVomsContext) self.m_context = context_patcher.start() self.addCleanup(context_patcher.stop) crl_patcher = mock.patch("keystone_voms.voms.VOMS._load_crl") self.m_crl = crl_patcher.start() self.m_crl.return_value = crypto.load_crl(crypto.FILETYPE_PEM, fakes.ca_empty_crl) self.addCleanup(crl_patcher.stop) ca_patcher = mock.patch("keystone_voms.voms.VOMS._load_ca") self.m_ca = ca_patcher.start() self.m_ca.return_value = crypto.load_certificate(crypto.FILETYPE_PEM, fakes.ca) self.addCleanup(ca_patcher.stop)
def certidude_request_certificate(server, key_path, request_path, certificate_path, authority_path, revocations_path, common_name, extended_key_usage_flags=None, org_unit=None, email_address=None, given_name=None, surname=None, autosign=False, wait=False, ip_address=None, dns=None, bundle=False, insecure=False): """ Exchange CSR for certificate using Certidude HTTP API server """ # Set up URL-s request_params = set() if autosign: request_params.add("autosign=true") if wait: request_params.add("wait=forever") # Expand ca.example.com scheme = "http" if insecure else "https" # TODO: Expose in CLI authority_url = "%s://%s/api/certificate/" % (scheme, server) request_url = "%s://%s/api/request/" % (scheme, server) revoked_url = "%s://%s/api/revoked/" % (scheme, server) if request_params: request_url = request_url + "?" + "&".join(request_params) if os.path.exists(authority_path): click.echo("Found authority certificate in: %s" % authority_path) else: click.echo("Attempting to fetch authority certificate from %s" % authority_url) try: r = requests.get(authority_url, headers={"Accept": "application/x-x509-ca-cert,application/x-pem-file"}) cert = crypto.load_certificate(crypto.FILETYPE_PEM, r.text) except crypto.Error: raise ValueError("Failed to parse PEM: %s" % r.text) authority_partial = tempfile.mktemp(prefix=authority_path + ".part") with open(authority_partial, "w") as oh: oh.write(r.text) click.echo("Writing authority certificate to: %s" % authority_path) os.rename(authority_partial, authority_path) # Fetch certificate revocation list r = requests.get(revoked_url, headers={'accept': 'application/x-pem-file'}, stream=True) click.echo("Fetching CRL from %s to %s" % (revoked_url, revocations_path)) revocations_partial = tempfile.mktemp(prefix=revocations_path + ".part") with open(revocations_partial, 'wb') as f: for chunk in r.iter_content(chunk_size=8192): if chunk: f.write(chunk) if subprocess.call(("openssl", "crl", "-CAfile", authority_path, "-in", revocations_partial, "-noout")): raise ValueError("Failed to verify CRL in %s" % revocations_partial) else: # TODO: Check monotonically increasing CRL number click.echo("Certificate revocation list passed verification") os.rename(revocations_partial, revocations_path) # Check if we have been inserted into CRL if os.path.exists(certificate_path): cert = crypto.load_certificate(crypto.FILETYPE_PEM, open(certificate_path).read()) revocation_list = crypto.load_crl(crypto.FILETYPE_PEM, open(revocations_path).read()) for revocation in revocation_list.get_revoked(): if int(revocation.get_serial(), 16) == cert.get_serial_number(): if revocation.get_reason() == "Certificate Hold": # TODO: 'Remove From CRL' # TODO: Disable service for time being click.echo("Certificate put on hold, doing nothing for now") break # Disable the client if operation has been ceased or # the certificate has been superseded by other if revocation.get_reason() in ("Cessation Of Operation", "Superseded"): if os.path.exists("/etc/certidude/client.conf"): clients.readfp(open("/etc/certidude/client.conf")) if clients.has_section(server): clients.set(server, "trigger", "operation ceased") clients.write(open("/etc/certidude/client.conf", "w")) click.echo("Authority operation ceased, disabling in /etc/certidude/client.conf") # TODO: Disable related services if revocation.get_reason() in ("CA Compromise", "AA Compromise"): if os.path.exists(authority_path): os.remove(key_path) click.echo("Certificate has been revoked, wiping keys and certificates!") if os.path.exists(key_path): os.remove(key_path) if os.path.exists(request_path): os.remove(request_path) if os.path.exists(certificate_path): os.remove(certificate_path) break else: click.echo("Certificate does not seem to be revoked. Good!") try: request = Request(open(request_path)) click.echo("Found signing request: %s" % request_path) except EnvironmentError: # Construct private key click.echo("Generating 4096-bit RSA key...") key = rsa.generate_private_key( public_exponent=65537, key_size=4096, backend=default_backend() ) # Dump private key key_partial = tempfile.mktemp(prefix=key_path + ".part") os.umask(0o077) with open(key_partial, "wb") as fh: fh.write(key.private_bytes( encoding=serialization.Encoding.PEM, format=serialization.PrivateFormat.TraditionalOpenSSL, encryption_algorithm=serialization.NoEncryption(), )) # Set subject name attributes names = [x509.NameAttribute(NameOID.COMMON_NAME, common_name.decode("utf-8"))] if given_name: names.append(x509.NameAttribute(NameOID.GIVEN_NAME, given_name.decode("utf-8"))) if surname: names.append(x509.NameAttribute(NameOID.SURNAME, surname.decode("utf-8"))) if org_unit: names.append(x509.NameAttribute(NameOID.ORGANIZATIONAL_UNIT, org_unit.decode("utf-8"))) # Collect subject alternative names subject_alt_names = set() if email_address: subject_alt_names.add(x509.RFC822Name(email_address)) if ip_address: subject_alt_names.add("IP:%s" % ip_address) if dns: subject_alt_names.add(x509.DNSName(dns)) # Construct CSR csr = x509.CertificateSigningRequestBuilder( ).subject_name(x509.Name(names)) if extended_key_usage_flags: click.echo("Adding extended key usage extension: %s" % extended_key_usage_flags) csr = csr.add_extension(x509.ExtendedKeyUsage( extended_key_usage_flags), critical=True) if subject_alt_names: click.echo("Adding subject alternative name extension: %s" % subject_alt_names) csr = csr.add_extension( x509.SubjectAlternativeName(subject_alt_names), critical=False) # Sign & dump CSR os.umask(0o022) with open(request_path + ".part", "wb") as f: f.write(csr.sign(key, hashes.SHA256(), default_backend()).public_bytes(serialization.Encoding.PEM)) click.echo("Writing private key to: %s" % key_path) os.rename(key_partial, key_path) click.echo("Writing certificate signing request to: %s" % request_path) os.rename(request_path + ".part", request_path) # We have CSR now, save the paths to client.conf so we could: # Update CRL, renew certificate, maybe something extra? if os.path.exists(certificate_path): click.echo("Found certificate: %s" % certificate_path) # TODO: Check certificate validity, download CRL? return # If machine is joined to domain attempt to present machine credentials for authentication if os.path.exists("/etc/krb5.keytab") and os.path.exists("/etc/samba/smb.conf"): # Get HTTP service ticket from configparser import ConfigParser cp = ConfigParser(delimiters=("=")) cp.readfp(open("/etc/samba/smb.conf")) name = cp.get("global", "netbios name") realm = cp.get("global", "realm") os.environ["KRB5CCNAME"]="/tmp/ca.ticket" os.system("kinit -k %s$ -S HTTP/%s@%s -t /etc/krb5.keytab" % (name, server, realm)) from requests_kerberos import HTTPKerberosAuth, OPTIONAL auth = HTTPKerberosAuth(mutual_authentication=OPTIONAL, force_preemptive=True) else: auth = None click.echo("Submitting to %s, waiting for response..." % request_url) submission = requests.post(request_url, auth=auth, data=open(request_path), headers={"Content-Type": "application/pkcs10", "Accept": "application/x-x509-user-cert,application/x-pem-file"}) # Destroy service ticket if os.path.exists("/tmp/ca.ticket"): os.system("kdestroy") if submission.status_code == requests.codes.ok: pass if submission.status_code == requests.codes.accepted: # Server stored the request for processing (202 Accepted), but waiting was not requested, hence quitting for now return if submission.status_code == requests.codes.conflict: raise errors.DuplicateCommonNameError("Different signing request with same CN is already present on server, server refuses to overwrite") elif submission.status_code == requests.codes.gone: # Should the client retry or disable request submission? raise ValueError("Server refused to sign the request") # TODO: Raise proper exception else: submission.raise_for_status() try: cert = crypto.load_certificate(crypto.FILETYPE_PEM, submission.text) except crypto.Error: raise ValueError("Failed to parse PEM: %s" % submission.text) os.umask(0o022) with open(certificate_path + ".part", "w") as fh: # Dump certificate fh.write(submission.text) # Bundle CA certificate, necessary for nginx if bundle: with open(authority_path) as ch: fh.write(ch.read()) click.echo("Writing certificate to: %s" % certificate_path) os.rename(certificate_path + ".part", certificate_path)
def verify_not_revoked(link): results =OrderedDict() errors = [] warnings=[] crl_list = [] revoked = False if link.has_key('crlDistributionPointsURIs'): url_list = link['crlDistributionPointsURIs'] for u in url_list: request_error = False crl_detail = OrderedDict() crl = None try: r = requests.get(u) except requests.exceptions.ConnectionError: msg = "ConnectionError: Could not fetch CRL %s" % (u ) warnings.append(msg) request_error = True except requests.exceptions.Timeout: msg = "Timeout: Could not fetch CRL %s" % (u ) warnings.append(msg) request_error = True except requests.exceptions.URLRequired: msg = "URLRequired: Could not fetch CRL %s" % (u ) warnings.append(msg) request_error = True except requests.exceptions.RequestException: msg = "RequestException: Could not fetch CRL %s" % (u ) warnings.append(msg) request_error = True except requests.exceptions.HTTPError: msg = "HTTPError: Could not fetch CRL %s" % (u ) warnings.append(msg) request_error = True except requests.exceptions.TooManyRedirects: msg = "TooManyRedirects: Could not fetch CRL %s" % (u ) warnings.append(msg) request_error = True if request_error: r = dummy_http_response() if r.status_code != 200: msg = "Could not fetch CRL %s" % (u) warnings.append(msg) else: #we got a response # try and parse it as pem try: crl = crypto.load_crl(crypto.FILETYPE_PEM, r.text) except UnicodeEncodeError: #Might be a der try: crl = crypto.load_crl(crypto.FILETYPE_ASN1, r.content) except crypto.Error: crl_detail["no_crl"] = True msg = "Error parsing CRL URI %s" % (u) errors.append(msg) except crypto.Error: crl_detail["no_crl"] = True msg = "Error parsing CRL URI %s" % (u) errors.append(msg) if crl: crl_detail['no_crl'] = False #print "Parse the CRL", crl, u, "for serial ", link['serial_number'] crl_detail['serial_number'] = link['serial_number'] #print "CRL Object loaded!!!!", crl.get_revoked() if crl.get_revoked(): for r in crl.get_revoked(): s =r.get_serial().upper() if s == link["serial_number"]: revoked = True if revoked == True: crl_detail['revoked'] = True else: crl_detail['revoked'] = False crl_list.append(crl_detail) else: msg = "No CRLs found for %s" % (link['CN']) warnings.append(msg) #print "Get CRL Chain" #print "Compare" if warnings: results['warnings']=warnings if errors: results['errors']=errors no_crl = True for c in crl_list: if c['no_crl']==False: no_crl = False if no_crl==False: results['no_crl'] = False results['crl']=crl_list results['CN'] = link['CN'] else: results['no_crl'] = True results['crl']= [{"no_crl": True, "CN": link['CN'], },] return results
def VerifySignature(self): from . import IX_ROOT_CA_FILE, VERIFIER_HELPER, IX_CRL from . import SIGNATURE_FAILURE if self.Signature() is None: return not SIGNATURE_FAILURE # Probably need a way to ignore the signature else: import subprocess import tempfile from base64 import b64decode import OpenSSL.crypto as Crypto try: cert_file = VerificationCertificateFile(self) except ValueError: cert_file = None if not os.path.isfile(IX_ROOT_CA_FILE) \ or cert_file is None \ or not os.path.isfile(cert_file): log.debug("VerifySignature: Cannot find a required file") return False # First we create a store store = Crypto.X509Store() store.set_flags(Crypto.X509StoreFlags.CRL_CHECK) # Load our root CA try: with open(IX_ROOT_CA_FILE, "r") as f: root_ca = Crypto.load_certificate(Crypto.FILETYPE_PEM, f.read()) store.add_cert(root_ca) except: log.debug("VerifySignature: Could not load iX root CA", exc_info=True) return False # Now need to get the CRL crl_file = tempfile.NamedTemporaryFile(suffix=".pem") if crl_file is None: log.debug("Could not create CRL, ignoring for now") else: try: if not self._config.TryGetNetworkFile( url=IX_CRL, pathname=crl_file.name, reason="FetchCRL" ): # TGNF will raise an exception in most cases. raise Exception("Could not get CRL file") except: log.error("Could not get CRL file %s" % IX_CRL) crl_file.close() crl_file = None if crl_file: try: crl = Crypto.load_crl(Crypto.FILETYPE_PEM, crl_file.read()) store.add_crl(crl) except: log.debug("Could not load CRL, ignoring for now", exc_info=True) # Now load the certificate files try: with open(cert_file, "r") as f: regexp = r'-----BEGIN CERTIFICATE-----.*?-----END CERTIFICATE-----' certs = re.findall(regexp, f.read(), re.DOTALL) except: log.error("Could not load certificates", exc_info=True) return false # Almost done: we need the signature as binary data try: signature = b64decode(self.Signature()) except: log.error("Could not decode signature", exc_info=True) return False verified = False tdata = self.dict().copy() tdata.pop(SIGNATURE_KEY, None) canonical = MakeString(tdata) for cert in certs: try: test_cert = Crypto.load_certificate(Crypto.FILETYPE_PEM, cert) Crypto.verify(test_cert, signature, canonical, "sha256") verified = True break except: # For now, just ignore pass return verified return False
def check_revocation_status(certificate): """ Checks bank certificate revocation status. @type certificate: (byte)String @param certificate: Certificate @rtype: boolean @return: Have asked certificate been revocated. """ # Check if crl file exists renew = False if os.path.isfile('resources/OP-Pohjola-ws.crl'): modified = os.path.getmtime('resources/OP-Pohjola-ws.crl') modify_time = datetime.datetime.fromtimestamp(modified) difference = datetime.datetime.today() - modify_time if difference.days > 0: renew = True else: renew = True if renew: url = "http://wsk.op.fi/crl/ws/OP-Pohjola-ws.crl" try: with open('resources/OP-Pohjola-ws.crl', 'wb') as f: r = request.urlopen(url).read() f.write(r) except urllib.error.URLError as e: log.error(e) print("Unable to update/download new certificate revocation list.") if not os.path.exists('resources/OP-Pohjola-ws.crl'): # Unable to test against anything return False except EnvironmentError as e: if not os.path.exists("resources"): try: os.mkdir("resources") except OSError as e: log.error(e) log.error("Unable to create directory for revocation" " list.") log.error("This means that certificate bank is using" "won't be checked.") return False else: try: with open('resources/OP-Pohjola-ws.crl', 'wb') as f: r = request.urlopen(url).read() f.write(r) except EnvironmentError as e: log.error(e) log.error("Unable to crl to disk.") log.error("This means that certificate that bank is" " using won't be checked.") return False with open('resources/OP-Pohjola-ws.crl', 'rb') as f: crl = f.read() op_crl = crypto.load_crl(crypto.FILETYPE_ASN1, crl) revoked = op_crl.get_revoked() try: certificate = crypto.load_certificate(crypto.FILETYPE_ASN1, certificate) except crypto.Error: raise ValueError("Unable to load certificate") sn = certificate.get_serial_number() for cert in revoked: if cert.get_serial() == sn: return True return False