def get_san_from_cert(CERT_FILE): cert = _load_certificate(CERT_FILE) e = cert.get_extension(2) for i in range(cert.get_extension_count()): logging.debug(cert.get_extension(i).get_short_name()) if cert.get_extension(i).get_short_name().decode() == "subjectAltName": e = cert.get_extension(i) break raw_alt_names = e.get_data() decoded_alt_names, _ = asn1_decoder(raw_alt_names, asn1Spec=SubjectAltName()) py_alt_names = nat_encoder(decoded_alt_names) logging.debug(py_alt_names) ip_sub_alt_name = [] dns_sub_alt_name = [] for element in py_alt_names: if element.keys() == OrderedDict([('iPAddress', '_')]).keys(): ip_sub_alt_name.append( str(ipaddress.IPv4Address(element['iPAddress']))) elif element.keys() == OrderedDict([('dNSName', '_')]).keys(): dns_sub_alt_name.append(element['dNSName'].decode("utf-8")) else: logging.error("Bad AltName Key") logging.debug(ip_sub_alt_name) logging.debug(dns_sub_alt_name) san = {"dns": dns_sub_alt_name, "ip": ip_sub_alt_name} logging.debug(san) return san
def extract_names(raw_cert): results = { 'CN': set(), 'DNS': set(), 'SRV': set(), 'URI': set(), 'XMPPAddr': set() } cert = decoder.decode(raw_cert, asn1Spec=Certificate())[0] tbs = cert.getComponentByName('tbsCertificate') subject = tbs.getComponentByName('subject') extensions = tbs.getComponentByName('extensions') or [] # Extract the CommonName(s) from the cert. for rdnss in subject: for rdns in rdnss: for name in rdns: oid = name.getComponentByName('type') value = name.getComponentByName('value') if oid != COMMON_NAME: continue value = decoder.decode(value, asn1Spec=DirectoryString())[0] value = decode_str(value.getComponent()) results['CN'].add(value) # Extract the Subject Alternate Names (DNS, SRV, URI, XMPPAddr) for extension in extensions: oid = extension.getComponentByName('extnID') if oid != SUBJECT_ALT_NAME: continue value = decoder.decode(extension.getComponentByName('extnValue'), asn1Spec=OctetString())[0] sa_names = decoder.decode(value, asn1Spec=SubjectAltName())[0] for name in sa_names: name_type = name.getName() if name_type == 'dNSName': results['DNS'].add(decode_str(name.getComponent())) if name_type == 'uniformResourceIdentifier': value = decode_str(name.getComponent()) if value.startswith('xmpp:'): results['URI'].add(value[5:]) elif name_type == 'otherName': name = name.getComponent() oid = name.getComponentByName('type-id') value = name.getComponentByName('value') if oid == XMPP_ADDR: value = decoder.decode(value, asn1Spec=UTF8String())[0] results['XMPPAddr'].add(decode_str(value)) elif oid == SRV_NAME: value = decoder.decode(value, asn1Spec=IA5String())[0] results['SRV'].add(decode_str(value)) return results
def chain_subject_names(chain): names = { name for field, name in chain[0].get_subject().get_components() if field == "CN" } for i in range(chain[0].get_extension_count()): ext = chain[0].get_extension(i) if ext.get_short_name() == "subjectAltName": value, substrate = der_decoder.decode( ext.get_data(), asn1Spec=SubjectAltName() ) assert substrate == b"" for component in value: if component.getName() == "dNSName": names.add(str(component.getComponent())) return names
def __extract_san(self, x509): domain = set() if isinstance(x509, OpenSSL.crypto.X509): extensions = [ x509.get_extension(i) for i in range(x509.get_extension_count()) ] else: extensions = x509.get_extensions() for extension in extensions: if extension.get_short_name() == b"subjectAltName": san = extension.get_data() san = decoder.decode(san, asn1Spec=SubjectAltName()) for name in san: if isinstance(name, SubjectAltName): for entry in range(len(name)): component = name.getComponentByPosition(entry) domain.add(str(component.getComponent())) return domain
def fnmt_data_from_pem(pem): ''' given an FNMT PEM certificate, returns the relevant data from it: returns nif, full_name, email The certificate might not contain an email - in that case it will return None for the email. If there's any error processing the certificate, it will throw an exception ''' import OpenSSL from pyasn1.type.base import AbstractConstructedAsn1Item from pyasn1.type.char import IA5String from pyasn1.codec.der.decoder import decode from pyasn1_modules.rfc2459 import SubjectAltName, AttributeTypeAndValue, GeneralName cert = OpenSSL.crypto.load_certificate(OpenSSL.crypto.FILETYPE_PEM, pem) # sanity check components = cert.get_subject().get_components() assert components[0][0].lower() == 'c' assert components[0][1].lower() == 'es' assert components[1][0].lower() == 'o' assert components[1][1].lower() == 'fnmt' assert components[2][0].lower() == 'ou' assert components[2][1].lower() == 'fnmt clase 2 ca' assert components[4][0].lower() == 'cn' def visit_asn(data, item): ''' visits asn items locating and saving relevant data ''' if isinstance(item, IA5String): data['email'] = str(item).lower() elif isinstance(item, AttributeTypeAndValue): item_type = str(item[0]) if item_type == '1.3.6.1.4.1.5734.1.1': data['name'] = str(decode(item[1])[0]) elif item_type == '1.3.6.1.4.1.5734.1.2': data['surname1'] = str(decode(item[1])[0]) elif item_type == '1.3.6.1.4.1.5734.1.3': data['surname2'] = str(decode(item[1])[0]) elif item_type == '1.3.6.1.4.1.5734.1.4': data['nif'] = str(decode(item[1])[0]) elif isinstance(item, AbstractConstructedAsn1Item) or isinstance( item, tuple): for child_item in item: visit_asn(data, child_item) # find subjectAltName, which should contain user's email address for i in xrange(cert.get_extension_count()): ext = cert.get_extension(i) if ext.get_short_name() == 'subjectAltName': alt_name = decode(ext.get_data(), asn1Spec=SubjectAltName()) data = dict() visit_asn(data, alt_name) # check that everything was found assert data.has_key('nif') assert data.has_key('surname1') assert data.has_key('surname2') assert data.has_key('name') # email might not be found full_name = "%s %s %s" % (data['name'], data['surname1'], data['surname2']) full_name = " ".join( [i.capitalize() for i in full_name.split(" ")]) # we can only store 30 chars in # django.contrib.auth.models.User.first_name field anyway full_name = full_name[:30] return data['nif'], full_name, data.get('email', None) raise Exception("subjectAltName not found in the certificate")