Re: X509_get_pubkey() in OpenSSL 3.0?

2021-11-04 Thread Matt Caswell

Going back to the original email in this thread:

On 02/11/2021 19:42, Jason Schultz wrote:

     mycert = PEM_read_X509(fp, NULL, 0, NULL);
     pkey = X509_get_pubkey(mycert);

All functions return good statuses or non-NULL pointers until the last 
one, X509_get_pubkey() returns NULL.



The PEM_read_X509 call looks suspicious. As I understand it you have a 
fips libctx and non-fips libctx, with no providers loaded into the 
default libctx. Correct?


The public key is actually decoded as part of the PEM_read_X509(). But, 
the PEM_read_X509() call does not take a libctx parameter. Subsequently, 
it attempts to decode the embedded X509 public key and will use the 
default libctx - which has no providers and so the decode of the key 
fails. Therefore when you subsequently try to obtain the public key with 
X509_get_pubkey() you get a NULL return.


Please raise this as an issue in github.

Matt


Re: X509_get_pubkey() in OpenSSL 3.0?

2021-11-04 Thread Tomas Mraz
On Wed, 2021-11-03 at 20:32 +, Jason Schultz wrote:
> 00B741558E7F:error:0308010C:digital envelope routines:(unknown
> function):unsupported:crypto/evp/evp_fetch.c:346:Global default
> library
> context, Algorithm (SHA1 : 96), Properties ()

The "Global default library context" hints at what is the issue -
somewhere in the chain verification or chain building routines the non-
default context is not passed appropriately in and this causes the
failures.

Could you please open this as an issue in GitHub?

-- 
Tomáš Mráz
No matter how far down the wrong road you've gone, turn back.
  Turkish proverb
[You'll know whether the road is wrong if you carefully listen to your
conscience.]




Re: X509_get_pubkey() in OpenSSL 3.0?

2021-11-03 Thread Jason Schultz
Unfortunately, the short answer is I can't avoid the problem. The application 
is complicated, and can be thought of as many applications, all of which have 
different needs. I don't think combining a certificate chain into one file 
eliminates the need for all of the calls I'm making, just some of them. I wish 
it were that easy, but I need to do this set up at run time.

I'll see what I can find, and try a few other things to attempt to isolate the 
cause. If I run out of ideas, I'll probably start a new thread since it may get 
more attention.

Thanks for your answers once again.

Jason



From: openssl-users  on behalf of Viktor 
Dukhovni 
Sent: Wednesday, November 3, 2021 9:25 PM
To: openssl-users@openssl.org 
Subject: Re: X509_get_pubkey() in OpenSSL 3.0?

On Wed, Nov 03, 2021 at 08:32:43PM +, Jason Schultz wrote:

> To summarize, at application start time I read in all of the
> certificates in /etc/ssl/certs/ to a trusted store created with
> X509_STORE_new().
>
> When getting ready to "start" a server (again, leaving a lot of
> specifics out to avoid getting bogged down in details), I'm doing the
> processing in the previous messages on this thread. Here are the API
> calls again, with the changes previously discussed:
>
> ctx = SSL_CTX_new_ex(non_fips_libctx, NULL, TLS_method());
> SSL_CTX_use_PrivateKey_file(ctx,,SSL_FILETYPE_PEM);
> SSL_CTX_use_certificate_file(ctx,,SSL_FILETYPE_PEM);
> SSL_CTX_check_private_key(ctx);
> mycert = SSL_CTX_get0_certificate(ctx);
> pkey = X509_get_pubkey(mycert);
>
>  After that's done, I make several OpenSSL calls to get things set up the way 
> I want:
>
> param = X509_VERIFY_PARAM_new();
> X509_VERIFY_PARAM_set_flags(param, X509_V_FLAG_PARTIAL_CHAIN);
> X509_STORE_set1_param(ssl_trusted_certs, param);
> X509_VERIFY_PARAM_free(param);
>
> I call these to treat intermediate certs as trust-anchors, so I can
> trust an intermediate certificate; ssl_trusted_certs is the
> aforementioned X509_STORE.

I am puzzled as to you working so hard (writing a bunch of low-level
trust-store and chain construction code) to construct at runtime, what
could be created statically at chain file construction time.  Especially
if you stick with best practice and keep certificate lifetimes
reasonably short (~90 days or less, not years).  The certificate chain
file constructed at the time the certificate is issued should work
unchanged for the lifetime of the certificate, and the server
applications can avoid having to execute any chain construction or
verification code.

Yes, you're asking somewhat "interesting" questions, in that, e.g., I am
not up to speed on all the changes in 3.0.0, and perhaps there are
indeed some issues around legacy SHA1 signatures, but I do suspect that
a more productive use of your time is likely to reconsider the decision
to work at such a low layer.  It may be wiser to find a way to "unask"
the question, i.e. make it moot, by avoiding rather than solving the
problem.

