def pkcs7_get_certs(self):
    """
    https://github.com/pyca/pyopenssl/pull/367/files#r67300900

    Returns all certificates for the PKCS7 structure, if present. Only
    objects of type ``signedData`` or ``signedAndEnvelopedData`` can embed
    certificates.

    :return: The certificates in the PKCS7, or :const:`None` if
        there are none.
    :rtype: :class:`tuple` of :class:`X509` or :const:`None`
    """
    from OpenSSL.crypto import _lib, _ffi, X509
    certs = _ffi.NULL
    if self.type_is_signed():
        certs = self._pkcs7.d.sign.cert
    elif self.type_is_signedAndEnveloped():
        certs = self._pkcs7.d.signed_and_enveloped.cert

    pycerts = []
    for i in range(_lib.sk_X509_num(certs)):
        x509 = _ffi.gc(_lib.X509_dup(_lib.sk_X509_value(certs, i)),
                       _lib.X509_free)
        pycert = X509._from_raw_x509_ptr(x509)
        pycerts.append(pycert)
    if pycerts:
        return [x.to_cryptography() for x in pycerts]
Esempio n. 2
0
def get_certificates(pkcs7):
    from OpenSSL.crypto import _lib, _ffi, X509
    """
    https://github.com/pyca/pyopenssl/pull/367/files#r67300900

    Returns all certificates for the PKCS7 structure, if present. Only
    objects of type ``signedData`` or ``signedAndEnvelopedData`` can embed
    certificates.

    :return: The certificates in the PKCS7, or :const:`None` if
        there are none.
    :rtype: :class:`tuple` of :class:`X509` or :const:`None`
    """
    certs = pkcs7._pkcs7.d.sign.b_sod_cert

    pycerts = []
    for i in range(_lib.sk_X509_num(certs)):
        pycert = X509.__new__(X509)
        # pycert._x509 = _lib.sk_X509_value(certs, i)
        # According to comment from @ Jari Turkia
        # to prevent segfaults use '_lib.X509_dup('
        pycert._x509 = _lib.X509_dup(_lib.sk_X509_value(certs, i))
        pycerts.append(pycert)

    if not pycerts:
        return None
    return tuple(pycerts)
Esempio n. 3
0
    def _parse(self, buff, digestalgo):
        pkcs7 = crypto.load_pkcs7_data(crypto.FILETYPE_ASN1, buff)

        certs_stack = _ffi.NULL
        if pkcs7.type_is_signed():
            certs_stack = pkcs7._pkcs7.d.sign.cert
        elif pkcs7.type_is_signedAndEnveloped():
            certs_stack = pkcs7._pkcs7.d.signed_and_enveloped.cert

        pycerts = []

        for i in range(_lib.sk_X509_num(certs_stack)):
            tmp = _lib.X509_dup(_lib.sk_X509_value(certs_stack, i))
            pycert = X509._from_raw_x509_ptr(tmp)
            pycerts.append(pycert)

        if not pycerts:
            return None

        for cert in pycerts:
            sbj = cert.get_subject()
            name = 'C={}, ST={}, L={}, O={}, CN={}'.format(
                sbj.C, sbj.ST, sbj.L, sbj.O, sbj.CN)
            checksum = cert.digest(digestalgo).decode().replace(':', '')
            self.content.append((name, checksum))
def get_certs(p7):
    # client-cert is a PKCS7-encoded set of certificates.
    # GnuTLS and OpenSSL order the certificates differently.
    # GnuTLS provides the certificates in 'canonical order',
    # while OpenSSL provides it in the order the programmer
    # added it to the PKCS#7 structure.
    #
    # Testing shows that Cisco servers can handle any order

    if p7.type_is_signed():
        certs = p7._pkcs7.d.sign.cert
    elif p7.type_is_signedAndEnveloped():
        certs = p7._pkcs7.d.signed_and_enveloped.cert
    else:
        return ()

    # Ensure that we have exactly one usercert, and that
    # all the rest are (possibly-intermediate) CA certs
    usercert = None
    extracerts = []
    for i in range(_lib.sk_X509_num(certs)):
        cert = _lib.X509_dup(_lib.sk_X509_value(certs, i))
        pycert = X509._from_raw_x509_ptr(cert)
        if is_ca_cert(pycert):
            extracerts.append(pycert)
        else:
            assert usercert is None
            usercert = pycert
    assert usercert

    # Build a path from the usercert to the root
    path = [usercert]

    # Verify that there are no duplicates in the set
    issuers = {}
    for c in extracerts:
        subject = c.get_subject().der()
        assert subject not in issuers
        issuers[subject] = c

    while True:
        try:
            path.append(issuers.pop(path[-1].get_issuer().der()))
        except KeyError:
            break

    # Verify that there are no remaining (unused) certificates
    assert len(issuers) == 0

    return tuple(path)
Esempio n. 5
0
def get_pem_data_from_pkcs7(data: bytes) -> bytes:
    """Extracts certificate from pkcs7 data and convert it to PEM data"""
    pkcs7 = crypto.load_pkcs7_data(crypto.FILETYPE_ASN1, data)
    certs = _ffi.NULL

    if pkcs7.type_is_signed():
        certs = pkcs7._pkcs7.d.sign.cert
    elif pkcs7.type_is_signedAndEnveloped():
        certs = pkcs7._pkcs7.d.signed_and_enveloped.cert

    if _lib.sk_X509_num(certs) > 1:
        raise Exception('Too many certificates')

    pycert = X509.__new__(X509)
    pycert._x509 = _lib.X509_dup(_lib.sk_X509_value(certs, 0))

    return bytes(crypto.dump_certificate(crypto.FILETYPE_PEM, pycert))
Esempio n. 6
0
def get_certificates(self):
    certs = _ffi.NULL
    if self.type_is_signed():
        certs = self._pkcs7.d.sign.cert
    elif self.type_is_signedAndEnveloped():
        certs = self._pkcs7.d.signed_and_enveloped.cert

    pycerts = []
    for i in range(_lib.sk_X509_num(certs)):
        pycert = X509.__new__(X509)
        # pycert._x509 = _lib.sk_X509_value(certs, i)
        # According to comment from @ Jari Turkia
        # to prevent segfaults use '_lib.X509_dup('
        pycert._x509 = _lib.X509_dup(_lib.sk_X509_value(certs, i))
        pycerts.append(pycert)

    if not pycerts:
        return None
    return tuple(pycerts)
Esempio n. 7
0
    def _parse(self, buff):
        pkcs7 = crypto.load_pkcs7_data(crypto.FILETYPE_ASN1, buff)

        certs_stack = _ffi.NULL
        if pkcs7.type_is_signed():
            certs_stack = pkcs7._pkcs7.d.sign.cert
        elif pkcs7.type_is_signedAndEnveloped():
            certs_stack = pkcs7._pkcs7.d.signed_and_enveloped.cert

        pycerts = []

        for i in range(_lib.sk_X509_num(certs_stack)):
            tmp = _lib.X509_dup(_lib.sk_X509_value(certs_stack, i))
            pycert = X509._from_raw_x509_ptr(tmp)
            pycerts.append(pycert)

        if not pycerts:
            return None

        for cert in pycerts:
            name = str(cert.get_subject())[19:-2].replace('/', ', ')
            md5 = cert.digest('md5').decode().replace(':', '')

            self.content.append((name, md5))