summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDr. Stephen Henson <steve@openssl.org>2008-07-13 14:25:36 +0000
committerDr. Stephen Henson <steve@openssl.org>2008-07-13 14:25:36 +0000
commitdb50661fce82a8f32bccaa7454be4041cbfad6d0 (patch)
tree761d5622052f34f9e45f906bff544792af5efc75
parentf9afd9f861bc7b5fc1ae32ceff15572ef73cbbec (diff)
X509 verification fixes.
Ignore self issued certificates when checking path length constraints. Duplicate OIDs in policy tree in case they are allocated. Use anyPolicy from certificate cache and not current tree level.
-rw-r--r--apps/cms.c9
-rw-r--r--crypto/x509/x509_vfy.c12
-rw-r--r--crypto/x509v3/pcy_data.c8
-rw-r--r--crypto/x509v3/pcy_tree.c7
-rw-r--r--crypto/x509v3/v3_purp.c3
-rw-r--r--crypto/x509v3/x509v3.h2
-rw-r--r--doc/apps/verify.pod14
7 files changed, 40 insertions, 15 deletions
diff --git a/apps/cms.c b/apps/cms.c
index 868de4e918..b7382a4f1f 100644
--- a/apps/cms.c
+++ b/apps/cms.c
@@ -95,6 +95,8 @@ static CMS_ReceiptRequest *make_receipt_request(STACK_OF(STRING) *rr_to,
#define SMIME_SIGN_RECEIPT (15 | SMIME_IP | SMIME_OP)
#define SMIME_VERIFY_RECEIPT (16 | SMIME_IP)
+int verify_err = 0;
+
int MAIN(int, char **);
int MAIN(int argc, char **argv)
@@ -118,6 +120,7 @@ int MAIN(int argc, char **argv)
BIO *in = NULL, *out = NULL, *indata = NULL, *rctin = NULL;
int badarg = 0;
int flags = CMS_DETACHED, noout = 0, print = 0;
+ int verify_retcode = 0;
int rr_print = 0, rr_allorfirst = -1;
STACK_OF(STRING) *rr_to = NULL, *rr_from = NULL;
CMS_ReceiptRequest *rr = NULL;
@@ -167,6 +170,8 @@ int MAIN(int argc, char **argv)
operation = SMIME_RESIGN;
else if (!strcmp (*args, "-verify"))
operation = SMIME_VERIFY;
+ else if (!strcmp (*args, "-verify_retcode"))
+ verify_retcode = 1;
else if (!strcmp(*args,"-verify_receipt"))
{
operation = SMIME_VERIFY_RECEIPT;
@@ -1077,6 +1082,8 @@ int MAIN(int argc, char **argv)
else
{
BIO_printf(bio_err, "Verification failure\n");
+ if (verify_retcode)
+ ret = verify_err + 32;
goto end;
}
if (signerfile)
@@ -1206,6 +1213,8 @@ static int cms_cb(int ok, X509_STORE_CTX *ctx)
error = X509_STORE_CTX_get_error(ctx);
+ verify_err = error;
+
if ((error != X509_V_ERR_NO_EXPLICIT_POLICY)
&& ((error != X509_V_OK) || (ok != 2)))
return ok;
diff --git a/crypto/x509/x509_vfy.c b/crypto/x509/x509_vfy.c
index 625af4fd9f..22d520b88a 100644
--- a/crypto/x509/x509_vfy.c
+++ b/crypto/x509/x509_vfy.c
@@ -396,7 +396,7 @@ static int check_chain_extensions(X509_STORE_CTX *ctx)
#ifdef OPENSSL_NO_CHAIN_VERIFY
return 1;
#else
- int i, ok=0, must_be_ca;
+ int i, ok=0, must_be_ca, plen = 0;
X509 *x;
int (*cb)(int xok,X509_STORE_CTX *xctx);
int proxy_path_length = 0;
@@ -497,9 +497,10 @@ static int check_chain_extensions(X509_STORE_CTX *ctx)
if (!ok) goto end;
}
}
- /* Check pathlen */
- if ((i > 1) && (x->ex_pathlen != -1)
- && (i > (x->ex_pathlen + proxy_path_length + 1)))
+ /* Check pathlen if not self issued */
+ if ((i > 1) && !(x->ex_flags & EXFLAG_SI)
+ && (x->ex_pathlen != -1)
+ && (plen > (x->ex_pathlen + proxy_path_length + 1)))
{
ctx->error = X509_V_ERR_PATH_LENGTH_EXCEEDED;
ctx->error_depth = i;
@@ -507,6 +508,9 @@ static int check_chain_extensions(X509_STORE_CTX *ctx)
ok=cb(0,ctx);
if (!ok) goto end;
}
+ /* Increment path length if not self issued */
+ if (!(x->ex_flags & EXFLAG_SI))
+ plen++;
/* If this certificate is a proxy certificate, the next
certificate must be another proxy certificate or a EE
certificate. If not, the next certificate must be a
diff --git a/crypto/x509v3/pcy_data.c b/crypto/x509v3/pcy_data.c
index 614d2b4935..4711b1ee92 100644
--- a/crypto/x509v3/pcy_data.c
+++ b/crypto/x509v3/pcy_data.c
@@ -87,6 +87,12 @@ X509_POLICY_DATA *policy_data_new(POLICYINFO *policy, ASN1_OBJECT *id, int crit)
X509_POLICY_DATA *ret;
if (!policy && !id)
return NULL;
+ if (id)
+ {
+ id = OBJ_dup(id);
+ if (!id)
+ return NULL;
+ }
ret = OPENSSL_malloc(sizeof(X509_POLICY_DATA));
if (!ret)
return NULL;
@@ -94,6 +100,8 @@ X509_POLICY_DATA *policy_data_new(POLICYINFO *policy, ASN1_OBJECT *id, int crit)
if (!ret->expected_policy_set)
{
OPENSSL_free(ret);
+ if (id)
+ ASN1_OBJECT_free(id);
return NULL;
}
diff --git a/crypto/x509v3/pcy_tree.c b/crypto/x509v3/pcy_tree.c
index 4fda1d419a..aed0155c2a 100644
--- a/crypto/x509v3/pcy_tree.c
+++ b/crypto/x509v3/pcy_tree.c
@@ -131,7 +131,7 @@ static int tree_init(X509_POLICY_TREE **ptree, STACK_OF(X509) *certs,
if (explicit_policy > 0)
{
explicit_policy--;
- if (!(x->ex_flags & EXFLAG_SS)
+ if (!(x->ex_flags & EXFLAG_SI)
&& (cache->explicit_skip != -1)
&& (cache->explicit_skip < explicit_policy))
explicit_policy = cache->explicit_skip;
@@ -197,7 +197,7 @@ static int tree_init(X509_POLICY_TREE **ptree, STACK_OF(X509) *certs,
/* Any matching allowed if certificate is self
* issued and not the last in the chain.
*/
- if (!(x->ex_flags & EXFLAG_SS) || (i == 0))
+ if (!(x->ex_flags & EXFLAG_SI) || (i == 0))
level->flags |= X509_V_FLAG_INHIBIT_ANY;
}
else
@@ -310,7 +310,8 @@ static int tree_link_any(X509_POLICY_LEVEL *curr,
if (data == NULL)
return 0;
- data->qualifier_set = curr->anyPolicy->data->qualifier_set;
+ /* Curr may not have anyPolicy */
+ data->qualifier_set = cache->anyPolicy->qualifier_set;
data->flags |= POLICY_DATA_FLAG_SHARED_QUALIFIERS;
if (!level_add_node(curr, data, node, tree))
{
diff --git a/crypto/x509v3/v3_purp.c b/crypto/x509v3/v3_purp.c
index ab923bb0d0..f5f8d1c176 100644
--- a/crypto/x509v3/v3_purp.c
+++ b/crypto/x509v3/v3_purp.c
@@ -293,6 +293,7 @@ int X509_supported_extension(X509_EXTENSION *ex)
NID_sbgp_ipAddrBlock, /* 290 */
NID_sbgp_autonomousSysNum, /* 291 */
#endif
+ NID_policy_constraints, /* 401 */
NID_proxyCertInfo /* 663 */
};
@@ -327,7 +328,7 @@ static void x509v3_cache_extensions(X509 *x)
#endif
/* Does subject name match issuer ? */
if(!X509_NAME_cmp(X509_get_subject_name(x), X509_get_issuer_name(x)))
- x->ex_flags |= EXFLAG_SS;
+ x->ex_flags |= EXFLAG_SI;
/* V1 should mean no extensions ... */
if(!X509_get_version(x)) x->ex_flags |= EXFLAG_V1;
/* Handle basic constraints */
diff --git a/crypto/x509v3/x509v3.h b/crypto/x509v3/x509v3.h
index 381ea1315b..7cc24348b1 100644
--- a/crypto/x509v3/x509v3.h
+++ b/crypto/x509v3/x509v3.h
@@ -388,6 +388,8 @@ struct ISSUING_DIST_POINT_st
#define EXFLAG_NSCERT 0x8
#define EXFLAG_CA 0x10
+/* Really self issued not necessarily self signed */
+#define EXFLAG_SI 0x20
#define EXFLAG_SS 0x20
#define EXFLAG_V1 0x40
#define EXFLAG_INVALID 0x80
diff --git a/doc/apps/verify.pod b/doc/apps/verify.pod
index ff2629d2cf..8c8cbaaf4d 100644
--- a/doc/apps/verify.pod
+++ b/doc/apps/verify.pod
@@ -171,7 +171,7 @@ of an untrusted certificate cannot be found.
=item B<3 X509_V_ERR_UNABLE_TO_GET_CRL: unable to get certificate CRL>
-the CRL of a certificate could not be found. Unused.
+the CRL of a certificate could not be found.
=item B<4 X509_V_ERR_UNABLE_TO_DECRYPT_CERT_SIGNATURE: unable to decrypt certificate's signature>
@@ -194,7 +194,7 @@ the signature of the certificate is invalid.
=item B<8 X509_V_ERR_CRL_SIGNATURE_FAILURE: CRL signature failure>
-the signature of the certificate is invalid. Unused.
+the signature of the certificate is invalid.
=item B<9 X509_V_ERR_CERT_NOT_YET_VALID: certificate is not yet valid>
@@ -206,11 +206,11 @@ the certificate has expired: that is the notAfter date is before the current tim
=item B<11 X509_V_ERR_CRL_NOT_YET_VALID: CRL is not yet valid>
-the CRL is not yet valid. Unused.
+the CRL is not yet valid.
=item B<12 X509_V_ERR_CRL_HAS_EXPIRED: CRL has expired>
-the CRL has expired. Unused.
+the CRL has expired.
=item B<13 X509_V_ERR_ERROR_IN_CERT_NOT_BEFORE_FIELD: format error in certificate's notBefore field>
@@ -222,11 +222,11 @@ the certificate notAfter field contains an invalid time.
=item B<15 X509_V_ERR_ERROR_IN_CRL_LAST_UPDATE_FIELD: format error in CRL's lastUpdate field>
-the CRL lastUpdate field contains an invalid time. Unused.
+the CRL lastUpdate field contains an invalid time.
=item B<16 X509_V_ERR_ERROR_IN_CRL_NEXT_UPDATE_FIELD: format error in CRL's nextUpdate field>
-the CRL nextUpdate field contains an invalid time. Unused.
+the CRL nextUpdate field contains an invalid time.
=item B<17 X509_V_ERR_OUT_OF_MEM: out of memory>
@@ -258,7 +258,7 @@ the certificate chain length is greater than the supplied maximum depth. Unused.
=item B<23 X509_V_ERR_CERT_REVOKED: certificate revoked>
-the certificate has been revoked. Unused.
+the certificate has been revoked.
=item B<24 X509_V_ERR_INVALID_CA: invalid CA certificate>