> I'm not clear on if the calls I've added to
> SSL_CTX_get0_certificate(ctx) and X509_get_pubkey(), the latter of
> which was being used before, are what's causing the problem. The
> OpenSSL error queue shows the following on the
> SSL_CTX_build_cert_chain() failure:
>
> 00B741558E7F:error:0308010C:digital envelope routines:(unknown 
> function):unsupported:crypto/evp/evp_fetch.c:346:Global default library 
> context, Algorithm (SHA1 : 96), Properties ()
> 00B741558E7F:error:0372:digital envelope routines:(unknown 
> function):decode error:crypto/x509/x_pubkey.c:444:
> 00B741558E7F:error:0372:digital envelope routines:(unknown 
> function):decode error:crypto/x509/x_pubkey.c:444:
> 00B741558E7F:error:0580006C:x509 certificate routines:(unknown 
> function):unable to get certs public key:crypto/x509/x509_vfy.c:1986:
> 00B741558E7F:error:0A86:SSL routines:(unknown function):certificate 
> verify failed:ssl/ssl_cert.c:905:Verify error:unspecified certificate 
> verification error

I haven't seen these before, your guess is as good as mine.

--
Viktor.


Re: X509_get_pubkey() in OpenSSL 3.0?

2021-11-03 Thread Viktor Dukhovni
On Wed, Nov 03, 2021 at 08:32:43PM +, Jason Schultz wrote:

> To summarize, at application start time I read in all of the
> certificates in /etc/ssl/certs/ to a trusted store created with
> X509_STORE_new().
> 
> When getting ready to "start" a server (again, leaving a lot of
> specifics out to avoid getting bogged down in details), I'm doing the
> processing in the previous messages on this thread. Here are the API
> calls again, with the changes previously discussed:
> 
> ctx = SSL_CTX_new_ex(non_fips_libctx, NULL, TLS_method());
> SSL_CTX_use_PrivateKey_file(ctx,,SSL_FILETYPE_PEM);
> SSL_CTX_use_certificate_file(ctx,,SSL_FILETYPE_PEM);
> SSL_CTX_check_private_key(ctx);
> mycert = SSL_CTX_get0_certificate(ctx);
> pkey = X509_get_pubkey(mycert);
> 
>  After that's done, I make several OpenSSL calls to get things set up the way 
> I want:
> 
> param = X509_VERIFY_PARAM_new();
> X509_VERIFY_PARAM_set_flags(param, X509_V_FLAG_PARTIAL_CHAIN);
> X509_STORE_set1_param(ssl_trusted_certs, param);
> X509_VERIFY_PARAM_free(param);
> 
> I call these to treat intermediate certs as trust-anchors, so I can
> trust an intermediate certificate; ssl_trusted_certs is the
> aforementioned X509_STORE.

I am puzzled as to you working so hard (writing a bunch of low-level
trust-store and chain construction code) to construct at runtime, what
could be created statically at chain file construction time.  Especially
if you stick with best practice and keep certificate lifetimes
reasonably short (~90 days or less, not years).  The certificate chain
file constructed at the time the certificate is issued should work
unchanged for the lifetime of the certificate, and the server
applications can avoid having to execute any chain construction or
verification code.

Yes, you're asking somewhat "interesting" questions, in that, e.g., I am
not up to speed on all the changes in 3.0.0, and perhaps there are
indeed some issues around legacy SHA1 signatures, but I do suspect that
a more productive use of your time is likely to reconsider the decision
to work at such a low layer.  It may be wiser to find a way to "unask"
the question, i.e. make it moot, by avoiding rather than solving the
problem.

> I'm not clear on if the calls I've added to
> SSL_CTX_get0_certificate(ctx) and X509_get_pubkey(), the latter of
> which was being used before, are what's causing the problem. The
> OpenSSL error queue shows the following on the
> SSL_CTX_build_cert_chain() failure:
> 
> 00B741558E7F:error:0308010C:digital envelope routines:(unknown 
> function):unsupported:crypto/evp/evp_fetch.c:346:Global default library 
> context, Algorithm (SHA1 : 96), Properties ()
> 00B741558E7F:error:0372:digital envelope routines:(unknown 
> function):decode error:crypto/x509/x_pubkey.c:444:
> 00B741558E7F:error:0372:digital envelope routines:(unknown 
> function):decode error:crypto/x509/x_pubkey.c:444:
> 00B741558E7F:error:0580006C:x509 certificate routines:(unknown 
> function):unable to get certs public key:crypto/x509/x509_vfy.c:1986:
> 00B741558E7F:error:0A86:SSL routines:(unknown function):certificate 
> verify failed:ssl/ssl_cert.c:905:Verify error:unspecified certificate 
> verification error

