|
|
71e593 |
From 4e627add38af409ec6a5023212677956babca1e7 Mon Sep 17 00:00:00 2001
|
|
|
71e593 |
From: Sumit Bose <sbose@redhat.com>
|
|
|
71e593 |
Date: Fri, 16 Nov 2018 17:31:00 +0100
|
|
|
71e593 |
Subject: [PATCH 73/74] utils: refactor ssh key extraction (NSS)
|
|
|
71e593 |
|
|
|
71e593 |
Prepare the current code to allow adding other key types.
|
|
|
71e593 |
|
|
|
71e593 |
Related to https://pagure.io/SSSD/sssd/issue/3887
|
|
|
71e593 |
|
|
|
71e593 |
Reviewed-by: Jakub Hrozek <jhrozek@redhat.com>
|
|
|
71e593 |
---
|
|
|
71e593 |
src/util/cert/nss/cert.c | 110 +++++++++++++++++++++++----------------
|
|
|
71e593 |
1 file changed, 65 insertions(+), 45 deletions(-)
|
|
|
71e593 |
|
|
|
71e593 |
diff --git a/src/util/cert/nss/cert.c b/src/util/cert/nss/cert.c
|
|
|
71e593 |
index a8efef818..b5c4769a8 100644
|
|
|
71e593 |
--- a/src/util/cert/nss/cert.c
|
|
|
71e593 |
+++ b/src/util/cert/nss/cert.c
|
|
|
71e593 |
@@ -223,14 +223,10 @@ done:
|
|
|
71e593 |
#define SSH_RSA_HEADER "ssh-rsa"
|
|
|
71e593 |
#define SSH_RSA_HEADER_LEN (sizeof(SSH_RSA_HEADER) - 1)
|
|
|
71e593 |
|
|
|
71e593 |
-errno_t get_ssh_key_from_cert(TALLOC_CTX *mem_ctx,
|
|
|
71e593 |
- uint8_t *der_blob, size_t der_size,
|
|
|
71e593 |
- uint8_t **key_blob, size_t *key_size)
|
|
|
71e593 |
+static errno_t rsa_pub_key_to_ssh(TALLOC_CTX *mem_ctx,
|
|
|
71e593 |
+ SECKEYPublicKey *cert_pub_key,
|
|
|
71e593 |
+ uint8_t **key_blob, size_t *key_size)
|
|
|
71e593 |
{
|
|
|
71e593 |
- CERTCertDBHandle *handle;
|
|
|
71e593 |
- CERTCertificate *cert = NULL;
|
|
|
71e593 |
- SECItem der_item;
|
|
|
71e593 |
- SECKEYPublicKey *cert_pub_key = NULL;
|
|
|
71e593 |
int ret;
|
|
|
71e593 |
size_t size;
|
|
|
71e593 |
uint8_t *buf = NULL;
|
|
|
71e593 |
@@ -238,44 +234,6 @@ errno_t get_ssh_key_from_cert(TALLOC_CTX *mem_ctx,
|
|
|
71e593 |
size_t exponent_prefix_len;
|
|
|
71e593 |
size_t modulus_prefix_len;
|
|
|
71e593 |
|
|
|
71e593 |
- if (der_blob == NULL || der_size == 0) {
|
|
|
71e593 |
- return EINVAL;
|
|
|
71e593 |
- }
|
|
|
71e593 |
-
|
|
|
71e593 |
- /* initialize NSS if needed */
|
|
|
71e593 |
- ret = nspr_nss_init();
|
|
|
71e593 |
- if (ret != EOK) {
|
|
|
71e593 |
- ret = EIO;
|
|
|
71e593 |
- goto done;
|
|
|
71e593 |
- }
|
|
|
71e593 |
-
|
|
|
71e593 |
- handle = CERT_GetDefaultCertDB();
|
|
|
71e593 |
-
|
|
|
71e593 |
- der_item.len = der_size;
|
|
|
71e593 |
- der_item.data = discard_const(der_blob);
|
|
|
71e593 |
-
|
|
|
71e593 |
- cert = CERT_NewTempCertificate(handle, &der_item, NULL, PR_FALSE, PR_TRUE);
|
|
|
71e593 |
- if (cert == NULL) {
|
|
|
71e593 |
- DEBUG(SSSDBG_OP_FAILURE, "CERT_NewTempCertificate failed.\n");
|
|
|
71e593 |
- ret = EINVAL;
|
|
|
71e593 |
- goto done;
|
|
|
71e593 |
- }
|
|
|
71e593 |
-
|
|
|
71e593 |
- cert_pub_key = CERT_ExtractPublicKey(cert);
|
|
|
71e593 |
- if (cert_pub_key == NULL) {
|
|
|
71e593 |
- DEBUG(SSSDBG_OP_FAILURE, "CERT_ExtractPublicKey failed.\n");
|
|
|
71e593 |
- ret = EIO;
|
|
|
71e593 |
- goto done;
|
|
|
71e593 |
- }
|
|
|
71e593 |
-
|
|
|
71e593 |
- if (cert_pub_key->keyType != rsaKey) {
|
|
|
71e593 |
- DEBUG(SSSDBG_CRIT_FAILURE,
|
|
|
71e593 |
- "Expected RSA public key, found unsupported [%d].\n",
|
|
|
71e593 |
- cert_pub_key->keyType);
|
|
|
71e593 |
- ret = EINVAL;
|
|
|
71e593 |
- goto done;
|
|
|
71e593 |
- }
|
|
|
71e593 |
-
|
|
|
71e593 |
/* Looks like nss drops the leading 00 which AFAIK is added to make sure
|
|
|
71e593 |
* the bigint is handled as positive number if the leading bit is set. */
|
|
|
71e593 |
exponent_prefix_len = 0;
|
|
|
71e593 |
@@ -330,6 +288,68 @@ done:
|
|
|
71e593 |
if (ret != EOK) {
|
|
|
71e593 |
talloc_free(buf);
|
|
|
71e593 |
}
|
|
|
71e593 |
+
|
|
|
71e593 |
+ return ret;
|
|
|
71e593 |
+}
|
|
|
71e593 |
+
|
|
|
71e593 |
+errno_t get_ssh_key_from_cert(TALLOC_CTX *mem_ctx,
|
|
|
71e593 |
+ uint8_t *der_blob, size_t der_size,
|
|
|
71e593 |
+ uint8_t **key_blob, size_t *key_size)
|
|
|
71e593 |
+{
|
|
|
71e593 |
+ CERTCertDBHandle *handle;
|
|
|
71e593 |
+ CERTCertificate *cert = NULL;
|
|
|
71e593 |
+ SECItem der_item;
|
|
|
71e593 |
+ SECKEYPublicKey *cert_pub_key = NULL;
|
|
|
71e593 |
+ int ret;
|
|
|
71e593 |
+
|
|
|
71e593 |
+ if (der_blob == NULL || der_size == 0) {
|
|
|
71e593 |
+ return EINVAL;
|
|
|
71e593 |
+ }
|
|
|
71e593 |
+
|
|
|
71e593 |
+ /* initialize NSS if needed */
|
|
|
71e593 |
+ ret = nspr_nss_init();
|
|
|
71e593 |
+ if (ret != EOK) {
|
|
|
71e593 |
+ ret = EIO;
|
|
|
71e593 |
+ goto done;
|
|
|
71e593 |
+ }
|
|
|
71e593 |
+
|
|
|
71e593 |
+ handle = CERT_GetDefaultCertDB();
|
|
|
71e593 |
+
|
|
|
71e593 |
+ der_item.len = der_size;
|
|
|
71e593 |
+ der_item.data = discard_const(der_blob);
|
|
|
71e593 |
+
|
|
|
71e593 |
+ cert = CERT_NewTempCertificate(handle, &der_item, NULL, PR_FALSE, PR_TRUE);
|
|
|
71e593 |
+ if (cert == NULL) {
|
|
|
71e593 |
+ DEBUG(SSSDBG_OP_FAILURE, "CERT_NewTempCertificate failed.\n");
|
|
|
71e593 |
+ ret = EINVAL;
|
|
|
71e593 |
+ goto done;
|
|
|
71e593 |
+ }
|
|
|
71e593 |
+
|
|
|
71e593 |
+ cert_pub_key = CERT_ExtractPublicKey(cert);
|
|
|
71e593 |
+ if (cert_pub_key == NULL) {
|
|
|
71e593 |
+ DEBUG(SSSDBG_OP_FAILURE, "CERT_ExtractPublicKey failed.\n");
|
|
|
71e593 |
+ ret = EIO;
|
|
|
71e593 |
+ goto done;
|
|
|
71e593 |
+ }
|
|
|
71e593 |
+
|
|
|
71e593 |
+ switch (cert_pub_key->keyType) {
|
|
|
71e593 |
+ case rsaKey:
|
|
|
71e593 |
+ ret = rsa_pub_key_to_ssh(mem_ctx, cert_pub_key, key_blob, key_size);
|
|
|
71e593 |
+ if (ret != EOK) {
|
|
|
71e593 |
+ DEBUG(SSSDBG_OP_FAILURE, "rsa_pub_key_to_ssh failed.\n");
|
|
|
71e593 |
+ goto done;
|
|
|
71e593 |
+ }
|
|
|
71e593 |
+ break;
|
|
|
71e593 |
+ default:
|
|
|
71e593 |
+ DEBUG(SSSDBG_CRIT_FAILURE,
|
|
|
71e593 |
+ "Expected RSA public key, found unsupported [%d].\n",
|
|
|
71e593 |
+ cert_pub_key->keyType);
|
|
|
71e593 |
+ ret = EINVAL;
|
|
|
71e593 |
+ goto done;
|
|
|
71e593 |
+ }
|
|
|
71e593 |
+
|
|
|
71e593 |
+done:
|
|
|
71e593 |
+
|
|
|
71e593 |
SECKEY_DestroyPublicKey(cert_pub_key);
|
|
|
71e593 |
CERT_DestroyCertificate(cert);
|
|
|
71e593 |
|
|
|
71e593 |
--
|
|
|
71e593 |
2.19.1
|
|
|
71e593 |
|