|
|
d738b9 |
From 5bca501af5e28e0a8f5194088fdaea53f5fa419f Mon Sep 17 00:00:00 2001
|
|
|
d738b9 |
From: Matt Rogers <mrogers@redhat.com>
|
|
|
d738b9 |
Date: Tue, 21 Mar 2017 21:24:14 -0400
|
|
|
d738b9 |
Subject: [PATCH] Simplify PKINIT cert iteration and selection
|
|
|
d738b9 |
|
|
|
d738b9 |
Remove the pkinit_cert_handle structures and iteration functions used
|
|
|
d738b9 |
during certificate matching. Instead, make pkinit_matching.c obtain a
|
|
|
d738b9 |
list of matching data objects from the crypto code, and then select a
|
|
|
d738b9 |
cert based on the index into that list.
|
|
|
d738b9 |
|
|
|
d738b9 |
Also fix a typo in the name of crypto_retrieve_X509_key_usage().
|
|
|
d738b9 |
|
|
|
d738b9 |
[ghudson@mit.edu: simplified code]
|
|
|
d738b9 |
|
|
|
d738b9 |
(cherry picked from commit 01b1c0e26252a00f2215408b0e473b84aa0f6a87)
|
|
|
d738b9 |
---
|
|
|
d738b9 |
src/plugins/preauth/pkinit/pkinit_crypto.h | 75 +---
|
|
|
d738b9 |
.../preauth/pkinit/pkinit_crypto_openssl.c | 383 +++++++-----------
|
|
|
d738b9 |
.../preauth/pkinit/pkinit_crypto_openssl.h | 19 -
|
|
|
d738b9 |
src/plugins/preauth/pkinit/pkinit_matching.c | 139 +------
|
|
|
d738b9 |
4 files changed, 194 insertions(+), 422 deletions(-)
|
|
|
d738b9 |
|
|
|
d738b9 |
diff --git a/src/plugins/preauth/pkinit/pkinit_crypto.h b/src/plugins/preauth/pkinit/pkinit_crypto.h
|
|
|
d738b9 |
index 49b96b8ee..a0176acad 100644
|
|
|
d738b9 |
--- a/src/plugins/preauth/pkinit/pkinit_crypto.h
|
|
|
d738b9 |
+++ b/src/plugins/preauth/pkinit/pkinit_crypto.h
|
|
|
d738b9 |
@@ -96,7 +96,6 @@ typedef struct _pkinit_cert_iter_info *pkinit_cert_iter_handle;
|
|
|
d738b9 |
#define PKINIT_ITER_NO_MORE 0x11111111 /* XXX */
|
|
|
d738b9 |
|
|
|
d738b9 |
typedef struct _pkinit_cert_matching_data {
|
|
|
d738b9 |
- pkinit_cert_handle ch; /* cert handle for this certificate */
|
|
|
d738b9 |
char *subject_dn; /* rfc2253-style subject name string */
|
|
|
d738b9 |
char *issuer_dn; /* rfc2253-style issuer name string */
|
|
|
d738b9 |
unsigned int ku_bits; /* key usage information */
|
|
|
d738b9 |
@@ -458,68 +457,38 @@ krb5_error_code crypto_free_cert_info
|
|
|
d738b9 |
|
|
|
d738b9 |
|
|
|
d738b9 |
/*
|
|
|
d738b9 |
- * Get number of certificates available after crypto_load_certs()
|
|
|
d738b9 |
+ * Get a null-terminated list of certificate matching data objects for the
|
|
|
d738b9 |
+ * certificates loaded in id_cryptoctx.
|
|
|
d738b9 |
*/
|
|
|
d738b9 |
-krb5_error_code crypto_cert_get_count
|
|
|
d738b9 |
- (krb5_context context, /* IN */
|
|
|
d738b9 |
- pkinit_plg_crypto_context plg_cryptoctx, /* IN */
|
|
|
d738b9 |
- pkinit_req_crypto_context req_cryptoctx, /* IN */
|
|
|
d738b9 |
- pkinit_identity_crypto_context id_cryptoctx, /* IN */
|
|
|
d738b9 |
- int *cert_count); /* OUT */
|
|
|
d738b9 |
+krb5_error_code
|
|
|
d738b9 |
+crypto_cert_get_matching_data(krb5_context context,
|
|
|
d738b9 |
+ pkinit_plg_crypto_context plg_cryptoctx,
|
|
|
d738b9 |
+ pkinit_req_crypto_context req_cryptoctx,
|
|
|
d738b9 |
+ pkinit_identity_crypto_context id_cryptoctx,
|
|
|
d738b9 |
+ pkinit_cert_matching_data ***md_out);
|
|
|
d738b9 |
|
|
|
d738b9 |
/*
|
|
|
d738b9 |
- * Begin iteration over the certs loaded in crypto_load_certs()
|
|
|
d738b9 |
+ * Free a matching data object.
|
|
|
d738b9 |
*/
|
|
|
d738b9 |
-krb5_error_code crypto_cert_iteration_begin
|
|
|
d738b9 |
- (krb5_context context, /* IN */
|
|
|
d738b9 |
- pkinit_plg_crypto_context plg_cryptoctx, /* IN */
|
|
|
d738b9 |
- pkinit_req_crypto_context req_cryptoctx, /* IN */
|
|
|
d738b9 |
- pkinit_identity_crypto_context id_cryptoctx, /* IN */
|
|
|
d738b9 |
- pkinit_cert_iter_handle *iter_handle); /* OUT */
|
|
|
d738b9 |
+void
|
|
|
d738b9 |
+crypto_cert_free_matching_data(krb5_context context,
|
|
|
d738b9 |
+ pkinit_cert_matching_data *md);
|
|
|
d738b9 |
|
|
|
d738b9 |
/*
|
|
|
d738b9 |
- * End iteration over the certs loaded in crypto_load_certs()
|
|
|
d738b9 |
+ * Free a list of matching data objects.
|
|
|
d738b9 |
*/
|
|
|
d738b9 |
-krb5_error_code crypto_cert_iteration_end
|
|
|
d738b9 |
- (krb5_context context, /* IN */
|
|
|
d738b9 |
- pkinit_cert_iter_handle iter_handle); /* IN */
|
|
|
d738b9 |
+void
|
|
|
d738b9 |
+crypto_cert_free_matching_data_list(krb5_context context,
|
|
|
d738b9 |
+ pkinit_cert_matching_data **matchdata);
|
|
|
d738b9 |
|
|
|
d738b9 |
/*
|
|
|
d738b9 |
- * Get next certificate handle
|
|
|
d738b9 |
+ * Choose one of the certificates loaded in idctx to use for PKINIT client
|
|
|
d738b9 |
+ * operations. cred_index must be an index into the array of matching objects
|
|
|
d738b9 |
+ * returned by crypto_cert_get_matching_data().
|
|
|
d738b9 |
*/
|
|
|
d738b9 |
-krb5_error_code crypto_cert_iteration_next
|
|
|
d738b9 |
- (krb5_context context, /* IN */
|
|
|
d738b9 |
- pkinit_cert_iter_handle iter_handle, /* IN */
|
|
|
d738b9 |
- pkinit_cert_handle *cert_handle); /* OUT */
|
|
|
d738b9 |
-
|
|
|
d738b9 |
-/*
|
|
|
d738b9 |
- * Release cert handle
|
|
|
d738b9 |
- */
|
|
|
d738b9 |
-krb5_error_code crypto_cert_release
|
|
|
d738b9 |
- (krb5_context context, /* IN */
|
|
|
d738b9 |
- pkinit_cert_handle cert_handle); /* IN */
|
|
|
d738b9 |
-
|
|
|
d738b9 |
-/*
|
|
|
d738b9 |
- * Get certificate matching information
|
|
|
d738b9 |
- */
|
|
|
d738b9 |
-krb5_error_code crypto_cert_get_matching_data
|
|
|
d738b9 |
- (krb5_context context, /* IN */
|
|
|
d738b9 |
- pkinit_cert_handle cert_handle, /* IN */
|
|
|
d738b9 |
- pkinit_cert_matching_data **ret_data); /* OUT */
|
|
|
d738b9 |
-
|
|
|
d738b9 |
-/*
|
|
|
d738b9 |
- * Free certificate information
|
|
|
d738b9 |
- */
|
|
|
d738b9 |
-krb5_error_code crypto_cert_free_matching_data
|
|
|
d738b9 |
- (krb5_context context, /* IN */
|
|
|
d738b9 |
- pkinit_cert_matching_data *data); /* IN */
|
|
|
d738b9 |
-
|
|
|
d738b9 |
-/*
|
|
|
d738b9 |
- * Make the given certificate "the chosen one"
|
|
|
d738b9 |
- */
|
|
|
d738b9 |
-krb5_error_code crypto_cert_select
|
|
|
d738b9 |
- (krb5_context context, /* IN */
|
|
|
d738b9 |
- pkinit_cert_matching_data *data); /* IN */
|
|
|
d738b9 |
+krb5_error_code
|
|
|
d738b9 |
+crypto_cert_select(krb5_context context, pkinit_identity_crypto_context idctx,
|
|
|
d738b9 |
+ size_t cred_index);
|
|
|
d738b9 |
|
|
|
d738b9 |
/*
|
|
|
d738b9 |
* Select the default certificate as "the chosen one"
|
|
|
d738b9 |
diff --git a/src/plugins/preauth/pkinit/pkinit_crypto_openssl.c b/src/plugins/preauth/pkinit/pkinit_crypto_openssl.c
|
|
|
d738b9 |
index 6098acc6a..f70aab5b3 100644
|
|
|
d738b9 |
--- a/src/plugins/preauth/pkinit/pkinit_crypto_openssl.c
|
|
|
d738b9 |
+++ b/src/plugins/preauth/pkinit/pkinit_crypto_openssl.c
|
|
|
d738b9 |
@@ -4974,136 +4974,16 @@ cleanup:
|
|
|
d738b9 |
return retval;
|
|
|
d738b9 |
}
|
|
|
d738b9 |
|
|
|
d738b9 |
-/*
|
|
|
d738b9 |
- * Get number of certificates available after crypto_load_certs()
|
|
|
d738b9 |
- */
|
|
|
d738b9 |
-krb5_error_code
|
|
|
d738b9 |
-crypto_cert_get_count(krb5_context context,
|
|
|
d738b9 |
- pkinit_plg_crypto_context plg_cryptoctx,
|
|
|
d738b9 |
- pkinit_req_crypto_context req_cryptoctx,
|
|
|
d738b9 |
- pkinit_identity_crypto_context id_cryptoctx,
|
|
|
d738b9 |
- int *cert_count)
|
|
|
d738b9 |
-{
|
|
|
d738b9 |
- int count;
|
|
|
d738b9 |
-
|
|
|
d738b9 |
- if (id_cryptoctx == NULL || id_cryptoctx->creds[0] == NULL)
|
|
|
d738b9 |
- return EINVAL;
|
|
|
d738b9 |
-
|
|
|
d738b9 |
- for (count = 0;
|
|
|
d738b9 |
- count <= MAX_CREDS_ALLOWED && id_cryptoctx->creds[count] != NULL;
|
|
|
d738b9 |
- count++);
|
|
|
d738b9 |
- *cert_count = count;
|
|
|
d738b9 |
- return 0;
|
|
|
d738b9 |
-}
|
|
|
d738b9 |
-
|
|
|
d738b9 |
-
|
|
|
d738b9 |
-/*
|
|
|
d738b9 |
- * Begin iteration over the certs loaded in crypto_load_certs()
|
|
|
d738b9 |
- */
|
|
|
d738b9 |
-krb5_error_code
|
|
|
d738b9 |
-crypto_cert_iteration_begin(krb5_context context,
|
|
|
d738b9 |
- pkinit_plg_crypto_context plg_cryptoctx,
|
|
|
d738b9 |
- pkinit_req_crypto_context req_cryptoctx,
|
|
|
d738b9 |
- pkinit_identity_crypto_context id_cryptoctx,
|
|
|
d738b9 |
- pkinit_cert_iter_handle *ih_ret)
|
|
|
d738b9 |
-{
|
|
|
d738b9 |
- struct _pkinit_cert_iter_data *id;
|
|
|
d738b9 |
-
|
|
|
d738b9 |
- if (id_cryptoctx == NULL || ih_ret == NULL)
|
|
|
d738b9 |
- return EINVAL;
|
|
|
d738b9 |
- if (id_cryptoctx->creds[0] == NULL) /* No cred info available */
|
|
|
d738b9 |
- return ENOENT;
|
|
|
d738b9 |
-
|
|
|
d738b9 |
- id = calloc(1, sizeof(*id));
|
|
|
d738b9 |
- if (id == NULL)
|
|
|
d738b9 |
- return ENOMEM;
|
|
|
d738b9 |
- id->magic = ITER_MAGIC;
|
|
|
d738b9 |
- id->plgctx = plg_cryptoctx,
|
|
|
d738b9 |
- id->reqctx = req_cryptoctx,
|
|
|
d738b9 |
- id->idctx = id_cryptoctx;
|
|
|
d738b9 |
- id->index = 0;
|
|
|
d738b9 |
- *ih_ret = (pkinit_cert_iter_handle) id;
|
|
|
d738b9 |
- return 0;
|
|
|
d738b9 |
-}
|
|
|
d738b9 |
-
|
|
|
d738b9 |
-/*
|
|
|
d738b9 |
- * End iteration over the certs loaded in crypto_load_certs()
|
|
|
d738b9 |
- */
|
|
|
d738b9 |
-krb5_error_code
|
|
|
d738b9 |
-crypto_cert_iteration_end(krb5_context context,
|
|
|
d738b9 |
- pkinit_cert_iter_handle ih)
|
|
|
d738b9 |
-{
|
|
|
d738b9 |
- struct _pkinit_cert_iter_data *id = (struct _pkinit_cert_iter_data *)ih;
|
|
|
d738b9 |
-
|
|
|
d738b9 |
- if (id == NULL || id->magic != ITER_MAGIC)
|
|
|
d738b9 |
- return EINVAL;
|
|
|
d738b9 |
- free(ih);
|
|
|
d738b9 |
- return 0;
|
|
|
d738b9 |
-}
|
|
|
d738b9 |
-
|
|
|
d738b9 |
-/*
|
|
|
d738b9 |
- * Get next certificate handle
|
|
|
d738b9 |
- */
|
|
|
d738b9 |
-krb5_error_code
|
|
|
d738b9 |
-crypto_cert_iteration_next(krb5_context context,
|
|
|
d738b9 |
- pkinit_cert_iter_handle ih,
|
|
|
d738b9 |
- pkinit_cert_handle *ch_ret)
|
|
|
d738b9 |
-{
|
|
|
d738b9 |
- struct _pkinit_cert_iter_data *id = (struct _pkinit_cert_iter_data *)ih;
|
|
|
d738b9 |
- struct _pkinit_cert_data *cd;
|
|
|
d738b9 |
- pkinit_identity_crypto_context id_cryptoctx;
|
|
|
d738b9 |
-
|
|
|
d738b9 |
- if (id == NULL || id->magic != ITER_MAGIC)
|
|
|
d738b9 |
- return EINVAL;
|
|
|
d738b9 |
-
|
|
|
d738b9 |
- if (ch_ret == NULL)
|
|
|
d738b9 |
- return EINVAL;
|
|
|
d738b9 |
-
|
|
|
d738b9 |
- id_cryptoctx = id->idctx;
|
|
|
d738b9 |
- if (id_cryptoctx == NULL)
|
|
|
d738b9 |
- return EINVAL;
|
|
|
d738b9 |
-
|
|
|
d738b9 |
- if (id_cryptoctx->creds[id->index] == NULL)
|
|
|
d738b9 |
- return PKINIT_ITER_NO_MORE;
|
|
|
d738b9 |
-
|
|
|
d738b9 |
- cd = calloc(1, sizeof(*cd));
|
|
|
d738b9 |
- if (cd == NULL)
|
|
|
d738b9 |
- return ENOMEM;
|
|
|
d738b9 |
-
|
|
|
d738b9 |
- cd->magic = CERT_MAGIC;
|
|
|
d738b9 |
- cd->plgctx = id->plgctx;
|
|
|
d738b9 |
- cd->reqctx = id->reqctx;
|
|
|
d738b9 |
- cd->idctx = id->idctx;
|
|
|
d738b9 |
- cd->index = id->index;
|
|
|
d738b9 |
- cd->cred = id_cryptoctx->creds[id->index++];
|
|
|
d738b9 |
- *ch_ret = (pkinit_cert_handle)cd;
|
|
|
d738b9 |
- return 0;
|
|
|
d738b9 |
-}
|
|
|
d738b9 |
-
|
|
|
d738b9 |
-/*
|
|
|
d738b9 |
- * Release cert handle
|
|
|
d738b9 |
- */
|
|
|
d738b9 |
-krb5_error_code
|
|
|
d738b9 |
-crypto_cert_release(krb5_context context,
|
|
|
d738b9 |
- pkinit_cert_handle ch)
|
|
|
d738b9 |
-{
|
|
|
d738b9 |
- struct _pkinit_cert_data *cd = (struct _pkinit_cert_data *)ch;
|
|
|
d738b9 |
- if (cd == NULL || cd->magic != CERT_MAGIC)
|
|
|
d738b9 |
- return EINVAL;
|
|
|
d738b9 |
- free(cd);
|
|
|
d738b9 |
- return 0;
|
|
|
d738b9 |
-}
|
|
|
d738b9 |
-
|
|
|
d738b9 |
/*
|
|
|
d738b9 |
* Get certificate Key Usage and Extended Key Usage
|
|
|
d738b9 |
*/
|
|
|
d738b9 |
static krb5_error_code
|
|
|
d738b9 |
-crypto_retieve_X509_key_usage(krb5_context context,
|
|
|
d738b9 |
- pkinit_plg_crypto_context plgcctx,
|
|
|
d738b9 |
- pkinit_req_crypto_context reqcctx,
|
|
|
d738b9 |
- X509 *x,
|
|
|
d738b9 |
- unsigned int *ret_ku_bits,
|
|
|
d738b9 |
- unsigned int *ret_eku_bits)
|
|
|
d738b9 |
+crypto_retrieve_X509_key_usage(krb5_context context,
|
|
|
d738b9 |
+ pkinit_plg_crypto_context plgcctx,
|
|
|
d738b9 |
+ pkinit_req_crypto_context reqcctx,
|
|
|
d738b9 |
+ X509 *x,
|
|
|
d738b9 |
+ unsigned int *ret_ku_bits,
|
|
|
d738b9 |
+ unsigned int *ret_eku_bits)
|
|
|
d738b9 |
{
|
|
|
d738b9 |
krb5_error_code retval = 0;
|
|
|
d738b9 |
int i;
|
|
|
d738b9 |
@@ -5202,55 +5082,99 @@ X509_NAME_oneline_ex(X509_NAME * a,
|
|
|
d738b9 |
}
|
|
|
d738b9 |
|
|
|
d738b9 |
/*
|
|
|
d738b9 |
- * Get certificate information
|
|
|
d738b9 |
+ * Get number of certificates available after crypto_load_certs()
|
|
|
d738b9 |
*/
|
|
|
d738b9 |
-krb5_error_code
|
|
|
d738b9 |
-crypto_cert_get_matching_data(krb5_context context,
|
|
|
d738b9 |
- pkinit_cert_handle ch,
|
|
|
d738b9 |
- pkinit_cert_matching_data **ret_md)
|
|
|
d738b9 |
+static krb5_error_code
|
|
|
d738b9 |
+crypto_cert_get_count(pkinit_identity_crypto_context id_cryptoctx,
|
|
|
d738b9 |
+ int *cert_count)
|
|
|
d738b9 |
{
|
|
|
d738b9 |
- krb5_error_code retval;
|
|
|
d738b9 |
- pkinit_cert_matching_data *md;
|
|
|
d738b9 |
- krb5_principal *pkinit_sans =NULL, *upn_sans = NULL;
|
|
|
d738b9 |
- struct _pkinit_cert_data *cd = (struct _pkinit_cert_data *)ch;
|
|
|
d738b9 |
- unsigned int i, j;
|
|
|
d738b9 |
+ int count;
|
|
|
d738b9 |
+
|
|
|
d738b9 |
+ *cert_count = 0;
|
|
|
d738b9 |
+ if (id_cryptoctx == NULL || id_cryptoctx->creds[0] == NULL)
|
|
|
d738b9 |
+ return EINVAL;
|
|
|
d738b9 |
+
|
|
|
d738b9 |
+ for (count = 0;
|
|
|
d738b9 |
+ count <= MAX_CREDS_ALLOWED && id_cryptoctx->creds[count] != NULL;
|
|
|
d738b9 |
+ count++);
|
|
|
d738b9 |
+ *cert_count = count;
|
|
|
d738b9 |
+ return 0;
|
|
|
d738b9 |
+}
|
|
|
d738b9 |
+
|
|
|
d738b9 |
+void
|
|
|
d738b9 |
+crypto_cert_free_matching_data(krb5_context context,
|
|
|
d738b9 |
+ pkinit_cert_matching_data *md)
|
|
|
d738b9 |
+{
|
|
|
d738b9 |
+ int i;
|
|
|
d738b9 |
+
|
|
|
d738b9 |
+ if (md == NULL)
|
|
|
d738b9 |
+ return;
|
|
|
d738b9 |
+ free(md->subject_dn);
|
|
|
d738b9 |
+ free(md->issuer_dn);
|
|
|
d738b9 |
+ for (i = 0; md->sans != NULL && md->sans[i] != NULL; i++)
|
|
|
d738b9 |
+ krb5_free_principal(context, md->sans[i]);
|
|
|
d738b9 |
+ free(md->sans);
|
|
|
d738b9 |
+ free(md);
|
|
|
d738b9 |
+}
|
|
|
d738b9 |
+
|
|
|
d738b9 |
+/*
|
|
|
d738b9 |
+ * Free certificate matching data.
|
|
|
d738b9 |
+ */
|
|
|
d738b9 |
+void
|
|
|
d738b9 |
+crypto_cert_free_matching_data_list(krb5_context context,
|
|
|
d738b9 |
+ pkinit_cert_matching_data **list)
|
|
|
d738b9 |
+{
|
|
|
d738b9 |
+ int i;
|
|
|
d738b9 |
+
|
|
|
d738b9 |
+ for (i = 0; list != NULL && list[i] != NULL; i++)
|
|
|
d738b9 |
+ crypto_cert_free_matching_data(context, list[i]);
|
|
|
d738b9 |
+ free(list);
|
|
|
d738b9 |
+}
|
|
|
d738b9 |
+
|
|
|
d738b9 |
+/*
|
|
|
d738b9 |
+ * Get certificate matching data for cert.
|
|
|
d738b9 |
+ */
|
|
|
d738b9 |
+static krb5_error_code
|
|
|
d738b9 |
+get_matching_data(krb5_context context,
|
|
|
d738b9 |
+ pkinit_plg_crypto_context plg_cryptoctx,
|
|
|
d738b9 |
+ pkinit_req_crypto_context req_cryptoctx, X509 *cert,
|
|
|
d738b9 |
+ pkinit_cert_matching_data **md_out)
|
|
|
d738b9 |
+{
|
|
|
d738b9 |
+ krb5_error_code ret = ENOMEM;
|
|
|
d738b9 |
+ pkinit_cert_matching_data *md = NULL;
|
|
|
d738b9 |
+ krb5_principal *pkinit_sans = NULL, *upn_sans = NULL;
|
|
|
d738b9 |
+ size_t i, j;
|
|
|
d738b9 |
char buf[DN_BUF_LEN];
|
|
|
d738b9 |
unsigned int bufsize = sizeof(buf);
|
|
|
d738b9 |
|
|
|
d738b9 |
- if (cd == NULL || cd->magic != CERT_MAGIC)
|
|
|
d738b9 |
- return EINVAL;
|
|
|
d738b9 |
- if (ret_md == NULL)
|
|
|
d738b9 |
- return EINVAL;
|
|
|
d738b9 |
+ *md_out = NULL;
|
|
|
d738b9 |
|
|
|
d738b9 |
md = calloc(1, sizeof(*md));
|
|
|
d738b9 |
if (md == NULL)
|
|
|
d738b9 |
- return ENOMEM;
|
|
|
d738b9 |
+ goto cleanup;
|
|
|
d738b9 |
|
|
|
d738b9 |
- md->ch = ch;
|
|
|
d738b9 |
-
|
|
|
d738b9 |
- /* get the subject name (in rfc2253 format) */
|
|
|
d738b9 |
- X509_NAME_oneline_ex(X509_get_subject_name(cd->cred->cert),
|
|
|
d738b9 |
- buf, &bufsize, XN_FLAG_SEP_COMMA_PLUS);
|
|
|
d738b9 |
+ /* Get the subject name (in rfc2253 format). */
|
|
|
d738b9 |
+ X509_NAME_oneline_ex(X509_get_subject_name(cert), buf, &bufsize,
|
|
|
d738b9 |
+ XN_FLAG_SEP_COMMA_PLUS);
|
|
|
d738b9 |
md->subject_dn = strdup(buf);
|
|
|
d738b9 |
if (md->subject_dn == NULL) {
|
|
|
d738b9 |
- retval = ENOMEM;
|
|
|
d738b9 |
+ ret = ENOMEM;
|
|
|
d738b9 |
goto cleanup;
|
|
|
d738b9 |
}
|
|
|
d738b9 |
|
|
|
d738b9 |
- /* get the issuer name (in rfc2253 format) */
|
|
|
d738b9 |
- X509_NAME_oneline_ex(X509_get_issuer_name(cd->cred->cert),
|
|
|
d738b9 |
- buf, &bufsize, XN_FLAG_SEP_COMMA_PLUS);
|
|
|
d738b9 |
+ /* Get the issuer name (in rfc2253 format). */
|
|
|
d738b9 |
+ X509_NAME_oneline_ex(X509_get_issuer_name(cert), buf, &bufsize,
|
|
|
d738b9 |
+ XN_FLAG_SEP_COMMA_PLUS);
|
|
|
d738b9 |
md->issuer_dn = strdup(buf);
|
|
|
d738b9 |
if (md->issuer_dn == NULL) {
|
|
|
d738b9 |
- retval = ENOMEM;
|
|
|
d738b9 |
+ ret = ENOMEM;
|
|
|
d738b9 |
goto cleanup;
|
|
|
d738b9 |
}
|
|
|
d738b9 |
|
|
|
d738b9 |
- /* get the san data */
|
|
|
d738b9 |
- retval = crypto_retrieve_X509_sans(context, cd->plgctx, cd->reqctx,
|
|
|
d738b9 |
- cd->cred->cert, &pkinit_sans,
|
|
|
d738b9 |
- &upn_sans, NULL);
|
|
|
d738b9 |
- if (retval)
|
|
|
d738b9 |
+ /* Get the SAN data. */
|
|
|
d738b9 |
+ ret = crypto_retrieve_X509_sans(context, plg_cryptoctx, req_cryptoctx,
|
|
|
d738b9 |
+ cert, &pkinit_sans, &upn_sans, NULL);
|
|
|
d738b9 |
+ if (ret)
|
|
|
d738b9 |
goto cleanup;
|
|
|
d738b9 |
|
|
|
d738b9 |
j = 0;
|
|
|
d738b9 |
@@ -5265,7 +5189,7 @@ crypto_cert_get_matching_data(krb5_context context,
|
|
|
d738b9 |
if (j != 0) {
|
|
|
d738b9 |
md->sans = calloc((size_t)j+1, sizeof(*md->sans));
|
|
|
d738b9 |
if (md->sans == NULL) {
|
|
|
d738b9 |
- retval = ENOMEM;
|
|
|
d738b9 |
+ ret = ENOMEM;
|
|
|
d738b9 |
goto cleanup;
|
|
|
d738b9 |
}
|
|
|
d738b9 |
j = 0;
|
|
|
d738b9 |
@@ -5283,88 +5207,96 @@ crypto_cert_get_matching_data(krb5_context context,
|
|
|
d738b9 |
} else
|
|
|
d738b9 |
md->sans = NULL;
|
|
|
d738b9 |
|
|
|
d738b9 |
- /* get the KU and EKU data */
|
|
|
d738b9 |
-
|
|
|
d738b9 |
- retval = crypto_retieve_X509_key_usage(context, cd->plgctx, cd->reqctx,
|
|
|
d738b9 |
- cd->cred->cert,
|
|
|
d738b9 |
- &md->ku_bits, &md->eku_bits);
|
|
|
d738b9 |
- if (retval)
|
|
|
d738b9 |
+ /* Get the KU and EKU data. */
|
|
|
d738b9 |
+ ret = crypto_retrieve_X509_key_usage(context, plg_cryptoctx,
|
|
|
d738b9 |
+ req_cryptoctx, cert, &md->ku_bits,
|
|
|
d738b9 |
+ &md->eku_bits);
|
|
|
d738b9 |
+ if (ret)
|
|
|
d738b9 |
goto cleanup;
|
|
|
d738b9 |
|
|
|
d738b9 |
- *ret_md = md;
|
|
|
d738b9 |
- retval = 0;
|
|
|
d738b9 |
+ *md_out = md;
|
|
|
d738b9 |
+ md = NULL;
|
|
|
d738b9 |
+
|
|
|
d738b9 |
cleanup:
|
|
|
d738b9 |
- if (retval) {
|
|
|
d738b9 |
- if (md)
|
|
|
d738b9 |
- crypto_cert_free_matching_data(context, md);
|
|
|
d738b9 |
+ crypto_cert_free_matching_data(context, md);
|
|
|
d738b9 |
+ return ret;
|
|
|
d738b9 |
+}
|
|
|
d738b9 |
+
|
|
|
d738b9 |
+krb5_error_code
|
|
|
d738b9 |
+crypto_cert_get_matching_data(krb5_context context,
|
|
|
d738b9 |
+ pkinit_plg_crypto_context plg_cryptoctx,
|
|
|
d738b9 |
+ pkinit_req_crypto_context req_cryptoctx,
|
|
|
d738b9 |
+ pkinit_identity_crypto_context id_cryptoctx,
|
|
|
d738b9 |
+ pkinit_cert_matching_data ***md_out)
|
|
|
d738b9 |
+{
|
|
|
d738b9 |
+ krb5_error_code ret;
|
|
|
d738b9 |
+ pkinit_cert_matching_data **md_list = NULL;
|
|
|
d738b9 |
+ int count, i;
|
|
|
d738b9 |
+
|
|
|
d738b9 |
+ ret = crypto_cert_get_count(id_cryptoctx, &count);
|
|
|
d738b9 |
+ if (ret)
|
|
|
d738b9 |
+ goto cleanup;
|
|
|
d738b9 |
+
|
|
|
d738b9 |
+ md_list = calloc(count + 1, sizeof(*md_list));
|
|
|
d738b9 |
+ if (md_list == NULL) {
|
|
|
d738b9 |
+ ret = ENOMEM;
|
|
|
d738b9 |
+ goto cleanup;
|
|
|
d738b9 |
}
|
|
|
d738b9 |
- return retval;
|
|
|
d738b9 |
+
|
|
|
d738b9 |
+ for (i = 0; i < count; i++) {
|
|
|
d738b9 |
+ ret = get_matching_data(context, plg_cryptoctx, req_cryptoctx,
|
|
|
d738b9 |
+ id_cryptoctx->creds[i]->cert, &md_list[i]);
|
|
|
d738b9 |
+ if (ret) {
|
|
|
d738b9 |
+ pkiDebug("%s: crypto_cert_get_matching_data error %d, %s\n",
|
|
|
d738b9 |
+ __FUNCTION__, ret, error_message(ret));
|
|
|
d738b9 |
+ goto cleanup;
|
|
|
d738b9 |
+ }
|
|
|
d738b9 |
+ }
|
|
|
d738b9 |
+
|
|
|
d738b9 |
+ *md_out = md_list;
|
|
|
d738b9 |
+ md_list = NULL;
|
|
|
d738b9 |
+
|
|
|
d738b9 |
+cleanup:
|
|
|
d738b9 |
+ crypto_cert_free_matching_data_list(context, md_list);
|
|
|
d738b9 |
+ return ret;
|
|
|
d738b9 |
}
|
|
|
d738b9 |
|
|
|
d738b9 |
/*
|
|
|
d738b9 |
- * Free certificate information
|
|
|
d738b9 |
+ * Set the certificate in idctx->creds[cred_index] as the selected certificate.
|
|
|
d738b9 |
*/
|
|
|
d738b9 |
krb5_error_code
|
|
|
d738b9 |
-crypto_cert_free_matching_data(krb5_context context,
|
|
|
d738b9 |
- pkinit_cert_matching_data *md)
|
|
|
d738b9 |
+crypto_cert_select(krb5_context context, pkinit_identity_crypto_context idctx,
|
|
|
d738b9 |
+ size_t cred_index)
|
|
|
d738b9 |
{
|
|
|
d738b9 |
- krb5_principal p;
|
|
|
d738b9 |
- int i;
|
|
|
d738b9 |
+ pkinit_cred_info ci = NULL;
|
|
|
d738b9 |
|
|
|
d738b9 |
- if (md == NULL)
|
|
|
d738b9 |
- return EINVAL;
|
|
|
d738b9 |
- if (md->subject_dn)
|
|
|
d738b9 |
- free(md->subject_dn);
|
|
|
d738b9 |
- if (md->issuer_dn)
|
|
|
d738b9 |
- free(md->issuer_dn);
|
|
|
d738b9 |
- if (md->sans) {
|
|
|
d738b9 |
- for (i = 0, p = md->sans[i]; p != NULL; p = md->sans[++i])
|
|
|
d738b9 |
- krb5_free_principal(context, p);
|
|
|
d738b9 |
- free(md->sans);
|
|
|
d738b9 |
- }
|
|
|
d738b9 |
- free(md);
|
|
|
d738b9 |
- return 0;
|
|
|
d738b9 |
-}
|
|
|
d738b9 |
-
|
|
|
d738b9 |
-/*
|
|
|
d738b9 |
- * Make this matching certificate "the chosen one"
|
|
|
d738b9 |
- */
|
|
|
d738b9 |
-krb5_error_code
|
|
|
d738b9 |
-crypto_cert_select(krb5_context context,
|
|
|
d738b9 |
- pkinit_cert_matching_data *md)
|
|
|
d738b9 |
-{
|
|
|
d738b9 |
- struct _pkinit_cert_data *cd;
|
|
|
d738b9 |
- if (md == NULL)
|
|
|
d738b9 |
- return EINVAL;
|
|
|
d738b9 |
-
|
|
|
d738b9 |
- cd = (struct _pkinit_cert_data *)md->ch;
|
|
|
d738b9 |
- if (cd == NULL || cd->magic != CERT_MAGIC)
|
|
|
d738b9 |
- return EINVAL;
|
|
|
d738b9 |
+ if (cred_index >= MAX_CREDS_ALLOWED || idctx->creds[cred_index] == NULL)
|
|
|
d738b9 |
+ return ENOENT;
|
|
|
d738b9 |
|
|
|
d738b9 |
+ ci = idctx->creds[cred_index];
|
|
|
d738b9 |
/* copy the selected cert into our id_cryptoctx */
|
|
|
d738b9 |
- if (cd->idctx->my_certs != NULL) {
|
|
|
d738b9 |
- sk_X509_pop_free(cd->idctx->my_certs, X509_free);
|
|
|
d738b9 |
- }
|
|
|
d738b9 |
- cd->idctx->my_certs = sk_X509_new_null();
|
|
|
d738b9 |
- sk_X509_push(cd->idctx->my_certs, cd->cred->cert);
|
|
|
d738b9 |
- free(cd->idctx->identity);
|
|
|
d738b9 |
+ if (idctx->my_certs != NULL)
|
|
|
d738b9 |
+ sk_X509_pop_free(idctx->my_certs, X509_free);
|
|
|
d738b9 |
+ idctx->my_certs = sk_X509_new_null();
|
|
|
d738b9 |
+ sk_X509_push(idctx->my_certs, ci->cert);
|
|
|
d738b9 |
+ free(idctx->identity);
|
|
|
d738b9 |
/* hang on to the selected credential name */
|
|
|
d738b9 |
- if (cd->idctx->creds[cd->index]->name != NULL)
|
|
|
d738b9 |
- cd->idctx->identity = strdup(cd->idctx->creds[cd->index]->name);
|
|
|
d738b9 |
+ if (ci->name != NULL)
|
|
|
d738b9 |
+ idctx->identity = strdup(ci->name);
|
|
|
d738b9 |
else
|
|
|
d738b9 |
- cd->idctx->identity = NULL;
|
|
|
d738b9 |
- cd->idctx->creds[cd->index]->cert = NULL; /* Don't free it twice */
|
|
|
d738b9 |
- cd->idctx->cert_index = 0;
|
|
|
d738b9 |
+ idctx->identity = NULL;
|
|
|
d738b9 |
|
|
|
d738b9 |
- if (cd->idctx->pkcs11_method != 1) {
|
|
|
d738b9 |
- cd->idctx->my_key = cd->cred->key;
|
|
|
d738b9 |
- cd->idctx->creds[cd->index]->key = NULL; /* Don't free it twice */
|
|
|
d738b9 |
+ ci->cert = NULL; /* Don't free it twice */
|
|
|
d738b9 |
+ idctx->cert_index = 0;
|
|
|
d738b9 |
+ if (idctx->pkcs11_method != 1) {
|
|
|
d738b9 |
+ idctx->my_key = ci->key;
|
|
|
d738b9 |
+ ci->key = NULL; /* Don't free it twice */
|
|
|
d738b9 |
}
|
|
|
d738b9 |
#ifndef WITHOUT_PKCS11
|
|
|
d738b9 |
else {
|
|
|
d738b9 |
- cd->idctx->cert_id = cd->cred->cert_id;
|
|
|
d738b9 |
- cd->idctx->creds[cd->index]->cert_id = NULL; /* Don't free it twice */
|
|
|
d738b9 |
- cd->idctx->cert_id_len = cd->cred->cert_id_len;
|
|
|
d738b9 |
+ idctx->cert_id = ci->cert_id;
|
|
|
d738b9 |
+ ci->cert_id = NULL; /* Don't free it twice */
|
|
|
d738b9 |
+ idctx->cert_id_len = ci->cert_id_len;
|
|
|
d738b9 |
}
|
|
|
d738b9 |
#endif
|
|
|
d738b9 |
return 0;
|
|
|
d738b9 |
@@ -5380,15 +5312,12 @@ crypto_cert_select_default(krb5_context context,
|
|
|
d738b9 |
pkinit_identity_crypto_context id_cryptoctx)
|
|
|
d738b9 |
{
|
|
|
d738b9 |
krb5_error_code retval;
|
|
|
d738b9 |
- int cert_count = 0;
|
|
|
d738b9 |
+ int cert_count;
|
|
|
d738b9 |
|
|
|
d738b9 |
- retval = crypto_cert_get_count(context, plg_cryptoctx, req_cryptoctx,
|
|
|
d738b9 |
- id_cryptoctx, &cert_count);
|
|
|
d738b9 |
- if (retval) {
|
|
|
d738b9 |
- pkiDebug("%s: crypto_cert_get_count error %d, %s\n",
|
|
|
d738b9 |
- __FUNCTION__, retval, error_message(retval));
|
|
|
d738b9 |
+ retval = crypto_cert_get_count(id_cryptoctx, &cert_count);
|
|
|
d738b9 |
+ if (retval)
|
|
|
d738b9 |
goto errout;
|
|
|
d738b9 |
- }
|
|
|
d738b9 |
+
|
|
|
d738b9 |
if (cert_count != 1) {
|
|
|
d738b9 |
TRACE_PKINIT_NO_DEFAULT_CERT(context, cert_count);
|
|
|
d738b9 |
retval = EINVAL;
|
|
|
d738b9 |
diff --git a/src/plugins/preauth/pkinit/pkinit_crypto_openssl.h b/src/plugins/preauth/pkinit/pkinit_crypto_openssl.h
|
|
|
d738b9 |
index 2fe357c5e..7411348fa 100644
|
|
|
d738b9 |
--- a/src/plugins/preauth/pkinit/pkinit_crypto_openssl.h
|
|
|
d738b9 |
+++ b/src/plugins/preauth/pkinit/pkinit_crypto_openssl.h
|
|
|
d738b9 |
@@ -115,23 +115,4 @@ struct _pkinit_req_crypto_context {
|
|
|
d738b9 |
DH *dh;
|
|
|
d738b9 |
};
|
|
|
d738b9 |
|
|
|
d738b9 |
-#define CERT_MAGIC 0x53534c43
|
|
|
d738b9 |
-struct _pkinit_cert_data {
|
|
|
d738b9 |
- unsigned int magic;
|
|
|
d738b9 |
- pkinit_plg_crypto_context plgctx;
|
|
|
d738b9 |
- pkinit_req_crypto_context reqctx;
|
|
|
d738b9 |
- pkinit_identity_crypto_context idctx;
|
|
|
d738b9 |
- pkinit_cred_info cred;
|
|
|
d738b9 |
- unsigned int index; /* Index of this cred in the creds[] array */
|
|
|
d738b9 |
-};
|
|
|
d738b9 |
-
|
|
|
d738b9 |
-#define ITER_MAGIC 0x53534c49
|
|
|
d738b9 |
-struct _pkinit_cert_iter_data {
|
|
|
d738b9 |
- unsigned int magic;
|
|
|
d738b9 |
- pkinit_plg_crypto_context plgctx;
|
|
|
d738b9 |
- pkinit_req_crypto_context reqctx;
|
|
|
d738b9 |
- pkinit_identity_crypto_context idctx;
|
|
|
d738b9 |
- unsigned int index;
|
|
|
d738b9 |
-};
|
|
|
d738b9 |
-
|
|
|
d738b9 |
#endif /* _PKINIT_CRYPTO_OPENSSL_H */
|
|
|
d738b9 |
diff --git a/src/plugins/preauth/pkinit/pkinit_matching.c b/src/plugins/preauth/pkinit/pkinit_matching.c
|
|
|
d738b9 |
index cad4c2b9a..d6775dc4f 100644
|
|
|
d738b9 |
--- a/src/plugins/preauth/pkinit/pkinit_matching.c
|
|
|
d738b9 |
+++ b/src/plugins/preauth/pkinit/pkinit_matching.c
|
|
|
d738b9 |
@@ -544,7 +544,7 @@ check_all_certs(krb5_context context,
|
|
|
d738b9 |
rule_set *rs, /* rule to check */
|
|
|
d738b9 |
pkinit_cert_matching_data **matchdata,
|
|
|
d738b9 |
int *match_found,
|
|
|
d738b9 |
- pkinit_cert_matching_data **matching_cert)
|
|
|
d738b9 |
+ size_t *match_index)
|
|
|
d738b9 |
{
|
|
|
d738b9 |
krb5_error_code retval;
|
|
|
d738b9 |
pkinit_cert_matching_data *md;
|
|
|
d738b9 |
@@ -553,12 +553,12 @@ check_all_certs(krb5_context context,
|
|
|
d738b9 |
int total_cert_matches = 0;
|
|
|
d738b9 |
rule_component *rc;
|
|
|
d738b9 |
int certs_checked = 0;
|
|
|
d738b9 |
- pkinit_cert_matching_data *save_match = NULL;
|
|
|
d738b9 |
+ size_t save_index = 0;
|
|
|
d738b9 |
|
|
|
d738b9 |
- if (match_found == NULL || matching_cert == NULL)
|
|
|
d738b9 |
+ if (match_found == NULL || match_index == NULL)
|
|
|
d738b9 |
return EINVAL;
|
|
|
d738b9 |
|
|
|
d738b9 |
- *matching_cert = NULL;
|
|
|
d738b9 |
+ *match_index = 0;
|
|
|
d738b9 |
*match_found = 0;
|
|
|
d738b9 |
|
|
|
d738b9 |
pkiDebug("%s: matching rule relation is %s with %d components\n",
|
|
|
d738b9 |
@@ -590,7 +590,7 @@ check_all_certs(krb5_context context,
|
|
|
d738b9 |
pkiDebug("%s: cert matches rule (OR relation)\n",
|
|
|
d738b9 |
__FUNCTION__);
|
|
|
d738b9 |
total_cert_matches++;
|
|
|
d738b9 |
- save_match = md;
|
|
|
d738b9 |
+ save_index = i;
|
|
|
d738b9 |
goto nextcert;
|
|
|
d738b9 |
}
|
|
|
d738b9 |
if (!comp_match && rs->relation == relation_and) {
|
|
|
d738b9 |
@@ -602,7 +602,7 @@ check_all_certs(krb5_context context,
|
|
|
d738b9 |
if (rc == NULL && comp_match) {
|
|
|
d738b9 |
pkiDebug("%s: cert matches rule (AND relation)\n", __FUNCTION__);
|
|
|
d738b9 |
total_cert_matches++;
|
|
|
d738b9 |
- save_match = md;
|
|
|
d738b9 |
+ save_index = i;
|
|
|
d738b9 |
}
|
|
|
d738b9 |
nextcert:
|
|
|
d738b9 |
continue;
|
|
|
d738b9 |
@@ -611,7 +611,7 @@ check_all_certs(krb5_context context,
|
|
|
d738b9 |
__FUNCTION__, certs_checked, total_cert_matches);
|
|
|
d738b9 |
if (total_cert_matches == 1) {
|
|
|
d738b9 |
*match_found = 1;
|
|
|
d738b9 |
- *matching_cert = save_match;
|
|
|
d738b9 |
+ *match_index = save_index;
|
|
|
d738b9 |
}
|
|
|
d738b9 |
|
|
|
d738b9 |
retval = 0;
|
|
|
d738b9 |
@@ -621,111 +621,6 @@ check_all_certs(krb5_context context,
|
|
|
d738b9 |
return retval;
|
|
|
d738b9 |
}
|
|
|
d738b9 |
|
|
|
d738b9 |
-static krb5_error_code
|
|
|
d738b9 |
-free_all_cert_matching_data(krb5_context context,
|
|
|
d738b9 |
- pkinit_cert_matching_data **matchdata)
|
|
|
d738b9 |
-{
|
|
|
d738b9 |
- krb5_error_code retval;
|
|
|
d738b9 |
- pkinit_cert_matching_data *md;
|
|
|
d738b9 |
- int i;
|
|
|
d738b9 |
-
|
|
|
d738b9 |
- if (matchdata == NULL)
|
|
|
d738b9 |
- return EINVAL;
|
|
|
d738b9 |
-
|
|
|
d738b9 |
- for (i = 0, md = matchdata[i]; md != NULL; md = matchdata[++i]) {
|
|
|
d738b9 |
- pkinit_cert_handle ch = md->ch;
|
|
|
d738b9 |
- retval = crypto_cert_free_matching_data(context, md);
|
|
|
d738b9 |
- if (retval) {
|
|
|
d738b9 |
- pkiDebug("%s: crypto_cert_free_matching_data error %d, %s\n",
|
|
|
d738b9 |
- __FUNCTION__, retval, error_message(retval));
|
|
|
d738b9 |
- goto cleanup;
|
|
|
d738b9 |
- }
|
|
|
d738b9 |
- retval = crypto_cert_release(context, ch);
|
|
|
d738b9 |
- if (retval) {
|
|
|
d738b9 |
- pkiDebug("%s: crypto_cert_release error %d, %s\n",
|
|
|
d738b9 |
- __FUNCTION__, retval, error_message(retval));
|
|
|
d738b9 |
- goto cleanup;
|
|
|
d738b9 |
- }
|
|
|
d738b9 |
- }
|
|
|
d738b9 |
- free(matchdata);
|
|
|
d738b9 |
- retval = 0;
|
|
|
d738b9 |
-
|
|
|
d738b9 |
-cleanup:
|
|
|
d738b9 |
- return retval;
|
|
|
d738b9 |
-}
|
|
|
d738b9 |
-
|
|
|
d738b9 |
-static krb5_error_code
|
|
|
d738b9 |
-obtain_all_cert_matching_data(krb5_context context,
|
|
|
d738b9 |
- pkinit_plg_crypto_context plg_cryptoctx,
|
|
|
d738b9 |
- pkinit_req_crypto_context req_cryptoctx,
|
|
|
d738b9 |
- pkinit_identity_crypto_context id_cryptoctx,
|
|
|
d738b9 |
- pkinit_cert_matching_data ***all_matching_data)
|
|
|
d738b9 |
-{
|
|
|
d738b9 |
- krb5_error_code retval;
|
|
|
d738b9 |
- int i, cert_count;
|
|
|
d738b9 |
- pkinit_cert_iter_handle ih = NULL;
|
|
|
d738b9 |
- pkinit_cert_handle ch;
|
|
|
d738b9 |
- pkinit_cert_matching_data **matchdata = NULL;
|
|
|
d738b9 |
-
|
|
|
d738b9 |
- retval = crypto_cert_get_count(context, plg_cryptoctx, req_cryptoctx,
|
|
|
d738b9 |
- id_cryptoctx, &cert_count);
|
|
|
d738b9 |
- if (retval) {
|
|
|
d738b9 |
- pkiDebug("%s: crypto_cert_get_count error %d, %s\n",
|
|
|
d738b9 |
- __FUNCTION__, retval, error_message(retval));
|
|
|
d738b9 |
- goto cleanup;
|
|
|
d738b9 |
- }
|
|
|
d738b9 |
-
|
|
|
d738b9 |
- pkiDebug("%s: crypto_cert_get_count says there are %d certs\n",
|
|
|
d738b9 |
- __FUNCTION__, cert_count);
|
|
|
d738b9 |
-
|
|
|
d738b9 |
- matchdata = calloc((size_t)cert_count + 1, sizeof(*matchdata));
|
|
|
d738b9 |
- if (matchdata == NULL)
|
|
|
d738b9 |
- return ENOMEM;
|
|
|
d738b9 |
-
|
|
|
d738b9 |
- retval = crypto_cert_iteration_begin(context, plg_cryptoctx, req_cryptoctx,
|
|
|
d738b9 |
- id_cryptoctx, &ih;;
|
|
|
d738b9 |
- if (retval) {
|
|
|
d738b9 |
- pkiDebug("%s: crypto_cert_iteration_begin returned %d, %s\n",
|
|
|
d738b9 |
- __FUNCTION__, retval, error_message(retval));
|
|
|
d738b9 |
- goto cleanup;
|
|
|
d738b9 |
- }
|
|
|
d738b9 |
-
|
|
|
d738b9 |
- for (i = 0; i < cert_count; i++) {
|
|
|
d738b9 |
- retval = crypto_cert_iteration_next(context, ih, &ch);
|
|
|
d738b9 |
- if (retval) {
|
|
|
d738b9 |
- if (retval == PKINIT_ITER_NO_MORE)
|
|
|
d738b9 |
- pkiDebug("%s: We thought there were %d certs, but "
|
|
|
d738b9 |
- "crypto_cert_iteration_next stopped after %d?\n",
|
|
|
d738b9 |
- __FUNCTION__, cert_count, i);
|
|
|
d738b9 |
- else
|
|
|
d738b9 |
- pkiDebug("%s: crypto_cert_iteration_next error %d, %s\n",
|
|
|
d738b9 |
- __FUNCTION__, retval, error_message(retval));
|
|
|
d738b9 |
- goto cleanup;
|
|
|
d738b9 |
- }
|
|
|
d738b9 |
-
|
|
|
d738b9 |
- retval = crypto_cert_get_matching_data(context, ch, &matchdata[i]);
|
|
|
d738b9 |
- if (retval) {
|
|
|
d738b9 |
- pkiDebug("%s: crypto_cert_get_matching_data error %d, %s\n",
|
|
|
d738b9 |
- __FUNCTION__, retval, error_message(retval));
|
|
|
d738b9 |
- goto cleanup;
|
|
|
d738b9 |
- }
|
|
|
d738b9 |
-
|
|
|
d738b9 |
- }
|
|
|
d738b9 |
-
|
|
|
d738b9 |
- *all_matching_data = matchdata;
|
|
|
d738b9 |
- retval = 0;
|
|
|
d738b9 |
-cleanup:
|
|
|
d738b9 |
- if (ih != NULL)
|
|
|
d738b9 |
- crypto_cert_iteration_end(context, ih);
|
|
|
d738b9 |
- if (retval) {
|
|
|
d738b9 |
- if (matchdata != NULL)
|
|
|
d738b9 |
- free_all_cert_matching_data(context, matchdata);
|
|
|
d738b9 |
- }
|
|
|
d738b9 |
- pkiDebug("%s: returning %d, certinfo %p\n",
|
|
|
d738b9 |
- __FUNCTION__, retval, *all_matching_data);
|
|
|
d738b9 |
- return retval;
|
|
|
d738b9 |
-}
|
|
|
d738b9 |
-
|
|
|
d738b9 |
krb5_error_code
|
|
|
d738b9 |
pkinit_cert_matching(krb5_context context,
|
|
|
d738b9 |
pkinit_plg_crypto_context plg_cryptoctx,
|
|
|
d738b9 |
@@ -740,7 +635,7 @@ pkinit_cert_matching(krb5_context context,
|
|
|
d738b9 |
rule_set *rs = NULL;
|
|
|
d738b9 |
int match_found = 0;
|
|
|
d738b9 |
pkinit_cert_matching_data **matchdata = NULL;
|
|
|
d738b9 |
- pkinit_cert_matching_data *the_matching_cert = NULL;
|
|
|
d738b9 |
+ size_t match_index = 0;
|
|
|
d738b9 |
|
|
|
d738b9 |
/* If no matching rules, select the default cert and we're done */
|
|
|
d738b9 |
pkinit_libdefault_strings(context, krb5_princ_realm(context, princ),
|
|
|
d738b9 |
@@ -777,7 +672,7 @@ pkinit_cert_matching(krb5_context context,
|
|
|
d738b9 |
* until we are done.
|
|
|
d738b9 |
*/
|
|
|
d738b9 |
if (matchdata == NULL) {
|
|
|
d738b9 |
- retval = obtain_all_cert_matching_data(context, plg_cryptoctx,
|
|
|
d738b9 |
+ retval = crypto_cert_get_matching_data(context, plg_cryptoctx,
|
|
|
d738b9 |
req_cryptoctx, id_cryptoctx,
|
|
|
d738b9 |
&matchdata);
|
|
|
d738b9 |
if (retval || matchdata == NULL) {
|
|
|
d738b9 |
@@ -790,7 +685,7 @@ pkinit_cert_matching(krb5_context context,
|
|
|
d738b9 |
|
|
|
d738b9 |
retval = check_all_certs(context, plg_cryptoctx, req_cryptoctx,
|
|
|
d738b9 |
id_cryptoctx, princ, rs, matchdata,
|
|
|
d738b9 |
- &match_found, &the_matching_cert);
|
|
|
d738b9 |
+ &match_found, &match_index);
|
|
|
d738b9 |
if (retval) {
|
|
|
d738b9 |
pkiDebug("%s: Error %d, checking certs against rule '%s'\n",
|
|
|
d738b9 |
__FUNCTION__, retval, rules[x]);
|
|
|
d738b9 |
@@ -803,9 +698,9 @@ pkinit_cert_matching(krb5_context context,
|
|
|
d738b9 |
}
|
|
|
d738b9 |
}
|
|
|
d738b9 |
|
|
|
d738b9 |
- if (match_found && the_matching_cert != NULL) {
|
|
|
d738b9 |
+ if (match_found) {
|
|
|
d738b9 |
pkiDebug("%s: Selecting the matching cert!\n", __FUNCTION__);
|
|
|
d738b9 |
- retval = crypto_cert_select(context, the_matching_cert);
|
|
|
d738b9 |
+ retval = crypto_cert_select(context, id_cryptoctx, match_index);
|
|
|
d738b9 |
if (retval) {
|
|
|
d738b9 |
pkiDebug("%s: crypto_cert_select error %d, %s\n",
|
|
|
d738b9 |
__FUNCTION__, retval, error_message(retval));
|
|
|
d738b9 |
@@ -818,12 +713,10 @@ pkinit_cert_matching(krb5_context context,
|
|
|
d738b9 |
}
|
|
|
d738b9 |
|
|
|
d738b9 |
retval = 0;
|
|
|
d738b9 |
+
|
|
|
d738b9 |
cleanup:
|
|
|
d738b9 |
- if (rules != NULL)
|
|
|
d738b9 |
- profile_free_list(rules);
|
|
|
d738b9 |
- if (rs != NULL)
|
|
|
d738b9 |
- free_rule_set(context, rs);
|
|
|
d738b9 |
- if (matchdata != NULL)
|
|
|
d738b9 |
- free_all_cert_matching_data(context, matchdata);
|
|
|
d738b9 |
+ profile_free_list(rules);
|
|
|
d738b9 |
+ free_rule_set(context, rs);
|
|
|
d738b9 |
+ crypto_cert_free_matching_data_list(context, matchdata);
|
|
|
d738b9 |
return retval;
|
|
|
d738b9 |
}
|