I haven't seen these before, your guess is as good as mine.

-- 
Viktor.


Re: X509_get_pubkey() in OpenSSL 3.0?

2021-11-03 Thread Jason Schultz
Victor-

Since the only code that's changed from this working with OpenSSL 1.1.1 is the 
code we've been talking about in this thread, it's possible that this is 
causing the problem.

I should explain more what I am doing and how, and also mention that you helped 
me with this when I was trying to sort things out when porting from 1.0.2 to 
1.1.1 over a year ago:

https://www.mail-archive.com/openssl-users@openssl.org/msg87754.html

To summarize, at application start time I read in all of the certificates in 
/etc/ssl/certs/ to a trusted store created with X509_STORE_new().

When getting ready to "start" a server (again, leaving a lot of specifics out 
to avoid getting bogged down in details), I'm doing the processing in the 
previous messages on this thread. Here are the API calls again, with the 
changes previously discussed:


ctx = SSL_CTX_new_ex(non_fips_libctx, NULL, TLS_method());
SSL_CTX_use_PrivateKey_file(ctx,,SSL_FILETYPE_PEM);
SSL_CTX_use_certificate_file(ctx,,SSL_FILETYPE_PEM);
SSL_CTX_check_private_key(ctx);
mycert = SSL_CTX_get0_certificate(ctx);
pkey = X509_get_pubkey(mycert);

 After that's done, I make several OpenSSL calls to get things set up the way I 
want:

param = X509_VERIFY_PARAM_new();
X509_VERIFY_PARAM_set_flags(param, X509_V_FLAG_PARTIAL_CHAIN);
X509_STORE_set1_param(ssl_trusted_certs, param);
X509_VERIFY_PARAM_free(param);

I call these to treat intermediate certs as trust-anchors, so I can trust an 
intermediate certificate; ssl_trusted_certs is the aforementioned X509_STORE.

Another call:

status = SSL_CTX_set1_verify_cert_store(ctx,ssl_trusted_certs);

...is to set the store for verifying peer certificates (in the case of client 
authentication) to the entire trusted store.

Then this API:

status = SSL_CTX_set1_chain_cert_store(ctx, ssl_trusted_certs);

...makes sure OpenSSL has access to that entire store to form a full 
certificate chain to a peer in a handshake. Our certificates are stored one per 
file, we do not store a full or partial chains in a single file.

Then, the final two calls before I hit the error:

status = SSL_CTX_set_mode(ctx, SSL_MODE_NO_AUTO_CHAIN);
status = SSL_CTX_build_cert_chain(ctx, SSL_BUILD_CHAIN_FLAG_NO_ROOT);

The purpose of the first is to allow self signed certificates to be used by the 
server. (This is only for testing purposes, but in this particular case where 
SSL_CTX_build_cert_chain() is throwing errors, I am using a self-signed 
certificate.) The second is to tell OpenSSL to (even though we have access to 
the entire chain, including the root) not include the root certificate when 
building the chain to send during a handshake.

I'm not clear on if the calls I've added to SSL_CTX_get0_certificate(ctx) and 
X509_get_pubkey(), the latter of which was being used before, are what's 
causing the problem. The OpenSSL error queue shows the following on the 
SSL_CTX_build_cert_chain() failure:

00B741558E7F:error:0308010C:digital envelope routines:(unknown 
function):unsupported:crypto/evp/evp_fetch.c:346:Global default library 
context, Algorithm (SHA1 : 96), Properties ()
00B741558E7F:error:0372:digital envelope routines:(unknown 
function):decode error:crypto/x509/x_pubkey.c:444:
00B741558E7F:error:0372:digital envelope routines:(unknown 
function):decode error:crypto/x509/x_pubkey.c:444:
00B741558E7F:error:0580006C:x509 certificate routines:(unknown 
function):unable to get certs public key:crypto/x509/x509_vfy.c:1986:
00B741558E7F:error:0A86:SSL routines:(unknown function):certificate 
verify failed:ssl/ssl_cert.c:905:Verify error:unspecified certificate 
verification error

I'm using the non-FIPS library context in this case, and the first error makes 
me think I need to load the legacy provider for my non FIPS library context if 
there are any SHA1 certificates in the X509_store? The one I am using for the 
server cert is not SHA1, but there are probably some SHA1 certs in 
/etc/ssl/certs/. I don't see errors when adding those certificates to the store 
though. I also don't see SHA1 in the list of algorithms provided by the legacy 
provider in the Wiki.

The next two errors are the same ones that I was getting when attempting to 
call X509_get_pubkey() before changing the code to get it to work, which is 
interesting.

