mirror of
https://git.libssh.org/projects/libssh.git
synced 2025-12-08 03:42:12 +03:00
curve25519: Avoid reading private curve25519 keys from OpenSSL structures
The previous code created private key curve25519 in OpenSSL, then exported private key and during key generation, created a new OpenSSL private key object. This is needless amount of copying potentially sensitive data back and forth and this will not work when the private key would be backed with external OpenSSL provider, such as pkcs11 provider or different crypto accelerator handling the private key operations for us. Signed-off-by: Jakub Jelen <jjelen@redhat.com> Reviewed-by: Sahana Prasad <sahana@redhat.com>
This commit is contained in:
@@ -125,7 +125,11 @@ struct ssh_crypto_struct {
|
||||
ssh_string ecdh_server_pubkey;
|
||||
#endif
|
||||
#ifdef HAVE_CURVE25519
|
||||
#ifdef HAVE_LIBCRYPTO
|
||||
EVP_PKEY *curve25519_privkey;
|
||||
#else
|
||||
ssh_curve25519_privkey curve25519_privkey;
|
||||
#endif
|
||||
ssh_curve25519_pubkey curve25519_client_pubkey;
|
||||
ssh_curve25519_pubkey curve25519_server_pubkey;
|
||||
#endif
|
||||
|
||||
@@ -62,8 +62,8 @@ static int ssh_curve25519_init(ssh_session session)
|
||||
#ifdef HAVE_LIBCRYPTO
|
||||
EVP_PKEY_CTX *pctx = NULL;
|
||||
EVP_PKEY *pkey = NULL;
|
||||
ssh_curve25519_pubkey *pubkey_loc = NULL;
|
||||
size_t pubkey_len = CURVE25519_PUBKEY_SIZE;
|
||||
size_t pkey_len = CURVE25519_PRIVKEY_SIZE;
|
||||
|
||||
pctx = EVP_PKEY_CTX_new_id(EVP_PKEY_X25519, NULL);
|
||||
if (pctx == NULL) {
|
||||
@@ -92,15 +92,12 @@ static int ssh_curve25519_init(ssh_session session)
|
||||
}
|
||||
|
||||
if (session->server) {
|
||||
rc = EVP_PKEY_get_raw_public_key(pkey,
|
||||
session->next_crypto->curve25519_server_pubkey,
|
||||
&pubkey_len);
|
||||
pubkey_loc = &session->next_crypto->curve25519_server_pubkey;
|
||||
} else {
|
||||
rc = EVP_PKEY_get_raw_public_key(pkey,
|
||||
session->next_crypto->curve25519_client_pubkey,
|
||||
&pubkey_len);
|
||||
pubkey_loc = &session->next_crypto->curve25519_client_pubkey;
|
||||
}
|
||||
|
||||
rc = EVP_PKEY_get_raw_public_key(pkey, *pubkey_loc, &pubkey_len);
|
||||
if (rc != 1) {
|
||||
SSH_LOG(SSH_LOG_TRACE,
|
||||
"Failed to get X25519 raw public key: %s",
|
||||
@@ -109,18 +106,8 @@ static int ssh_curve25519_init(ssh_session session)
|
||||
return SSH_ERROR;
|
||||
}
|
||||
|
||||
rc = EVP_PKEY_get_raw_private_key(pkey,
|
||||
session->next_crypto->curve25519_privkey,
|
||||
&pkey_len);
|
||||
if (rc != 1) {
|
||||
SSH_LOG(SSH_LOG_TRACE,
|
||||
"Failed to get X25519 raw private key: %s",
|
||||
ERR_error_string(ERR_get_error(), NULL));
|
||||
EVP_PKEY_free(pkey);
|
||||
return SSH_ERROR;
|
||||
}
|
||||
|
||||
EVP_PKEY_free(pkey);
|
||||
session->next_crypto->curve25519_privkey = pkey;
|
||||
pkey = NULL;
|
||||
#else
|
||||
rc = ssh_get_random(session->next_crypto->curve25519_privkey,
|
||||
CURVE25519_PRIVKEY_SIZE, 1);
|
||||
@@ -187,9 +174,7 @@ static int ssh_curve25519_build_k(ssh_session session)
|
||||
size_t shared_key_len = sizeof(k);
|
||||
int rc, ret = SSH_ERROR;
|
||||
|
||||
pkey = EVP_PKEY_new_raw_private_key(EVP_PKEY_X25519, NULL,
|
||||
session->next_crypto->curve25519_privkey,
|
||||
CURVE25519_PRIVKEY_SIZE);
|
||||
pkey = session->next_crypto->curve25519_privkey;
|
||||
if (pkey == NULL) {
|
||||
SSH_LOG(SSH_LOG_TRACE,
|
||||
"Failed to create X25519 EVP_PKEY: %s",
|
||||
@@ -246,7 +231,6 @@ static int ssh_curve25519_build_k(ssh_session session)
|
||||
}
|
||||
ret = SSH_OK;
|
||||
out:
|
||||
EVP_PKEY_free(pkey);
|
||||
EVP_PKEY_free(pubkey);
|
||||
EVP_PKEY_CTX_free(pctx);
|
||||
if (ret == SSH_ERROR) {
|
||||
|
||||
@@ -188,6 +188,9 @@ void crypto_free(struct ssh_crypto_struct *crypto)
|
||||
#endif
|
||||
crypto->ecdh_privkey = NULL;
|
||||
}
|
||||
#endif
|
||||
#ifdef HAVE_LIBCRYPTO
|
||||
EVP_PKEY_free(crypto->curve25519_privkey);
|
||||
#endif
|
||||
SAFE_FREE(crypto->dh_server_signature);
|
||||
if (crypto->session_id != NULL) {
|
||||
|
||||
Reference in New Issue
Block a user