Add matching on EKU, validate EKUs, add hxtool matching glue, add check. Adapted from pach from Tim Miller of Mitre
git-svn-id: svn://svn.h5l.se/heimdal/trunk/heimdal@22538 ec53bebd-3082-4978-b11e-865c3cabbd6b
This commit is contained in:
@@ -1,3 +1,8 @@
|
|||||||
|
2008-01-27 Love H<>rnquist <20>strand <lha@it.su.se>
|
||||||
|
|
||||||
|
* Add matching on EKU, validate EKUs, add hxtool matching glue,
|
||||||
|
add check. Adapted from pach from Tim Miller of Mitre
|
||||||
|
|
||||||
2008-01-21 Love H<>rnquist <20>strand <lha@it.su.se>
|
2008-01-21 Love H<>rnquist <20>strand <lha@it.su.se>
|
||||||
|
|
||||||
* test_soft_pkcs11.c: use func for more C_ functions.
|
* test_soft_pkcs11.c: use func for more C_ functions.
|
||||||
|
@@ -2609,6 +2609,40 @@ hx509_query_match_friendly_name(hx509_query *q, const char *name)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set the query controller to require an specific EKU (extended key
|
||||||
|
* usage).
|
||||||
|
*
|
||||||
|
* @param q a hx509 query controller.
|
||||||
|
* @param eku an EKU to match on
|
||||||
|
*
|
||||||
|
* @return An hx509 error code, see hx509_get_error_string().
|
||||||
|
*
|
||||||
|
* @ingroup hx509_cert
|
||||||
|
*/
|
||||||
|
|
||||||
|
int
|
||||||
|
hx509_query_match_eku(hx509_query *q, const heim_oid *eku)
|
||||||
|
{
|
||||||
|
int ret;
|
||||||
|
|
||||||
|
if (q->eku) {
|
||||||
|
der_free_oid(q->eku);
|
||||||
|
} else {
|
||||||
|
q->eku = calloc(1, sizeof(*q->eku));
|
||||||
|
if (q->eku == NULL)
|
||||||
|
return ENOMEM;
|
||||||
|
}
|
||||||
|
ret = der_copy_oid(eku, q->eku);
|
||||||
|
if (ret) {
|
||||||
|
free(q->eku);
|
||||||
|
q->eku = NULL;
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
q->match |= HX509_QUERY_MATCH_EKU;
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set the query controller to match using a specific match function.
|
* Set the query controller to match using a specific match function.
|
||||||
*
|
*
|
||||||
@@ -2648,20 +2682,24 @@ hx509_query_match_cmp_func(hx509_query *q,
|
|||||||
void
|
void
|
||||||
hx509_query_free(hx509_context context, hx509_query *q)
|
hx509_query_free(hx509_context context, hx509_query *q)
|
||||||
{
|
{
|
||||||
|
if (q == NULL)
|
||||||
|
return;
|
||||||
|
|
||||||
if (q->serial) {
|
if (q->serial) {
|
||||||
der_free_heim_integer(q->serial);
|
der_free_heim_integer(q->serial);
|
||||||
free(q->serial);
|
free(q->serial);
|
||||||
q->serial = NULL;
|
|
||||||
}
|
}
|
||||||
if (q->issuer_name) {
|
if (q->issuer_name) {
|
||||||
free_Name(q->issuer_name);
|
free_Name(q->issuer_name);
|
||||||
free(q->issuer_name);
|
free(q->issuer_name);
|
||||||
q->issuer_name = NULL;
|
|
||||||
}
|
}
|
||||||
if (q) {
|
if (q->eku) {
|
||||||
|
der_free_oid(q->eku);
|
||||||
|
free(q->eku);
|
||||||
|
}
|
||||||
|
if (q->friendlyname)
|
||||||
free(q->friendlyname);
|
free(q->friendlyname);
|
||||||
memset(q, 0, sizeof(*q));
|
memset(q, 0, sizeof(*q));
|
||||||
}
|
|
||||||
free(q);
|
free(q);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -2790,6 +2828,11 @@ _hx509_query_match_cert(hx509_context context, const hx509_query *q, hx509_cert
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* If an EKU is required, check the cert for it. */
|
||||||
|
if ((q->match & HX509_QUERY_MATCH_EKU) &&
|
||||||
|
hx509_cert_check_eku(context, cert, q->eku, 0))
|
||||||
|
return 0;
|
||||||
|
|
||||||
if (q->match & ~HX509_QUERY_MASK)
|
if (q->match & ~HX509_QUERY_MASK)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
|
@@ -128,7 +128,8 @@ struct hx509_query_data {
|
|||||||
#define HX509_QUERY_MATCH_FUNCTION 0x080000
|
#define HX509_QUERY_MATCH_FUNCTION 0x080000
|
||||||
#define HX509_QUERY_MATCH_KEY_HASH_SHA1 0x100000
|
#define HX509_QUERY_MATCH_KEY_HASH_SHA1 0x100000
|
||||||
#define HX509_QUERY_MATCH_TIME 0x200000
|
#define HX509_QUERY_MATCH_TIME 0x200000
|
||||||
#define HX509_QUERY_MASK 0x3fffff
|
#define HX509_QUERY_MATCH_EKU 0x400000
|
||||||
|
#define HX509_QUERY_MASK 0x7fffff
|
||||||
Certificate *subject;
|
Certificate *subject;
|
||||||
Certificate *certificate;
|
Certificate *certificate;
|
||||||
heim_integer *serial;
|
heim_integer *serial;
|
||||||
@@ -142,6 +143,7 @@ struct hx509_query_data {
|
|||||||
void *cmp_func_ctx;
|
void *cmp_func_ctx;
|
||||||
heim_octet_string *keyhash_sha1;
|
heim_octet_string *keyhash_sha1;
|
||||||
time_t timenow;
|
time_t timenow;
|
||||||
|
heim_oid *eku;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct hx509_keyset_ops {
|
struct hx509_keyset_ops {
|
||||||
|
@@ -437,6 +437,12 @@ command = {
|
|||||||
argument = "name"
|
argument = "name"
|
||||||
help = "match on friendly name"
|
help = "match on friendly name"
|
||||||
}
|
}
|
||||||
|
option = {
|
||||||
|
long = "eku"
|
||||||
|
type = "string"
|
||||||
|
argument = "oid-string"
|
||||||
|
help = "match on EKU"
|
||||||
|
}
|
||||||
option = {
|
option = {
|
||||||
long = "keyEncipherment"
|
long = "keyEncipherment"
|
||||||
type = "flag"
|
type = "flag"
|
||||||
|
@@ -885,6 +885,17 @@ query(struct query_options *opt, int argc, char **argv)
|
|||||||
if (opt->friendlyname_string)
|
if (opt->friendlyname_string)
|
||||||
hx509_query_match_friendly_name(q, opt->friendlyname_string);
|
hx509_query_match_friendly_name(q, opt->friendlyname_string);
|
||||||
|
|
||||||
|
if (opt->eku_string) {
|
||||||
|
heim_oid oid;
|
||||||
|
|
||||||
|
parse_oid(opt->eku_string, NULL, &oid);
|
||||||
|
|
||||||
|
ret = hx509_query_match_eku(q, &oid);
|
||||||
|
if (ret)
|
||||||
|
errx(1, "hx509_query_match_eku: %d", ret);
|
||||||
|
der_free_oid(&oid);
|
||||||
|
}
|
||||||
|
|
||||||
if (opt->private_key_flag)
|
if (opt->private_key_flag)
|
||||||
hx509_query_match_option(q, HX509_QUERY_OPTION_PRIVATE_KEY);
|
hx509_query_match_option(q, HX509_QUERY_OPTION_PRIVATE_KEY);
|
||||||
|
|
||||||
|
@@ -335,9 +335,6 @@ check_authorityKeyIdentifier(hx509_validate_ctx ctx,
|
|||||||
status->haveAKI = 1;
|
status->haveAKI = 1;
|
||||||
check_Null(ctx, status, cf, e);
|
check_Null(ctx, status, cf, e);
|
||||||
|
|
||||||
status->haveSKI = 1;
|
|
||||||
check_Null(ctx, status, cf, e);
|
|
||||||
|
|
||||||
ret = decode_AuthorityKeyIdentifier(e->extnValue.data,
|
ret = decode_AuthorityKeyIdentifier(e->extnValue.data,
|
||||||
e->extnValue.length,
|
e->extnValue.length,
|
||||||
&ai, &size);
|
&ai, &size);
|
||||||
@@ -365,6 +362,56 @@ check_authorityKeyIdentifier(hx509_validate_ctx ctx,
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int
|
||||||
|
check_extKeyUsage(hx509_validate_ctx ctx,
|
||||||
|
struct cert_status *status,
|
||||||
|
enum critical_flag cf,
|
||||||
|
const Extension *e)
|
||||||
|
{
|
||||||
|
ExtKeyUsage eku;
|
||||||
|
size_t size, i;
|
||||||
|
int ret;
|
||||||
|
|
||||||
|
check_Null(ctx, status, cf, e);
|
||||||
|
|
||||||
|
ret = decode_ExtKeyUsage(e->extnValue.data,
|
||||||
|
e->extnValue.length,
|
||||||
|
&eku, &size);
|
||||||
|
if (ret) {
|
||||||
|
validate_print(ctx, HX509_VALIDATE_F_VALIDATE,
|
||||||
|
"Decoding ExtKeyUsage failed: %d", ret);
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
if (size != e->extnValue.length) {
|
||||||
|
validate_print(ctx, HX509_VALIDATE_F_VALIDATE,
|
||||||
|
"Padding data in EKU");
|
||||||
|
free_ExtKeyUsage(&eku);
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
if (eku.len == 0) {
|
||||||
|
validate_print(ctx, HX509_VALIDATE_F_VALIDATE,
|
||||||
|
"ExtKeyUsage length is 0");
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
for (i = 0; i < eku.len; i++) {
|
||||||
|
char *str;
|
||||||
|
ret = der_print_heim_oid (&eku.val[i], '.', &str);
|
||||||
|
if (ret) {
|
||||||
|
validate_print(ctx, HX509_VALIDATE_F_VALIDATE,
|
||||||
|
"\tEKU: failed to print oid %d", i);
|
||||||
|
free_ExtKeyUsage(&eku);
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
validate_print(ctx, HX509_VALIDATE_F_VERBOSE,
|
||||||
|
"\teku-%d: %s\n", i, str);;
|
||||||
|
free(str);
|
||||||
|
}
|
||||||
|
|
||||||
|
free_ExtKeyUsage(&eku);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
static int
|
static int
|
||||||
check_pkinit_san(hx509_validate_ctx ctx, heim_any *a)
|
check_pkinit_san(hx509_validate_ctx ctx, heim_any *a)
|
||||||
@@ -731,7 +778,7 @@ struct {
|
|||||||
{ ext(policyMappings, Null), M_N_C },
|
{ ext(policyMappings, Null), M_N_C },
|
||||||
{ ext(authorityKeyIdentifier, authorityKeyIdentifier), M_N_C },
|
{ ext(authorityKeyIdentifier, authorityKeyIdentifier), M_N_C },
|
||||||
{ ext(policyConstraints, Null), D_C },
|
{ ext(policyConstraints, Null), D_C },
|
||||||
{ ext(extKeyUsage, Null), D_C },
|
{ ext(extKeyUsage, extKeyUsage), D_C },
|
||||||
{ ext(freshestCRL, Null), M_N_C },
|
{ ext(freshestCRL, Null), M_N_C },
|
||||||
{ ext(inhibitAnyPolicy, Null), M_C },
|
{ ext(inhibitAnyPolicy, Null), M_C },
|
||||||
#undef ext
|
#undef ext
|
||||||
|
@@ -44,8 +44,15 @@ hxtool="${TESTS_ENVIRONMENT} ./hxtool ${stat}"
|
|||||||
echo "try printing"
|
echo "try printing"
|
||||||
${hxtool} print \
|
${hxtool} print \
|
||||||
--pass=PASS:foobar \
|
--pass=PASS:foobar \
|
||||||
|
--info --content \
|
||||||
PKCS12:$srcdir/data/test.p12 >/dev/null 2>/dev/null || exit 1
|
PKCS12:$srcdir/data/test.p12 >/dev/null 2>/dev/null || exit 1
|
||||||
|
|
||||||
|
echo "try printing"
|
||||||
|
${hxtool} print \
|
||||||
|
--pass=PASS:foobar \
|
||||||
|
--info --content \
|
||||||
|
FILE:$srcdir/data/kdc.crt || exit 1
|
||||||
|
|
||||||
${hxtool} print \
|
${hxtool} print \
|
||||||
--pass=PASS:foobar \
|
--pass=PASS:foobar \
|
||||||
--info \
|
--info \
|
||||||
@@ -63,6 +70,16 @@ ${hxtool} query \
|
|||||||
--friendlyname=friendlyname-test-not \
|
--friendlyname=friendlyname-test-not \
|
||||||
PKCS12:$srcdir/data/test.p12 >/dev/null 2>/dev/null && exit 1
|
PKCS12:$srcdir/data/test.p12 >/dev/null 2>/dev/null && exit 1
|
||||||
|
|
||||||
|
echo "make sure entry is found (eku)"
|
||||||
|
${hxtool} query \
|
||||||
|
--eku=1.3.6.1.5.2.3.5 \
|
||||||
|
FILE:$srcdir/data/kdc.crt >/dev/null 2>/dev/null || exit 1
|
||||||
|
|
||||||
|
echo "make sure entry is not found (eku)"
|
||||||
|
${hxtool} query \
|
||||||
|
--eku=1.3.6.1.5.2.3.6 \
|
||||||
|
FILE:$srcdir/data/kdc.crt >/dev/null 2>/dev/null && exit 1
|
||||||
|
|
||||||
echo "make sure entry is found (friendlyname, no-pw)"
|
echo "make sure entry is found (friendlyname, no-pw)"
|
||||||
${hxtool} query \
|
${hxtool} query \
|
||||||
--friendlyname=friendlyname-cert \
|
--friendlyname=friendlyname-cert \
|
||||||
|
@@ -139,6 +139,7 @@ HEIMDAL_X509_1.0 {
|
|||||||
hx509_query_alloc;
|
hx509_query_alloc;
|
||||||
hx509_query_free;
|
hx509_query_free;
|
||||||
hx509_query_match_cmp_func;
|
hx509_query_match_cmp_func;
|
||||||
|
hx509_query_match_eku;
|
||||||
hx509_query_match_friendly_name;
|
hx509_query_match_friendly_name;
|
||||||
hx509_query_match_issuer_serial;
|
hx509_query_match_issuer_serial;
|
||||||
hx509_query_match_option;
|
hx509_query_match_option;
|
||||||
|
Reference in New Issue
Block a user