Maybe this is what you were trying to explain in your email, but I'm not 
understanding?

Jason



From: openssl-users  on behalf of Viktor 
Dukhovni 
Sent: Wednesday, November 3, 2021 4:47 PM
To: openssl-users@openssl.org 
Subject: Re: X509_get_pubkey() in OpenSSL 3.0?

On Wed, Nov 03, 2021 at 12:38:51PM +, Jason Schultz wrote:

> In any case, things appear to be working now, but I'm hitting an issue
> later on when calling SSL_CTX_build_cert_chain(). I working on
> debugging that, I may have to start yet another thread later.

Your mistake is 

Re: X509_get_pubkey() in OpenSSL 3.0?

2021-11-03 Thread Viktor Dukhovni
On Wed, Nov 03, 2021 at 12:38:51PM +, Jason Schultz wrote:

> In any case, things appear to be working now, but I'm hitting an issue
> later on when calling SSL_CTX_build_cert_chain(). I working on
> debugging that, I may have to start yet another thread later.

Your mistake is probably in loading a certificate file, rather than
a certificate chain file.  With the latter, you'd also pick up any
associated intermediate issuer certificates (e.g. from certbot's
"fullchain.pem").

With the intermediate certificates thus obtained, you're far more likely
to be able to verify the completely server's chain relative to some
trust store with exclusively or mostly just a bunch of root CAs.

I'd in fact recommend not rebuilding the provided chain, but just
observing whether it is complete, the user may have good reasons
for going with some alternative sequence of issuer CAs (e.g. to
support old Android devices, as with e.g. current Let's Encrypt
redundant cross cert).  Therefore, per:

SSL_CTX_build_cert_chain() builds the certificate chain for ctx.
Normally this uses the chain store or the verify store if the chain
store is not set. If the function is successful the built chain will
replace any existing chain. The flags parameter can be set to
SSL_BUILD_CHAIN_FLAG_UNTRUSTED to use existing chain certificates as
untrusted CAs, SSL_BUILD_CHAIN_FLAG_NO_ROOT to omit the root CA from
the built chain, SSL_BUILD_CHAIN_FLAG_CHECK to use all existing
chain certificates only to build the chain (effectively sanity
checking and rearranging them if necessary), the flag
SSL_BUILD_CHAIN_FLAG_IGNORE_ERROR ignores any errors during
verification: if flag SSL_BUILD_CHAIN_FLAG_CLEAR_ERROR is also set
verification errors are cleared from the error queue. Details of the
chain building process are described in "Certification Path
Building" in openssl-verification-options(1).

I'd set the flags to:

SSL_BUILD_CHAIN_FLAG_UNTRUSTED | SSL_BUILD_CHAIN_FLAG_CHECK

if you're sure the service is not DANE TLSA enabled, and there's
definitely good reason to omit the root CA from the chain, or
you provide a configuration to let the user make the choice,
you can also add:

SSL_BUILD_CHAIN_FLAG_NO_ROOT

which is often, but not always appropriate, and should ideally
not be unconditionally hardcoded.

Be sure to clear the error queue before starting, and after reporting
any errors observed.

-- 
Viktor.


Re: X509_get_pubkey() in OpenSSL 3.0?

2021-11-03 Thread Jason Schultz
Victor-

Thanks for the info. I think I'm going to use:

X509 *SSL_CTX_get0_certificate(const SSL_CTX *ctx)
EVP_PKEY pkey = X509_get_pubkey(cert);

(also suggested by Selva) The reason is, and to answer some of your questions, 
all of this is taking place well before any handshakes, so the SSL object 
doesn't come into play at this point. We do allow users to specify both an RSA 
and EC cert/key pair, but the order in which we set them up will work since 
these functions operate on the last one to load. If the certificate loads, 
that's great, but we also tell our users if they specified an RSA cert if it's 
really a EC cert, etc. We also do some checks on the certificate, like if it's 
expired, or not valid yet; that's why I chose SSL_CTX_get0_certificate() above, 
so I have the X509 certificate object to make those checks, with 
X509_get0_notBefore(), etc.

In any case, things appear to be working now, but I'm hitting an issue later on 
when calling SSL_CTX_build_cert_chain(). I working on debugging that, I may 
have to start yet another thread later.

Thanks,

Jason


From: openssl-users  on behalf of Viktor 
Dukhovni 
Sent: Tuesday, November 2, 2021 9:01 PM
To: openssl-users@openssl.org 
Subject: Re: X509_get_pubkey() in OpenSSL 3.0?

On Tue, Nov 02, 2021 at 08:28:01PM +, Jason Schultz wrote:
> Victor-
>
> I can't seem to find any documentation on SSL_CTX_get0_privatekey(),
> but by the name of it, it sounds like it's getting the private key;
> I'm trying to get the public key.

