mirror of
https://github.com/QuasarApp/openssl.git
synced 2025-05-08 15:39:41 +00:00
Add the ability to ECX to import keys with only the private key
ECX keys can very easily crete the public key from the private key. Therefore when we import ecx keys it is sufficent to just have the private key. Reviewed-by: Shane Lontis <shane.lontis@oracle.com> (Merged from https://github.com/openssl/openssl/pull/11635)
This commit is contained in:
parent
a6f8a834ba
commit
969024b458
@ -9,6 +9,8 @@
|
||||
|
||||
#include <openssl/core_names.h>
|
||||
#include <openssl/params.h>
|
||||
#include <openssl/ec.h>
|
||||
#include <openssl/err.h>
|
||||
#include "crypto/ecx.h"
|
||||
#include "ecx_backend.h"
|
||||
|
||||
@ -18,10 +20,35 @@
|
||||
* implementations alike.
|
||||
*/
|
||||
|
||||
int ecx_public_from_private(ECX_KEY *key)
|
||||
{
|
||||
switch (key->type) {
|
||||
case ECX_KEY_TYPE_X25519:
|
||||
X25519_public_from_private(key->pubkey, key->privkey);
|
||||
break;
|
||||
case ECX_KEY_TYPE_ED25519:
|
||||
if (!ED25519_public_from_private(key->libctx, key->pubkey, key->privkey)) {
|
||||
ECerr(0, EC_R_FAILED_MAKING_PUBLIC_KEY);
|
||||
return 0;
|
||||
}
|
||||
break;
|
||||
case ECX_KEY_TYPE_X448:
|
||||
X448_public_from_private(key->pubkey, key->privkey);
|
||||
break;
|
||||
case ECX_KEY_TYPE_ED448:
|
||||
if (!ED448_public_from_private(key->libctx, key->pubkey, key->privkey)) {
|
||||
ECerr(0, EC_R_FAILED_MAKING_PUBLIC_KEY);
|
||||
return 0;
|
||||
}
|
||||
break;
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
int ecx_key_fromdata(ECX_KEY *ecx, const OSSL_PARAM params[],
|
||||
int include_private)
|
||||
{
|
||||
size_t privkeylen = 0, pubkeylen;
|
||||
size_t privkeylen = 0, pubkeylen = 0;
|
||||
const OSSL_PARAM *param_priv_key = NULL, *param_pub_key;
|
||||
unsigned char *pubkey;
|
||||
|
||||
@ -32,11 +59,8 @@ int ecx_key_fromdata(ECX_KEY *ecx, const OSSL_PARAM params[],
|
||||
if (include_private)
|
||||
param_priv_key =
|
||||
OSSL_PARAM_locate_const(params, OSSL_PKEY_PARAM_PRIV_KEY);
|
||||
/*
|
||||
* If a private key is present then a public key must also be present.
|
||||
* Alternatively we've just got a public key.
|
||||
*/
|
||||
if (param_pub_key == NULL)
|
||||
|
||||
if (param_pub_key == NULL && param_priv_key == NULL)
|
||||
return 0;
|
||||
|
||||
if (param_priv_key != NULL
|
||||
@ -46,15 +70,19 @@ int ecx_key_fromdata(ECX_KEY *ecx, const OSSL_PARAM params[],
|
||||
return 0;
|
||||
|
||||
pubkey = ecx->pubkey;
|
||||
if (!OSSL_PARAM_get_octet_string(param_pub_key,
|
||||
(void **)&pubkey,
|
||||
sizeof(ecx->pubkey), &pubkeylen))
|
||||
if (param_pub_key != NULL
|
||||
&& !OSSL_PARAM_get_octet_string(param_pub_key,
|
||||
(void **)&pubkey,
|
||||
sizeof(ecx->pubkey), &pubkeylen))
|
||||
return 0;
|
||||
|
||||
if (pubkeylen != ecx->keylen
|
||||
if ((param_pub_key != NULL && pubkeylen != ecx->keylen)
|
||||
|| (param_priv_key != NULL && privkeylen != ecx->keylen))
|
||||
return 0;
|
||||
|
||||
if (param_pub_key == NULL && !ecx_public_from_private(ecx))
|
||||
return 0;
|
||||
|
||||
ecx->haspubkey = 1;
|
||||
|
||||
return 1;
|
||||
|
@ -88,25 +88,9 @@ static int ecx_key_op(EVP_PKEY *pkey, int id, const X509_ALGOR *palg,
|
||||
} else {
|
||||
memcpy(privkey, p, KEYLENID(id));
|
||||
}
|
||||
switch (id) {
|
||||
case EVP_PKEY_X25519:
|
||||
X25519_public_from_private(pubkey, privkey);
|
||||
break;
|
||||
case EVP_PKEY_ED25519:
|
||||
if (!ED25519_public_from_private(libctx, pubkey, privkey)) {
|
||||
ECerr(EC_F_ECX_KEY_OP, EC_R_FAILED_MAKING_PUBLIC_KEY);
|
||||
goto err;
|
||||
}
|
||||
break;
|
||||
case EVP_PKEY_X448:
|
||||
X448_public_from_private(pubkey, privkey);
|
||||
break;
|
||||
case EVP_PKEY_ED448:
|
||||
if (!ED448_public_from_private(libctx, pubkey, privkey)) {
|
||||
ECerr(EC_F_ECX_KEY_OP, EC_R_FAILED_MAKING_PUBLIC_KEY);
|
||||
goto err;
|
||||
}
|
||||
break;
|
||||
if (!ecx_public_from_private(key)) {
|
||||
ECerr(EC_F_ECX_KEY_OP, EC_R_FAILED_MAKING_PUBLIC_KEY);
|
||||
goto err;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -109,6 +109,7 @@ void X448_public_from_private(uint8_t out_public_value[56],
|
||||
const uint8_t private_key[56]);
|
||||
|
||||
/* Backend support */
|
||||
int ecx_public_from_private(ECX_KEY *key);
|
||||
int ecx_key_fromdata(ECX_KEY *ecx, const OSSL_PARAM params[],
|
||||
int include_private);
|
||||
|
||||
|
@ -113,12 +113,11 @@ static int ecx_import(void *keydata, int selection, const OSSL_PARAM params[])
|
||||
if (key == NULL)
|
||||
return 0;
|
||||
|
||||
if ((selection & OSSL_KEYMGMT_SELECT_PUBLIC_KEY) == 0)
|
||||
if ((selection & OSSL_KEYMGMT_SELECT_KEYPAIR) == 0)
|
||||
return 0;
|
||||
|
||||
include_private = ((selection & OSSL_KEYMGMT_SELECT_PRIVATE_KEY) != 0);
|
||||
if ((selection & OSSL_KEYMGMT_SELECT_KEYPAIR) != 0)
|
||||
ok = ok && ecx_key_fromdata(key, params, include_private);
|
||||
ok = ok && ecx_key_fromdata(key, params, include_private);
|
||||
|
||||
return ok;
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user