I'm building an OpenSSL engine that implements ECDSA_METHOD, which includes signature creation and signature verification functions. Since the only usage of ECDHE private key is related to signature creation, having the key exported from the engine and presenting it anywhere else is not required.
However, if I don't supply the private key to SSL_Context through SSL_set_private_key function SSL handshake fails with the error below:
error:14094410:SSL routines:ssl3_read_bytes:sslv3 alert handshake failure
I've also tried to provide a mock key (one that is not related to a public key in the cert) to SSL_set_private_key function, but this function does verify if private/public keys match and throws an error about bad certificate if they don't.
It looks like openssl allows by-passing this validation in some cases, e.g. this is what I found in ssl/ssl_rsa.c
#ifndef OPENSSL_NO_RSA
/*
* Don't check the public/private key, this is mostly for smart
* cards.
*/
if ((pkey->type == EVP_PKEY_RSA) &&
(RSA_flags(pkey->pkey.rsa) & RSA_METHOD_FLAG_NO_CHECK)) ;
else
#endif
if (!X509_check_private_key(c->pkeys[i].x509, pkey)) {
X509_free(c->pkeys[i].x509);
c->pkeys[i].x509 = NULL;
return 0;
}
I think, I need something similar for an EC key, but I didn't find it anywhere. Any other solutions are appreciated as well.
This might not be the only option you have, but I think that you can achieve what you are looking for by creating your own
EVP_PKEY_METHOD
and implementing its functions as required. That way, you can store a handle to your own, for example, smart card based key and then invoke the proper sign methods at the right moment. You have to set the proper methods with theEVP_PKEY_meth_set_Xyz()
functions, likeEVP_PKEY_meth_set_sign(<yourSigningFunction>)
. For example, if you were using the Windows crypto API, you would have to invokeNCryptSignHash()
from your signing function. That way, you do not have to export the private key from the Windows key store to obtain a signature.I have done this before and the only big thing I ran into (apart from lack of documentation and examples) was a missing key store functionality at the
EVP
level. There seems to be some work in progress as you can see here. As a work around, I had to select keys/certificates from the a store as part of the key generation mechanism and it is not really intended for that.If you decide to go this route, then be prepared for a few weeks of trial and error.