It does appear to be "under-documented" (i.e. not at all), perhaps
that could be addressed.  Note that you can get a public key from
the private key.

> That said, I should probably explain more of why I'm doing what I'm
> doing, because there may be an easier way all together. Basically, we
> allow configuring RSA or EC certificates/keys, and I want to get the
> public key so I can check the type of key with a call to:
>
>  EVP_PKEY_base_id(pubkey);

Which you can equally get from the private key, but there's also:

SSL_CTX_get0_certificate(sadly also "under-documented")

which means that you certainly don't need to read the PEM file again.

> So maybe there's a better way? After I call:
>
>  SSL_CTX_use_certificate_file(ctx,,SSL_FILETYPE_PEM);
>
> Is there an API I can call passing the ctx that will tell me what type
> of certificate is in use for that ctx? Or something else along those
> lines?

Also once you have an (SSL *) handle you can call SSL_get_certificate(3)
which is documented, and proceed from there.

> It's very possible I'm overcomplicating things with the fopen(),
> PEM_read_X509(), X509_get_pubkey() sequence, so any suggestions on how
> to better accomplish this verification are welcome.

Yes.  Query the data you already have in memory.

Note that a context can be configured with *both* an RSA certificate
chain *and* an EC certificate chain.  The above functions return the one
most recently loaded, but a handshake with a peer may select one of
the other chains.

Most applications only load keys for just one algorithm, but in general
more may be present.

It is surprising that you care which algorithm is in cert/keys.  So
long as it loads, why does it matter?

If you want to log data for each handshake, at that point you can use
SSL_get_certificate(3) for the cert actually selected by this handshake
on the local end:


https://github.com/vdukhovni/postfix/blob/master/postfix/src/tls/tls_misc.c#L950-L953

--
Viktor.


Re: X509_get_pubkey() in OpenSSL 3.0?

2021-11-02 Thread Selva Nair
> X509 cert = SSL_CTX_get0_certificate(ctx);
> EVP_PKEY pkey = X509_get_pubkey(cert);
>

*cert and *pkey ...


Re: X509_get_pubkey() in OpenSSL 3.0?

2021-11-02 Thread Viktor Dukhovni
On Tue, Nov 02, 2021 at 08:28:01PM +, Jason Schultz wrote:
> Victor-
> 
> I can't seem to find any documentation on SSL_CTX_get0_privatekey(),
> but by the name of it, it sounds like it's getting the private key;
> I'm trying to get the public key.

It does appear to be "under-documented" (i.e. not at all), perhaps
that could be addressed.  Note that you can get a public key from
the private key.

> That said, I should probably explain more of why I'm doing what I'm
> doing, because there may be an easier way all together. Basically, we
> allow configuring RSA or EC certificates/keys, and I want to get the
> public key so I can check the type of key with a call to:
> 
>  EVP_PKEY_base_id(pubkey);

Which you can equally get from the private key, but there's also:

SSL_CTX_get0_certificate(sadly also "under-documented")

which means that you certainly don't need to read the PEM file again.

> So maybe there's a better way? After I call:
> 
>  SSL_CTX_use_certificate_file(ctx,,SSL_FILETYPE_PEM);
> 
> Is there an API I can call passing the ctx that will tell me what type
> of certificate is in use for that ctx? Or something else along those
> lines?

Also once you have an (SSL *) handle you can call SSL_get_certificate(3)
which is documented, and proceed from there.

> It's very possible I'm overcomplicating things with the fopen(),
> PEM_read_X509(), X509_get_pubkey() sequence, so any suggestions on how
> to better accomplish this verification are welcome.

Yes.  Query the data you already have in memory.

Note that a context can be configured with *both* an RSA certificate
chain *and* an EC certificate chain.  The above functions return the one
most recently loaded, but a handshake with a peer may select one of
the other chains.

Most applications only load keys for just one algorithm, but in general
more may be present.

It is surprising that you care which algorithm is in cert/keys.  So
long as it loads, why does it matter?

If you want to log data for each handshake, at that point you can use
SSL_get_certificate(3) for the cert actually selected by this handshake
on the local end:


https://github.com/vdukhovni/postfix/blob/master/postfix/src/tls/tls_misc.c#L950-L953

-- 
Viktor.


Re: X509_get_pubkey() in OpenSSL 3.0?

2021-11-02 Thread Selva Nair
On Tue, Nov 2, 2021 at 3:42 PM Jason Schultz  wrote:

