Add basic EVP_KEYMGMT API and libcrypto <-> provider interface#9312
Add basic EVP_KEYMGMT API and libcrypto <-> provider interface#9312levitte wants to merge 11 commits intoopenssl:masterfrom
Conversation
|
Do note that this is a very early draft. The primary purpose for submitting this PR this early is to expose they ideas and get early feedback on the line of thoughts. I hope that this will be useful for changes such as #9266 |
This is highly experimental for now, but does provide the necessary support for getting keys through provider OSSL_STORE backends. More on that in a separate PR. |
|
I really want to review this in more detail. I didn't get to it today and am too tired to think too hard this evening. |
|
Key Derivation? I'm not sure about operations "Key loading" vs "Key import". Second is defined for private and public. What will load first one? |
|
Perhaps API could be based on basic(elementary/atomic) operations
defined in "key management protocol".
There is some standard protocols but I prefer experts to propose which
one to use.
Roumen
|
Different operation, see #9266... but yes, it has occured to @mattcaswell and me that key exchange result in a key as well, that wasn't lost on us. There will be some form of integration eventually, I'm sure, but not now and not in this PR. Let's take it a step at a time, yeah? |
Not sure if that would make things better or not. Maybe... |
The key import function takes key material from the input |
|
Documentation added |
|
Richard Levitte wrote:
> I'm not sure about operations "Key loading" vs "Key import".
The key import function takes key material from the input `OSSL_PARAM` array and creates a key from that input (usually a bunch of big numbers).
Interesting.
Working with different cryptographic libraries I note that common part
is exchange of DER encoded data (key, cert). So instead ASN1 encoding
you prefer data encoded as OSSL_PARAM, right?
The key loading function is aimed at HSMs, and gives the option to "load" an HSM protected key given some kind of identity. The identity isn't defined at all for the moment, and I'm thinking of it as highly provider specific, i.e. unstandardised.
This cannot be restricted to "hardware" only. Software "key-store" may
not allow private part to be exported.
My current thinking is that it can work together with a provider OSSL_STORE implementation that returns such identities instead of EVP_PKEYs, and leaves it to libcrypto to actually "load" the key given such an identity. I've an unsubmitted branch where I currently experiment with this.
Right now I'm not sure what you mean by provider and what is difference
to engine. Shall we consider engine as simple provider?
Regards,
Roumen
|
|
I think you need to read up in https://www.openssl.org/docs/OpenSSL300Design.html and https://www.openssl.org/docs/OpenSSLStrategicArchitecture.html. The former is what were working toward, and is the reason you're seeing so much moving around right now. |
|
Richard Levitte wrote:
The identity isn't defined at all for the moment, and I'm thinking of it as highly provider specific, i.e. unstandardised.
In some implementation "identity" is X.509 certificate(a) and private
key. For other is pair public(b) and private key. Private key is
accessed indirectly by (a) or by (b).
May be you want to use another kind of keys . But this will require
delegation of cryptographic operations to identity or "identity provider".
Roumen
|
We have chosen the OSSL_PARAM array as a data transfer medium between libcrypto and provider, yes. We wanted something that isn't tied to any particular form of serialization. I've realized after the fact that they have certain similarities with PKCS#11's attribute templates. |
Correct, I use "HSM" loosly, i.e. for something that keeps keys and other sensitive data for themselves. |
|
This is not a draft any more |
|
"make doc-nits" is complaining. |
mattcaswell
left a comment
There was a problem hiding this comment.
We should have some tests for this code.
There was a problem hiding this comment.
Should we be documenting what "importdomain" actually does? Similarly with the other lines below.
There was a problem hiding this comment.
Yeah, we should. I also think we should document the dispatch functions, I just dunno how, or rather where. (I'm trying to document in the header file at the very least, something we generally suck at, I might add...)
There was a problem hiding this comment.
Whether in this PR or another, we're going to need to document all of these provider functions in the man pages. A provider author should be able to find all the information they need in the man pages, without have to read the source.
There was a problem hiding this comment.
Agreed. For the core_numbers.h stuff, that will be another PR. I have ideas on that...
crypto/evp/keymgmt_lib.c
Outdated
There was a problem hiding this comment.
I just realised nothing is done about the case where all the slots of pk->pkeys are filled in and none of them matched the given keymgmt, i.e. we're not dropping any single entry from the cache... Needs to be fixed.
Ah, in Sure, I will, if you add one for |
Fixed |
Yup, I noticed. Especially with #9266 just being merged... |
8134a5b to
4017ca5
Compare
|
Rebased and squashed, to get a clean slate. |
3c8faa8 to
5ad4970
Compare
|
I think this is ready for final review. There was a failure in Travis, but that turned out to be an unrelated timeout. I've restarted that job, just for the hope of greenery 😉 |
mattcaswell
left a comment
There was a problem hiding this comment.
LGTM. A couple of minor comments which may or may not be addressed before committing. Approval counts either way.
crypto/evp/keymgmt_lib.c
Outdated
There was a problem hiding this comment.
This sentence doesn't seem to quite make sense
crypto/include/internal/asn1_int.h
Outdated
There was a problem hiding this comment.
Perhaps we should add a TODO here (or somewhere else appropriate) to remind us to go and implement these for the various legacy keys that we have?
The idea with the key management "operation" is to support the following set of functionality: - Key domain parameter generation - Key domain parameter import - Key domain parameter export - Key generation - Key import - Key export - Key loading (HSM / hidden key support) With that set of function, we can support handling domain parameters on one provider, key handling on another, and key usage on a third, with transparent export / import of applicable data. Of course, if a provider doesn't offer export / import functionality, then all operations surrounding a key must be performed with the same provider. This method also avoids having to do anything special with legacy assignment of libcrypto key structures, i.e. EVP_PKEY_assign_RSA(). They will simply be used as keys to be exported from whenever they are used with provider based operations. This change only adds the EVP_KEYMGMT API and the libcrypto <-> provider interface. Further changes will integrate them into existing libcrypto functionality.
This function is used to transport private key materia from whatever is already attached to the EVP_PKEY to the new provider, using key data export and import functionality. If a legacy lower level key has been assigned to the EVP_PKEY, we use its data to create a provider side key, and thereby have a bridge between old style public key types and the EVP_PKEY on providers. If successful, this function returns a reference to the appropriate provider side data for the key. This can be used by any operation that wants to use this key.
This affects all its callers: EVP_PKEY_CTX_new(), EVP_PKEY_CTX_new_id().
They are now possible to called with "zero" values, i.e.:
EVP_PKEY_CTX *pctx = EVP_PKEY_CTX_new(NULL, NULL);
or
EVP_PKEY_CTX *pctx = EVP_PKEY_CTX_new_id(0, NULL);
This is suitable for provider use, as the key functionality is tied
with its keys, and the operation time is determined by the init
functions the EVP_PKEY_CTX is used with.
This function clears the cache of provider key references, and is used in evp_keymgmt_export_to_provider() when the internal key is dirty, as well as by EVP_PKEY_free_it().
|
Merged. a94a3e0 Add basic EVP_KEYMGMT API and libcrypto <-> provider interface |
The idea with the key management "operation" is to support the following set of functionality: - Key domain parameter generation - Key domain parameter import - Key domain parameter export - Key generation - Key import - Key export - Key loading (HSM / hidden key support) With that set of function, we can support handling domain parameters on one provider, key handling on another, and key usage on a third, with transparent export / import of applicable data. Of course, if a provider doesn't offer export / import functionality, then all operations surrounding a key must be performed with the same provider. This method also avoids having to do anything special with legacy assignment of libcrypto key structures, i.e. EVP_PKEY_assign_RSA(). They will simply be used as keys to be exported from whenever they are used with provider based operations. This change only adds the EVP_KEYMGMT API and the libcrypto <-> provider interface. Further changes will integrate them into existing libcrypto functionality. Reviewed-by: Matt Caswell <matt@openssl.org> (Merged from #9312)
This function is used to transport private key materia from whatever is already attached to the EVP_PKEY to the new provider, using key data export and import functionality. If a legacy lower level key has been assigned to the EVP_PKEY, we use its data to create a provider side key, and thereby have a bridge between old style public key types and the EVP_PKEY on providers. If successful, this function returns a reference to the appropriate provider side data for the key. This can be used by any operation that wants to use this key. Reviewed-by: Matt Caswell <matt@openssl.org> (Merged from #9312)
This affects all its callers: EVP_PKEY_CTX_new(), EVP_PKEY_CTX_new_id().
They are now possible to called with "zero" values, i.e.:
EVP_PKEY_CTX *pctx = EVP_PKEY_CTX_new(NULL, NULL);
or
EVP_PKEY_CTX *pctx = EVP_PKEY_CTX_new_id(0, NULL);
This is suitable for provider use, as the key functionality is tied
with its keys, and the operation time is determined by the init
functions the EVP_PKEY_CTX is used with.
Reviewed-by: Matt Caswell <matt@openssl.org>
(Merged from #9312)
This function clears the cache of provider key references, and is used in evp_keymgmt_export_to_provider() when the internal key is dirty, as well as by EVP_PKEY_free_it(). Reviewed-by: Matt Caswell <matt@openssl.org> (Merged from #9312)
Reviewed-by: Matt Caswell <matt@openssl.org> (Merged from #9312)
The idea with the key management "operation" is to support the
following set of functionality:
Key domain parameter generation
Key domain parameter import
Key domain parameter export
Key generation
Key import
Key export
Key loading (HSM / hidden key support)
With that set of function, we can support handling domain parameters
on one provider, key handling on another, and key usage on a third,
with transparent export / import of applicable data. Of course, if a
provider doesn't offer export / import functionality, then all
operations surrounding a key must be performed with the same
provider.
This method also avoids having to do anything special with legacy
assignment of libcrypto key structures, i.e. EVP_PKEY_assign_RSA().
They will simply be used as keys to be exported from whenever they are
used with provider based operations.
This change only adds the EVP_KEYMGMT API and the libcrypto <->
provider interface. Further changes will integrate them into existing
libcrypto functionality.