Clairfy and make proxy cert handling work for multiple levels, before

it was too restrictive. More helpful error message.


git-svn-id: svn://svn.h5l.se/heimdal/trunk/heimdal@19283 ec53bebd-3082-4978-b11e-865c3cabbd6b
This commit is contained in:
Love Hörnquist Åstrand
2006-12-07 23:39:26 +00:00
parent a55d8abf5c
commit 71e4dc1497

View File

@@ -1458,38 +1458,45 @@ hx509_verify_path(hx509_context context,
/* XXX make constants for keyusage */ /* XXX make constants for keyusage */
ret = check_key_usage(context, c, 1 << 5, ret = check_key_usage(context, c, 1 << 5,
REQUIRE_RFC3280(ctx) ? TRUE : FALSE); REQUIRE_RFC3280(ctx) ? TRUE : FALSE);
if (ret) if (ret) {
hx509_set_error_string(context, HX509_ERROR_APPEND, ret,
"Key usage missing from CA certificate");
goto out; goto out;
}
break; break;
case PROXY_CERT: { case PROXY_CERT: {
ProxyCertInfo info; ProxyCertInfo info;
if (is_proxy_cert(context, c, &info) == 0) { if (is_proxy_cert(context, c, &info) == 0) {
Name name;
int j; int j;
if (info.pCPathLenConstraint != NULL && if (info.pCPathLenConstraint != NULL &&
*info.pCPathLenConstraint < i + 1) *info.pCPathLenConstraint < i + 1)
{ {
free_ProxyCertInfo(&info); free_ProxyCertInfo(&info);
hx509_clear_error_string(context);
ret = HX509_PATH_TOO_LONG; ret = HX509_PATH_TOO_LONG;
hx509_set_error_string(context, 0, ret,
"Proxy certificate chain "
"longer then allowed");
goto out; goto out;
} }
free_ProxyCertInfo(&info);
j = 0; j = 0;
if (find_extension(c, oid_id_x509_ce_subjectAltName(), &j)) { if (find_extension(c, oid_id_x509_ce_subjectAltName(), &j)) {
free_ProxyCertInfo(&info);
hx509_clear_error_string(context);
ret = HX509_PROXY_CERT_INVALID; ret = HX509_PROXY_CERT_INVALID;
hx509_set_error_string(context, 0, ret,
"Proxy certificate have explicity "
"forbidden subjectAltName");
goto out; goto out;
} }
j = 0; j = 0;
if (find_extension(c, oid_id_x509_ce_issuerAltName(), &j)) { if (find_extension(c, oid_id_x509_ce_issuerAltName(), &j)) {
free_ProxyCertInfo(&info);
hx509_clear_error_string(context);
ret = HX509_PROXY_CERT_INVALID; ret = HX509_PROXY_CERT_INVALID;
hx509_set_error_string(context, 0, ret,
"Proxy certificate have explicity "
"forbidden issuerAltName");
goto out; goto out;
} }
@@ -1500,72 +1507,85 @@ hx509_verify_path(hx509_context context,
* then check with the EE cert when we get to it. * then check with the EE cert when we get to it.
*/ */
ret = copy_Name(&c->tbsCertificate.subject, &name);
if (ret) {
hx509_clear_error_string(context);
free_ProxyCertInfo(&info);
goto out;
}
j = name.u.rdnSequence.len;
if (name.u.rdnSequence.len < 2
|| name.u.rdnSequence.val[j - 1].len > 1
|| der_heim_oid_cmp(&name.u.rdnSequence.val[j - 1].val[0].type,
oid_id_at_commonName()))
{
free_ProxyCertInfo(&info);
hx509_clear_error_string(context);
ret = HX509_PROXY_CERT_NAME_WRONG;
goto out;
}
free_RelativeDistinguishedName(&name.u.rdnSequence.val[j - 1]);
name.u.rdnSequence.len -= 1;
if (proxy_cert_depth) { if (proxy_cert_depth) {
ret = _hx509_name_cmp(&proxy_issuer, &name); ret = _hx509_name_cmp(&proxy_issuer, &c->tbsCertificate.subject);
free_Name(&name);
if (ret) { if (ret) {
free_ProxyCertInfo(&info);
hx509_clear_error_string(context);
ret = HX509_PROXY_CERT_NAME_WRONG; ret = HX509_PROXY_CERT_NAME_WRONG;
hx509_set_error_string(context, 0, ret,
"Base proxy name not right");
goto out; goto out;
} }
} else {
proxy_issuer = name;
} }
free_ProxyCertInfo(&info); free_Name(&proxy_issuer);
ret = copy_Name(&c->tbsCertificate.subject, &proxy_issuer);
if (ret) {
hx509_clear_error_string(context);
goto out;
}
j = proxy_issuer.u.rdnSequence.len;
if (proxy_issuer.u.rdnSequence.len < 2
|| proxy_issuer.u.rdnSequence.val[j - 1].len > 1
|| der_heim_oid_cmp(&proxy_issuer.u.rdnSequence.val[j - 1].val[0].type,
oid_id_at_commonName()))
{
ret = HX509_PROXY_CERT_NAME_WRONG;
hx509_set_error_string(context, 0, ret,
"Proxy name too short or "
"does not have Common name "
"at the top");
goto out;
}
free_RelativeDistinguishedName(&proxy_issuer.u.rdnSequence.val[j - 1]);
proxy_issuer.u.rdnSequence.len -= 1;
ret = _hx509_name_cmp(&proxy_issuer, &c->tbsCertificate.issuer);
if (ret != 0) {
ret = HX509_PROXY_CERT_NAME_WRONG;
hx509_set_error_string(context, 0, ret,
"Proxy issuer name not as expected");
goto out;
}
break; break;
} else { } else {
/* /*
* Now we are done with the proxy certificates, if * Now we are done with the proxy certificates, this
* there where any proxy certificates * cert was an EE cert and we we will fall though to
* (proxy_cert_depth > 0), check that the proxy issuer * EE checking below.
* matched proxy certificates subject.
*/ */
if (proxy_cert_depth) { type = EE_CERT;
ret = _hx509_name_cmp(&proxy_issuer, /* FALLTHOUGH */
&c->tbsCertificate.subject);
if (ret) {
ret = HX509_PROXY_CERT_NAME_WRONG;
hx509_clear_error_string(context);
goto out;
}
if (cert->basename)
hx509_name_free(&cert->basename);
ret = _hx509_name_from_Name(&proxy_issuer, &cert->basename);
if (ret) {
hx509_clear_error_string(context);
goto out;
}
}
} }
type = EE_CERT;
/* FALLTHOUGH */
} }
case EE_CERT: case EE_CERT:
/*
* If there where any proxy certificates in the chain
* (proxy_cert_depth > 0), check that the proxy issuer
* matched proxy certificates "base" subject.
*/
if (proxy_cert_depth) {
ret = _hx509_name_cmp(&proxy_issuer,
&c->tbsCertificate.subject);
if (ret) {
ret = HX509_PROXY_CERT_NAME_WRONG;
hx509_clear_error_string(context);
goto out;
}
if (cert->basename)
hx509_name_free(&cert->basename);
ret = _hx509_name_from_Name(&proxy_issuer, &cert->basename);
if (ret) {
hx509_clear_error_string(context);
goto out;
}
}
break; break;
} }