> I thought I should start a new thread since this question was buried in my
> "FIPS" thread and I dont' think it has anything to do with FIPS and OpenSSL
> providers. I'm hitting another problem that I think is related to the
> migration to OpenSSL 3.0, as this code works with OpenSSL 1.1.1 (and 1.0.2
> before it). When looking at the documentation pages for 1.1.1 vs 3.0, I'm
> not seeing any differences between the OpenSSL APIs I'm calling in the 2
> different release levels.
>
> Here is the sequence, I'm basically setting up my certificate and private
> key, both in PEM format, for the server, then I need to extract some
> information from them:
>
> ctx = SSL_CTX_new_ex(non_fips_libctx, NULL, TLS_method());
> SSL_CTX_use_PrivateKey_file(ctx,,SSL_FILETYPE_PEM);
> SSL_CTX_use_certificate_file(ctx,,SSL_FILETYPE_PEM);
>
SSL_CTX_check_private_key(ctx);
> fp = fopen(, "r");
> mycert = PEM_read_X509(fp, NULL, 0, NULL)
>

>
All functions return good statuses or non-NULL pointers until the last one,
> X509_get_pubkey() returns NULL.
>

You probably do not have any providers loaded in the default libctx (NULL).
As the first 4 calls have succeeded, non_fips_libctx does have a working
provider.

Check your code for what is stopping default provider getting auto-loaded
into the default libctx (config file misconfiguration or explicit provider
loading?). Or try the following after successfully loading the cert to the
SSL context (ctx):

X509 cert = SSL_CTX_get0_certificate(ctx);
EVP_PKEY pkey = X509_get_pubkey(cert);

This should work as the decoding will happen in non_fips_libctx.

Selva


Re: X509_get_pubkey() in OpenSSL 3.0?

2021-11-02 Thread Jason Schultz
Victor-

I can't seem to find any documentation on SSL_CTX_get0_privatekey(), but by the 
name of it, it sounds like it's getting the private key; I'm trying to get the 
public key.

That said, I should probably explain more of why I'm doing what I'm doing, 
because there may be an easier way all together. Basically, we allow 
configuring RSA or EC certificates/keys, and I want to get the public key so I 
can check the type of key with a call to:

 EVP_PKEY_base_id(pubkey);

I check the return value from that against, for example, EVP_PKEY_EC to verify 
an EC certificate was configured, as opposed to RSA. That's the gist of it, 
without going into too many application specific details.

So maybe there's a better way? After I call:

 SSL_CTX_use_certificate_file(ctx,,SSL_FILETYPE_PEM);

Is there an API I can call passing the ctx that will tell me what type of 
certificate is in use for that ctx? Or something else along those lines?

It's very possible I'm overcomplicating things with the fopen(), 
PEM_read_X509(), X509_get_pubkey() sequence, so any suggestions on how to 
better accomplish this verification are welcome.

Regards,

Jason


> I thought I should start a new thread since this question was buried in my 
> "FIPS" thread and I dont' think it has anything to do with FIPS and OpenSSL 
> providers. I'm hitting another problem that I think is related to the 
> migration to OpenSSL 3.0, as this code works with OpenSSL 1.1.1 (and 1.0.2 
> before it). When looking at the documentation pages for 1.1.1 vs 3.0, I'm not 
> seeing any differences between the OpenSSL APIs I'm calling in the 2 
> different release levels.
>
> Here is the sequence, I'm basically setting up my certificate and private 
> key, both in PEM format, for the server, then I need to extract some 
> information from them:
>
> ctx = SSL_CTX_new_ex(non_fips_libctx, NULL, TLS_method());
> SSL_CTX_use_PrivateKey_file(ctx,,SSL_FILETYPE_PEM);
> SSL_CTX_use_certificate_file(ctx,,SSL_FILETYPE_PEM);
> SSL_CTX_check_private_key(ctx);
> fp = fopen(, "r");
> mycert = PEM_read_X509(fp, NULL, 0, NULL);
> pkey = X509_get_pubkey(mycert);

