Re: Trying to get a public info for a certificate

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Thanks a lot, Matt and Viktor! You guys are absolutely right, X509_get0_pubkey_bitstr gives me the same struct that was once inside of cert_info->key->public_key.

@Viktor I had also tried your second approach (didn't know about the first one!) and for some reason it doesn't have the "correct" data. My guess is you're right and the application has been hashing the wrong thing all along. I will look into it.

Anyway, thanks a lot you guys, you are the best!

On Mon, Jun 3, 2019 at 11:31 AM Viktor Dukhovni <openssl-users@xxxxxxxxxxxx> wrote:
On Mon, Jun 03, 2019 at 10:40:02AM -0500, Daniel Pedraza wrote:

> There's a part of the code where we're doing a sha256 hash of the public
> key of our certificate. On the older OpenSSL, we were able to get the
> public key by doing cert->cert_info->key->public_key->data. On the newer
> version, we no longer have access to the cert_info struct.
>
> I tried doing:
>
> EVP_PKEY * public_key = X509_get0_pubkey(cert);
>
> this gives me an EVP_PKEY value, which I tried to convert to a char** by
> doing this:
>
> unsigned char *buf, *p;
> int len = i2d_PublicKey(public_key, NULL);
> buf = OPENSSL_malloc(len);
> p = buf;
> i2d_PublicKey(public_key, &p);

To obtain the serialized buffer 'buf' of length 'len' that you
can then checksum, there are two essentially equivalent approaches:

   1.   X509 *cert = ...;
        X509_PUBKEY *xpk = X509_get_X509_PUBKEY(cert);
        int len = i2d_X509_PUBKEY(xpk, NULL);
        unsigned char *buf = malloc(len);       /* error check */
        unsigned char *buf2 = buf;

        i2d_X509_PUBKEY(xpk, &buf2);
        OPENSSL_assert(buf2 - buf == len);

   2.   X509 *cert = ...;
        EVP_PKEY *pkey = X509_get0_pubkey(cert);
        int len = i2d_PUBKEY(pkey, NULL);
        unsigned char *buf = malloc(len);       /* error check */
        unsigned char *buf2 = buf;

        i2d_PUBKEY(pkey, &buf2);
        OPENSSL_assert(buf2 - buf == len);

The first approach avoids having to reconstruct (allocate, use and
free) the X509_PUBKEY (SPKI) from the underlying EVP_PKEY, so will
be slightly more efficient.

> This gives me a buffer with the correct length, but it seems like it has
> different data from what the public_key->data used to give me.

I don't recall what public_key->data contains, but if different it
was probably not the right thing to use, since you should be capturing
the complete SPKI structure (public key algorithm OID, any parameters
and the key data).  If it contains just the key bits, without the
algorithm and parameters, it is unwise to use that.

If needed for backwards-compatibility, you should be able to recover
the key bitstring with X509_get0_pubkey_bitstr(3), but you really
should not.  The SPKI is the right object to fingerprint.

--
        Viktor.

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Index of Archives]     [Linux ARM Kernel]     [Linux ARM]     [Linux Omap]     [Fedora ARM]     [IETF Annouce]     [Security]     [Bugtraq]     [Linux]     [Linux OMAP]     [Linux MIPS]     [ECOS]     [Asterisk Internet PBX]     [Linux API]

  Powered by Linux