Without addressing the question of why you're unable to get the public
key handle from the certificate, why not just:

 pkey = SSL_CTX_get0_privatekey(ctx){

and skip reading the cert again?

--
Viktor.


自动回复: Re: X509_get_pubkey() in OpenSSL 3.0?

2021-11-02 Thread 562430030 via openssl-users
您好,您的邮件我已收到,我会尽快阅读,谢谢!

Re: X509_get_pubkey() in OpenSSL 3.0?

2021-11-02 Thread Viktor Dukhovni
On Tue, Nov 02, 2021 at 07:42:15PM +, Jason Schultz wrote:

> I thought I should start a new thread since this question was buried in my 
> "FIPS" thread and I dont' think it has anything to do with FIPS and OpenSSL 
> providers. I'm hitting another problem that I think is related to the 
> migration to OpenSSL 3.0, as this code works with OpenSSL 1.1.1 (and 1.0.2 
> before it). When looking at the documentation pages for 1.1.1 vs 3.0, I'm not 
> seeing any differences between the OpenSSL APIs I'm calling in the 2 
> different release levels.
> 
> Here is the sequence, I'm basically setting up my certificate and private 
> key, both in PEM format, for the server, then I need to extract some 
> information from them:
> 
> ctx = SSL_CTX_new_ex(non_fips_libctx, NULL, TLS_method());
> SSL_CTX_use_PrivateKey_file(ctx,,SSL_FILETYPE_PEM);
> SSL_CTX_use_certificate_file(ctx,,SSL_FILETYPE_PEM);
> SSL_CTX_check_private_key(ctx);
> fp = fopen(, "r");
> mycert = PEM_read_X509(fp, NULL, 0, NULL);
> pkey = X509_get_pubkey(mycert);

Without addressing the question of why you're unable to get the public
key handle from the certificate, why not just:

 pkey = SSL_CTX_get0_privatekey(ctx){

and skip reading the cert again?

-- 
Viktor.


Re: X509_get_pubkey() in OpenSSL 3.0?

2021-11-02 Thread Jason Schultz
Sorry, I send this before finishing the Aside. I ended up calling these APIs:

DECODER_ctx = OSSL_DECODER_CTX_new_for_pkey(EVP_PKEY **pkey,
   const char *input_type,
   const char *input_struct,
   const char *keytype, int selection,
   OSSL_LIB_CTX *libctx, const char *propquery);

OSSL_DECODER_from_fp(dctx, fp);

SSL_CTX_set0_tmp_dh_pkey(ctx, dh_pkey);

To get the DH set up. I can't test this until I get past the intial problem, 
but I tried using the above functions for getting the public key from the 
certificate file, and the problem is still the same.

An example of a certificate I'm using that is failing is below:

# openssl x509 -noout -text -in /etc/ssl/certs/servercert.pem
Certificate:
Data:
Version: 3 (0x2)
Serial Number: 286 (0x11e)
Signature Algorithm: ecdsa-with-SHA256
Issuer: C = US, ST = PA, L = City, O = Example, OU = Networking, CN = 
JCS-EC-CA, emailAddress = joe@example.com
Validity
Not Before: Mar  3 18:15:13 2021 GMT
Not After : Nov 28 18:15:13 2023 GMT
Subject: C = US, ST = PA, L = City, O = Example, OU = Networking, CN = 
JCS-EC-server, emailAddress = joe1@example.com
Subject Public Key Info:
Public Key Algorithm: id-ecPublicKey
Public-Key: (256 bit)
pub:
04:c2:1a:0c:76:dc:d9:b9:3d:49:f6:60:72:fa:18:
c2:e9:31:bc:64:42:24:02:61:06:80:e0:69:2c:5a:
c3:0e:e4:09:ce:79:64:f8:fd:b0:65:63:e1:e9:35:
34:ff:48:58:aa:72:21:20:c1:ce:f2:7a:90:2b:c7:
e7:b7:76:ad:88
ASN1 OID: prime256v1
NIST CURVE: P-256
X509v3 extensions:
X509v3 Basic Constraints:
CA:FALSE
Netscape Comment:
OpenSSL Generated Certificate
X509v3 Subject Key Identifier:
EF:1E:DA:81:3A:43:AA:12:E4:53:B6:4B:E5:A0:3D:AB:CD:30:6B:2F
X509v3 Authority Key Identifier:
60:A2:DC:A3:7A:FB:78:A9:92:5F:88:B5:1A:03:65:9C:F4:10:CD:38
Signature Algorithm: ecdsa-with-SHA256
Signature Value:
30:46:02:21:00:dc:fc:69:9c:a6:54:e1:fa:3c:e7:65:9f:cc:
d5:a4:a2:3a:a7:b1:37:79:60:d0:61:9e:87:15:79:09:0f:34:
14:02:21:00:fd:29:34:bf:bb:c5:02:0d:9a:04:44:6e:94:22:
52:b4:0e:ab:1f:3d:15:5c:07:47:eb:76:68:80:f9:72:96:f6



From: openssl-users  on behalf of Jason 
Schultz 
Sent: Tuesday, November 2, 2021 7:42 PM
To: openssl-users@openssl.org 
Subject: X509_get_pubkey() in OpenSSL 3.0?

I thought I should start a new thread since this question was buried in my 
"FIPS" thread and I dont' think it has anything to do with FIPS and OpenSSL 
providers. I'm hitting another problem that I think is related to the migration 
to OpenSSL 3.0, as this code works with OpenSSL 1.1.1 (and 1.0.2 before it). 
When looking at the documentation pages for 1.1.1 vs 3.0, I'm not seeing any 
differences between the OpenSSL APIs I'm calling in the 2 different release 
levels.

Here is the sequence, I'm basically setting up my certificate and private key, 
both in PEM format, for the server, then I need to extract some information 
from them:

ctx = SSL_CTX_new_ex(non_fips_libctx, NULL, TLS_method());
SSL_CTX_use_PrivateKey_file(ctx,,SSL_FILETYPE_PEM);
SSL_CTX_use_certificate_file(ctx,,SSL_FILETYPE_PEM);
SSL_CTX_check_private_key(ctx);
fp = fopen(, "r");
mycert = PEM_read_X509(fp, NULL, 0, NULL);
pkey = X509_get_pubkey(mycert);

All functions return good statuses or non-NULL pointers until the last one, 
X509_get_pubkey() returns NULL. I have tried this with RSA and Elliptic Curve 
cert/key pairs. I have tried with pairs created with OpenSSL 1.1.1 as well as 
3.0 via the command line.

This seems like a pretty straightforward operation, but it appears that 
key->pkey is NULL in the code below:

EVP_PKEY *X509_PUBKEY_get0(const X509_PUBKEY *key)
{
if (key == NULL) {
ERR_raise(ERR_LIB_X509, ERR_R_PASSED_NULL_PARAMETER);
return NULL;
}

if (key->pkey == NULL) {
/* We failed to decode the key when we loaded it, or it was never set */
ERR_raise(ERR_LIB_EVP, EVP_R_DECODE_ERROR);
return NULL;
}

return key->pkey;
}

I got to this code from the error information I dumped from OpenSSL:

00079FF8647F:error:0372:digital envelope routines:(unknown 
function):decode error:crypto/x509/x_pubkey.c:444:

I can paste certificates if anyone thinks it will help, but I've tried several 
types of cert/key pairs, and using the command line to do "openssl x509 
-pubkey..." displays the public key just fine with the certificate file in 
question.

Here is an example of the openssl command line to create one of t

X509_get_pubkey() in OpenSSL 3.0?

2021-11-02 Thread Jason Schultz
I thought I should start a new thread since this question was buried in my 
"FIPS" thread and I dont' think it has anything to do with FIPS and OpenSSL 
providers. I'm hitting another problem that I think is related to the migration 
to OpenSSL 3.0, as this code works with OpenSSL 1.1.1 (and 1.0.2 before it). 
When looking at the documentation pages for 1.1.1 vs 3.0, I'm not seeing any 
differences between the OpenSSL APIs I'm calling in the 2 different release 
levels.

Here is the sequence, I'm basically setting up my certificate and private key, 
both in PEM format, for the server, then I need to extract some information 
from them:

ctx = SSL_CTX_new_ex(non_fips_libctx, NULL, TLS_method());
SSL_CTX_use_PrivateKey_file(ctx,,SSL_FILETYPE_PEM);
SSL_CTX_use_certificate_file(ctx,,SSL_FILETYPE_PEM);
SSL_CTX_check_private_key(ctx);
fp = fopen(, "r");
mycert = PEM_read_X509(fp, NULL, 0, NULL);
pkey = X509_get_pubkey(mycert);

All functions return good statuses or non-NULL pointers until the last one, 
X509_get_pubkey() returns NULL. I have tried this with RSA and Elliptic Curve 
cert/key pairs. I have tried with pairs created with OpenSSL 1.1.1 as well as 
3.0 via the command line.

This seems like a pretty straightforward operation, but it appears that 
key->pkey is NULL in the code below:

EVP_PKEY *X509_PUBKEY_get0(const X509_PUBKEY *key)
{
if (key == NULL) {
ERR_raise(ERR_LIB_X509, ERR_R_PASSED_NULL_PARAMETER);
return NULL;
}

if (key->pkey == NULL) {
/* We failed to decode the key when we loaded it, or it was never set */
ERR_raise(ERR_LIB_EVP, EVP_R_DECODE_ERROR);
return NULL;
}

return key->pkey;
}

I got to this code from the error information I dumped from OpenSSL:

00079FF8647F:error:0372:digital envelope routines:(unknown 
function):decode error:crypto/x509/x_pubkey.c:444:

I can paste certificates if anyone thinks it will help, but I've tried several 
types of cert/key pairs, and using the command line to do "openssl x509 
-pubkey..." displays the public key just fine with the certificate file in 
question.

Here is an example of the openssl command line to create one of the cert/key 
pairs that hits this error:

openssl req -new -x509 -nodes -newkey ec:<(openssl ecparam -name secp384r1) 
-keyout threecert.key -out threecert.crt -days 365

Aside: While I was waiting for an answer on this, I started working on removing 
some of the deprecated functions in my code, for example, PEM_read_DHparams(). 
I ended up finding the DECODER functions and plan on doing something like:


Thanks,

Jason