summaryrefslogtreecommitdiff
path: root/src/lib/libcrypto/x509
diff options
context:
space:
mode:
Diffstat (limited to 'src/lib/libcrypto/x509')
-rw-r--r--src/lib/libcrypto/x509/by_file.c4
-rw-r--r--src/lib/libcrypto/x509/x509.h11
-rw-r--r--src/lib/libcrypto/x509/x509_cmp.c48
-rw-r--r--src/lib/libcrypto/x509/x509_r2x.c6
-rw-r--r--src/lib/libcrypto/x509/x509_req.c35
-rw-r--r--src/lib/libcrypto/x509/x509_txt.c13
-rw-r--r--src/lib/libcrypto/x509/x509_vfy.c131
-rw-r--r--src/lib/libcrypto/x509/x509_vfy.h8
-rw-r--r--src/lib/libcrypto/x509/x509cset.c1
-rw-r--r--src/lib/libcrypto/x509/x509name.c10
-rw-r--r--src/lib/libcrypto/x509/x_all.c1
11 files changed, 205 insertions, 63 deletions
diff --git a/src/lib/libcrypto/x509/by_file.c b/src/lib/libcrypto/x509/by_file.c
index b4b04183d0..a5e0d4aefa 100644
--- a/src/lib/libcrypto/x509/by_file.c
+++ b/src/lib/libcrypto/x509/by_file.c
@@ -150,7 +150,7 @@ int X509_load_cert_file(X509_LOOKUP *ctx, const char *file, int type)
150 x=PEM_read_bio_X509_AUX(in,NULL,NULL,NULL); 150 x=PEM_read_bio_X509_AUX(in,NULL,NULL,NULL);
151 if (x == NULL) 151 if (x == NULL)
152 { 152 {
153 if ((ERR_GET_REASON(ERR_peek_error()) == 153 if ((ERR_GET_REASON(ERR_peek_last_error()) ==
154 PEM_R_NO_START_LINE) && (count > 0)) 154 PEM_R_NO_START_LINE) && (count > 0))
155 { 155 {
156 ERR_clear_error(); 156 ERR_clear_error();
@@ -217,7 +217,7 @@ int X509_load_crl_file(X509_LOOKUP *ctx, const char *file, int type)
217 x=PEM_read_bio_X509_CRL(in,NULL,NULL,NULL); 217 x=PEM_read_bio_X509_CRL(in,NULL,NULL,NULL);
218 if (x == NULL) 218 if (x == NULL)
219 { 219 {
220 if ((ERR_GET_REASON(ERR_peek_error()) == 220 if ((ERR_GET_REASON(ERR_peek_last_error()) ==
221 PEM_R_NO_START_LINE) && (count > 0)) 221 PEM_R_NO_START_LINE) && (count > 0))
222 { 222 {
223 ERR_clear_error(); 223 ERR_clear_error();
diff --git a/src/lib/libcrypto/x509/x509.h b/src/lib/libcrypto/x509/x509.h
index 8d0c7e2e17..e8c1a59cf2 100644
--- a/src/lib/libcrypto/x509/x509.h
+++ b/src/lib/libcrypto/x509/x509.h
@@ -410,6 +410,7 @@ typedef struct X509_crl_info_st
410 ASN1_TIME *nextUpdate; 410 ASN1_TIME *nextUpdate;
411 STACK_OF(X509_REVOKED) *revoked; 411 STACK_OF(X509_REVOKED) *revoked;
412 STACK_OF(X509_EXTENSION) /* [0] */ *extensions; 412 STACK_OF(X509_EXTENSION) /* [0] */ *extensions;
413 ASN1_ENCODING enc;
413 } X509_CRL_INFO; 414 } X509_CRL_INFO;
414 415
415struct X509_crl_st 416struct X509_crl_st
@@ -1037,18 +1038,18 @@ int X509_NAME_add_entry_by_OBJ(X509_NAME *name, ASN1_OBJECT *obj, int type,
1037int X509_NAME_add_entry_by_NID(X509_NAME *name, int nid, int type, 1038int X509_NAME_add_entry_by_NID(X509_NAME *name, int nid, int type,
1038 unsigned char *bytes, int len, int loc, int set); 1039 unsigned char *bytes, int len, int loc, int set);
1039X509_NAME_ENTRY *X509_NAME_ENTRY_create_by_txt(X509_NAME_ENTRY **ne, 1040X509_NAME_ENTRY *X509_NAME_ENTRY_create_by_txt(X509_NAME_ENTRY **ne,
1040 char *field, int type, unsigned char *bytes, int len); 1041 const char *field, int type, const unsigned char *bytes, int len);
1041X509_NAME_ENTRY *X509_NAME_ENTRY_create_by_NID(X509_NAME_ENTRY **ne, int nid, 1042X509_NAME_ENTRY *X509_NAME_ENTRY_create_by_NID(X509_NAME_ENTRY **ne, int nid,
1042 int type,unsigned char *bytes, int len); 1043 int type,unsigned char *bytes, int len);
1043int X509_NAME_add_entry_by_txt(X509_NAME *name, char *field, int type, 1044int X509_NAME_add_entry_by_txt(X509_NAME *name, const char *field, int type,
1044 unsigned char *bytes, int len, int loc, int set); 1045 const unsigned char *bytes, int len, int loc, int set);
1045X509_NAME_ENTRY *X509_NAME_ENTRY_create_by_OBJ(X509_NAME_ENTRY **ne, 1046X509_NAME_ENTRY *X509_NAME_ENTRY_create_by_OBJ(X509_NAME_ENTRY **ne,
1046 ASN1_OBJECT *obj, int type,unsigned char *bytes, 1047 ASN1_OBJECT *obj, int type,const unsigned char *bytes,
1047 int len); 1048 int len);
1048int X509_NAME_ENTRY_set_object(X509_NAME_ENTRY *ne, 1049int X509_NAME_ENTRY_set_object(X509_NAME_ENTRY *ne,
1049 ASN1_OBJECT *obj); 1050 ASN1_OBJECT *obj);
1050int X509_NAME_ENTRY_set_data(X509_NAME_ENTRY *ne, int type, 1051int X509_NAME_ENTRY_set_data(X509_NAME_ENTRY *ne, int type,
1051 unsigned char *bytes, int len); 1052 const unsigned char *bytes, int len);
1052ASN1_OBJECT * X509_NAME_ENTRY_get_object(X509_NAME_ENTRY *ne); 1053ASN1_OBJECT * X509_NAME_ENTRY_get_object(X509_NAME_ENTRY *ne);
1053ASN1_STRING * X509_NAME_ENTRY_get_data(X509_NAME_ENTRY *ne); 1054ASN1_STRING * X509_NAME_ENTRY_get_data(X509_NAME_ENTRY *ne);
1054 1055
diff --git a/src/lib/libcrypto/x509/x509_cmp.c b/src/lib/libcrypto/x509/x509_cmp.c
index f460102f49..030d0966fc 100644
--- a/src/lib/libcrypto/x509/x509_cmp.c
+++ b/src/lib/libcrypto/x509/x509_cmp.c
@@ -254,33 +254,49 @@ static int nocase_spacenorm_cmp(const ASN1_STRING *a, const ASN1_STRING *b)
254 return 0; 254 return 0;
255} 255}
256 256
257static int asn1_string_memcmp(ASN1_STRING *a, ASN1_STRING *b)
258 {
259 int j;
260 j = a->length - b->length;
261 if (j)
262 return j;
263 return memcmp(a->data, b->data, a->length);
264 }
265
266#define STR_TYPE_CMP (B_ASN1_PRINTABLESTRING|B_ASN1_T61STRING|B_ASN1_UTF8STRING)
267
257int X509_NAME_cmp(const X509_NAME *a, const X509_NAME *b) 268int X509_NAME_cmp(const X509_NAME *a, const X509_NAME *b)
258 { 269 {
259 int i,j; 270 int i,j;
260 X509_NAME_ENTRY *na,*nb; 271 X509_NAME_ENTRY *na,*nb;
261 272
262 if (sk_X509_NAME_ENTRY_num(a->entries) 273 unsigned long nabit, nbbit;
263 != sk_X509_NAME_ENTRY_num(b->entries)) 274
264 return sk_X509_NAME_ENTRY_num(a->entries) 275 j = sk_X509_NAME_ENTRY_num(a->entries)
265 -sk_X509_NAME_ENTRY_num(b->entries); 276 - sk_X509_NAME_ENTRY_num(b->entries);
277 if (j)
278 return j;
266 for (i=sk_X509_NAME_ENTRY_num(a->entries)-1; i>=0; i--) 279 for (i=sk_X509_NAME_ENTRY_num(a->entries)-1; i>=0; i--)
267 { 280 {
268 na=sk_X509_NAME_ENTRY_value(a->entries,i); 281 na=sk_X509_NAME_ENTRY_value(a->entries,i);
269 nb=sk_X509_NAME_ENTRY_value(b->entries,i); 282 nb=sk_X509_NAME_ENTRY_value(b->entries,i);
270 j=na->value->type-nb->value->type; 283 j=na->value->type-nb->value->type;
271 if (j) return(j); 284 if (j)
272 if (na->value->type == V_ASN1_PRINTABLESTRING) 285 {
286 nabit = ASN1_tag2bit(na->value->type);
287 nbbit = ASN1_tag2bit(nb->value->type);
288 if (!(nabit & STR_TYPE_CMP) ||
289 !(nbbit & STR_TYPE_CMP))
290 return j;
291 j = asn1_string_memcmp(na->value, nb->value);
292 }
293 else if (na->value->type == V_ASN1_PRINTABLESTRING)
273 j=nocase_spacenorm_cmp(na->value, nb->value); 294 j=nocase_spacenorm_cmp(na->value, nb->value);
274 else if (na->value->type == V_ASN1_IA5STRING 295 else if (na->value->type == V_ASN1_IA5STRING
275 && OBJ_obj2nid(na->object) == NID_pkcs9_emailAddress) 296 && OBJ_obj2nid(na->object) == NID_pkcs9_emailAddress)
276 j=nocase_cmp(na->value, nb->value); 297 j=nocase_cmp(na->value, nb->value);
277 else 298 else
278 { 299 j = asn1_string_memcmp(na->value, nb->value);
279 j=na->value->length-nb->value->length;
280 if (j) return(j);
281 j=memcmp(na->value->data,nb->value->data,
282 na->value->length);
283 }
284 if (j) return(j); 300 if (j) return(j);
285 j=na->set-nb->set; 301 j=na->set-nb->set;
286 if (j) return(j); 302 if (j) return(j);
@@ -306,10 +322,16 @@ unsigned long X509_NAME_hash(X509_NAME *x)
306 { 322 {
307 unsigned long ret=0; 323 unsigned long ret=0;
308 unsigned char md[16]; 324 unsigned char md[16];
325 EVP_MD_CTX md_ctx;
309 326
310 /* Make sure X509_NAME structure contains valid cached encoding */ 327 /* Make sure X509_NAME structure contains valid cached encoding */
311 i2d_X509_NAME(x,NULL); 328 i2d_X509_NAME(x,NULL);
312 EVP_Digest(x->bytes->data, x->bytes->length, md, NULL, EVP_md5(), NULL); 329 EVP_MD_CTX_init(&md_ctx);
330 EVP_MD_CTX_set_flags(&md_ctx, EVP_MD_CTX_FLAG_NON_FIPS_ALLOW);
331 EVP_DigestInit_ex(&md_ctx, EVP_md5(), NULL);
332 EVP_DigestUpdate(&md_ctx, x->bytes->data, x->bytes->length);
333 EVP_DigestFinal_ex(&md_ctx,md,NULL);
334 EVP_MD_CTX_cleanup(&md_ctx);
313 335
314 ret=( ((unsigned long)md[0] )|((unsigned long)md[1]<<8L)| 336 ret=( ((unsigned long)md[0] )|((unsigned long)md[1]<<8L)|
315 ((unsigned long)md[2]<<16L)|((unsigned long)md[3]<<24L) 337 ((unsigned long)md[2]<<16L)|((unsigned long)md[3]<<24L)
diff --git a/src/lib/libcrypto/x509/x509_r2x.c b/src/lib/libcrypto/x509/x509_r2x.c
index db051033d9..fb8a78dabe 100644
--- a/src/lib/libcrypto/x509/x509_r2x.c
+++ b/src/lib/libcrypto/x509/x509_r2x.c
@@ -92,8 +92,10 @@ X509 *X509_REQ_to_X509(X509_REQ *r, int days, EVP_PKEY *pkey)
92 X509_set_subject_name(ret,X509_NAME_dup(xn)); 92 X509_set_subject_name(ret,X509_NAME_dup(xn));
93 X509_set_issuer_name(ret,X509_NAME_dup(xn)); 93 X509_set_issuer_name(ret,X509_NAME_dup(xn));
94 94
95 X509_gmtime_adj(xi->validity->notBefore,0); 95 if (X509_gmtime_adj(xi->validity->notBefore,0) == NULL)
96 X509_gmtime_adj(xi->validity->notAfter,(long)60*60*24*days); 96 goto err;
97 if (X509_gmtime_adj(xi->validity->notAfter,(long)60*60*24*days) == NULL)
98 goto err;
97 99
98 X509_set_pubkey(ret,X509_REQ_get_pubkey(r)); 100 X509_set_pubkey(ret,X509_REQ_get_pubkey(r));
99 101
diff --git a/src/lib/libcrypto/x509/x509_req.c b/src/lib/libcrypto/x509/x509_req.c
index 0affa3bf30..59fc6ca548 100644
--- a/src/lib/libcrypto/x509/x509_req.c
+++ b/src/lib/libcrypto/x509/x509_req.c
@@ -118,7 +118,7 @@ EVP_PKEY *X509_REQ_get_pubkey(X509_REQ *req)
118 * used and there may be more: so the list is configurable. 118 * used and there may be more: so the list is configurable.
119 */ 119 */
120 120
121static int ext_nid_list[] = { NID_ms_ext_req, NID_ext_req, NID_undef}; 121static int ext_nid_list[] = { NID_ext_req, NID_ms_ext_req, NID_undef};
122 122
123static int *ext_nids = ext_nid_list; 123static int *ext_nids = ext_nid_list;
124 124
@@ -143,32 +143,33 @@ void X509_REQ_set_extension_nids(int *nids)
143} 143}
144 144
145STACK_OF(X509_EXTENSION) *X509_REQ_get_extensions(X509_REQ *req) 145STACK_OF(X509_EXTENSION) *X509_REQ_get_extensions(X509_REQ *req)
146{ 146 {
147 X509_ATTRIBUTE *attr; 147 X509_ATTRIBUTE *attr;
148 STACK_OF(X509_ATTRIBUTE) *sk;
149 ASN1_TYPE *ext = NULL; 148 ASN1_TYPE *ext = NULL;
150 int i; 149 int idx, *pnid;
151 unsigned char *p; 150 unsigned char *p;
152 if ((req == NULL) || (req->req_info == NULL)) 151
152 if ((req == NULL) || (req->req_info == NULL) || !ext_nids)
153 return(NULL); 153 return(NULL);
154 sk=req->req_info->attributes; 154 for (pnid = ext_nids; *pnid != NID_undef; pnid++)
155 if (!sk) return NULL; 155 {
156 for(i = 0; i < sk_X509_ATTRIBUTE_num(sk); i++) { 156 idx = X509_REQ_get_attr_by_NID(req, *pnid, -1);
157 attr = sk_X509_ATTRIBUTE_value(sk, i); 157 if (idx == -1)
158 if(X509_REQ_extension_nid(OBJ_obj2nid(attr->object))) { 158 continue;
159 if(attr->single) ext = attr->value.single; 159 attr = X509_REQ_get_attr(req, idx);
160 else if(sk_ASN1_TYPE_num(attr->value.set)) 160 if(attr->single) ext = attr->value.single;
161 ext = sk_ASN1_TYPE_value(attr->value.set, 0); 161 else if(sk_ASN1_TYPE_num(attr->value.set))
162 break; 162 ext = sk_ASN1_TYPE_value(attr->value.set, 0);
163 break;
163 } 164 }
164 } 165 if(!ext || (ext->type != V_ASN1_SEQUENCE))
165 if(!ext || (ext->type != V_ASN1_SEQUENCE)) return NULL; 166 return NULL;
166 p = ext->value.sequence->data; 167 p = ext->value.sequence->data;
167 return d2i_ASN1_SET_OF_X509_EXTENSION(NULL, &p, 168 return d2i_ASN1_SET_OF_X509_EXTENSION(NULL, &p,
168 ext->value.sequence->length, 169 ext->value.sequence->length,
169 d2i_X509_EXTENSION, X509_EXTENSION_free, 170 d2i_X509_EXTENSION, X509_EXTENSION_free,
170 V_ASN1_SEQUENCE, V_ASN1_UNIVERSAL); 171 V_ASN1_SEQUENCE, V_ASN1_UNIVERSAL);
171} 172 }
172 173
173/* Add a STACK_OF extensions to a certificate request: allow alternative OIDs 174/* Add a STACK_OF extensions to a certificate request: allow alternative OIDs
174 * in case we want to create a non standard one. 175 * in case we want to create a non standard one.
diff --git a/src/lib/libcrypto/x509/x509_txt.c b/src/lib/libcrypto/x509/x509_txt.c
index e31ebc6741..f19e66a238 100644
--- a/src/lib/libcrypto/x509/x509_txt.c
+++ b/src/lib/libcrypto/x509/x509_txt.c
@@ -122,8 +122,14 @@ const char *X509_verify_cert_error_string(long n)
122 return("certificate revoked"); 122 return("certificate revoked");
123 case X509_V_ERR_INVALID_CA: 123 case X509_V_ERR_INVALID_CA:
124 return ("invalid CA certificate"); 124 return ("invalid CA certificate");
125 case X509_V_ERR_INVALID_NON_CA:
126 return ("invalid non-CA certificate (has CA markings)");
125 case X509_V_ERR_PATH_LENGTH_EXCEEDED: 127 case X509_V_ERR_PATH_LENGTH_EXCEEDED:
126 return ("path length constraint exceeded"); 128 return ("path length constraint exceeded");
129 case X509_V_ERR_PROXY_PATH_LENGTH_EXCEEDED:
130 return("proxy path length constraint exceeded");
131 case X509_V_ERR_PROXY_CERTIFICATES_NOT_ALLOWED:
132 return("proxy cerificates not allowed, please set the appropriate flag");
127 case X509_V_ERR_INVALID_PURPOSE: 133 case X509_V_ERR_INVALID_PURPOSE:
128 return ("unsupported certificate purpose"); 134 return ("unsupported certificate purpose");
129 case X509_V_ERR_CERT_UNTRUSTED: 135 case X509_V_ERR_CERT_UNTRUSTED:
@@ -140,19 +146,16 @@ const char *X509_verify_cert_error_string(long n)
140 return("authority and issuer serial number mismatch"); 146 return("authority and issuer serial number mismatch");
141 case X509_V_ERR_KEYUSAGE_NO_CERTSIGN: 147 case X509_V_ERR_KEYUSAGE_NO_CERTSIGN:
142 return("key usage does not include certificate signing"); 148 return("key usage does not include certificate signing");
143
144 case X509_V_ERR_UNABLE_TO_GET_CRL_ISSUER: 149 case X509_V_ERR_UNABLE_TO_GET_CRL_ISSUER:
145 return("unable to get CRL issuer certificate"); 150 return("unable to get CRL issuer certificate");
146
147 case X509_V_ERR_UNHANDLED_CRITICAL_EXTENSION: 151 case X509_V_ERR_UNHANDLED_CRITICAL_EXTENSION:
148 return("unhandled critical extension"); 152 return("unhandled critical extension");
149
150 case X509_V_ERR_KEYUSAGE_NO_CRL_SIGN: 153 case X509_V_ERR_KEYUSAGE_NO_CRL_SIGN:
151 return("key usage does not include CRL signing"); 154 return("key usage does not include CRL signing");
152 155 case X509_V_ERR_KEYUSAGE_NO_DIGITAL_SIGNATURE:
156 return("key usage does not include digital signature");
153 case X509_V_ERR_UNHANDLED_CRITICAL_CRL_EXTENSION: 157 case X509_V_ERR_UNHANDLED_CRITICAL_CRL_EXTENSION:
154 return("unhandled critical CRL extension"); 158 return("unhandled critical CRL extension");
155
156 default: 159 default:
157 BIO_snprintf(buf,sizeof buf,"error number %ld",n); 160 BIO_snprintf(buf,sizeof buf,"error number %ld",n);
158 return(buf); 161 return(buf);
diff --git a/src/lib/libcrypto/x509/x509_vfy.c b/src/lib/libcrypto/x509/x509_vfy.c
index 2e4d0b823a..e43c861ee7 100644
--- a/src/lib/libcrypto/x509/x509_vfy.c
+++ b/src/lib/libcrypto/x509/x509_vfy.c
@@ -73,7 +73,7 @@
73static int null_callback(int ok,X509_STORE_CTX *e); 73static int null_callback(int ok,X509_STORE_CTX *e);
74static int check_issued(X509_STORE_CTX *ctx, X509 *x, X509 *issuer); 74static int check_issued(X509_STORE_CTX *ctx, X509 *x, X509 *issuer);
75static X509 *find_issuer(X509_STORE_CTX *ctx, STACK_OF(X509) *sk, X509 *x); 75static X509 *find_issuer(X509_STORE_CTX *ctx, STACK_OF(X509) *sk, X509 *x);
76static int check_chain_purpose(X509_STORE_CTX *ctx); 76static int check_chain_extensions(X509_STORE_CTX *ctx);
77static int check_trust(X509_STORE_CTX *ctx); 77static int check_trust(X509_STORE_CTX *ctx);
78static int check_revocation(X509_STORE_CTX *ctx); 78static int check_revocation(X509_STORE_CTX *ctx);
79static int check_cert(X509_STORE_CTX *ctx); 79static int check_cert(X509_STORE_CTX *ctx);
@@ -281,7 +281,7 @@ int X509_verify_cert(X509_STORE_CTX *ctx)
281 } 281 }
282 282
283 /* We have the chain complete: now we need to check its purpose */ 283 /* We have the chain complete: now we need to check its purpose */
284 if (ctx->purpose > 0) ok = check_chain_purpose(ctx); 284 ok = check_chain_extensions(ctx);
285 285
286 if (!ok) goto end; 286 if (!ok) goto end;
287 287
@@ -365,21 +365,39 @@ static int get_issuer_sk(X509 **issuer, X509_STORE_CTX *ctx, X509 *x)
365 else 365 else
366 return 0; 366 return 0;
367} 367}
368 368
369 369
370/* Check a certificate chains extensions for consistency 370/* Check a certificate chains extensions for consistency
371 * with the supplied purpose 371 * with the supplied purpose
372 */ 372 */
373 373
374static int check_chain_purpose(X509_STORE_CTX *ctx) 374static int check_chain_extensions(X509_STORE_CTX *ctx)
375{ 375{
376#ifdef OPENSSL_NO_CHAIN_VERIFY 376#ifdef OPENSSL_NO_CHAIN_VERIFY
377 return 1; 377 return 1;
378#else 378#else
379 int i, ok=0; 379 int i, ok=0, must_be_ca;
380 X509 *x; 380 X509 *x;
381 int (*cb)(); 381 int (*cb)();
382 int proxy_path_length = 0;
383 int allow_proxy_certs = !!(ctx->flags & X509_V_FLAG_ALLOW_PROXY_CERTS);
382 cb=ctx->verify_cb; 384 cb=ctx->verify_cb;
385
386 /* must_be_ca can have 1 of 3 values:
387 -1: we accept both CA and non-CA certificates, to allow direct
388 use of self-signed certificates (which are marked as CA).
389 0: we only accept non-CA certificates. This is currently not
390 used, but the possibility is present for future extensions.
391 1: we only accept CA certificates. This is currently used for
392 all certificates in the chain except the leaf certificate.
393 */
394 must_be_ca = -1;
395
396 /* A hack to keep people who don't want to modify their software
397 happy */
398 if (getenv("OPENSSL_ALLOW_PROXY_CERTS"))
399 allow_proxy_certs = 1;
400
383 /* Check all untrusted certificates */ 401 /* Check all untrusted certificates */
384 for (i = 0; i < ctx->last_untrusted; i++) 402 for (i = 0; i < ctx->last_untrusted; i++)
385 { 403 {
@@ -394,23 +412,73 @@ static int check_chain_purpose(X509_STORE_CTX *ctx)
394 ok=cb(0,ctx); 412 ok=cb(0,ctx);
395 if (!ok) goto end; 413 if (!ok) goto end;
396 } 414 }
397 ret = X509_check_purpose(x, ctx->purpose, i); 415 if (!allow_proxy_certs && (x->ex_flags & EXFLAG_PROXY))
398 if ((ret == 0)
399 || ((ctx->flags & X509_V_FLAG_X509_STRICT)
400 && (ret != 1)))
401 { 416 {
402 if (i) 417 ctx->error = X509_V_ERR_PROXY_CERTIFICATES_NOT_ALLOWED;
418 ctx->error_depth = i;
419 ctx->current_cert = x;
420 ok=cb(0,ctx);
421 if (!ok) goto end;
422 }
423 ret = X509_check_ca(x);
424 switch(must_be_ca)
425 {
426 case -1:
427 if ((ctx->flags & X509_V_FLAG_X509_STRICT)
428 && (ret != 1) && (ret != 0))
429 {
430 ret = 0;
403 ctx->error = X509_V_ERR_INVALID_CA; 431 ctx->error = X509_V_ERR_INVALID_CA;
432 }
404 else 433 else
405 ctx->error = X509_V_ERR_INVALID_PURPOSE; 434 ret = 1;
435 break;
436 case 0:
437 if (ret != 0)
438 {
439 ret = 0;
440 ctx->error = X509_V_ERR_INVALID_NON_CA;
441 }
442 else
443 ret = 1;
444 break;
445 default:
446 if ((ret == 0)
447 || ((ctx->flags & X509_V_FLAG_X509_STRICT)
448 && (ret != 1)))
449 {
450 ret = 0;
451 ctx->error = X509_V_ERR_INVALID_CA;
452 }
453 else
454 ret = 1;
455 break;
456 }
457 if (ret == 0)
458 {
406 ctx->error_depth = i; 459 ctx->error_depth = i;
407 ctx->current_cert = x; 460 ctx->current_cert = x;
408 ok=cb(0,ctx); 461 ok=cb(0,ctx);
409 if (!ok) goto end; 462 if (!ok) goto end;
410 } 463 }
464 if (ctx->purpose > 0)
465 {
466 ret = X509_check_purpose(x, ctx->purpose,
467 must_be_ca > 0);
468 if ((ret == 0)
469 || ((ctx->flags & X509_V_FLAG_X509_STRICT)
470 && (ret != 1)))
471 {
472 ctx->error = X509_V_ERR_INVALID_PURPOSE;
473 ctx->error_depth = i;
474 ctx->current_cert = x;
475 ok=cb(0,ctx);
476 if (!ok) goto end;
477 }
478 }
411 /* Check pathlen */ 479 /* Check pathlen */
412 if ((i > 1) && (x->ex_pathlen != -1) 480 if ((i > 1) && (x->ex_pathlen != -1)
413 && (i > (x->ex_pathlen + 1))) 481 && (i > (x->ex_pathlen + proxy_path_length + 1)))
414 { 482 {
415 ctx->error = X509_V_ERR_PATH_LENGTH_EXCEEDED; 483 ctx->error = X509_V_ERR_PATH_LENGTH_EXCEEDED;
416 ctx->error_depth = i; 484 ctx->error_depth = i;
@@ -418,6 +486,32 @@ static int check_chain_purpose(X509_STORE_CTX *ctx)
418 ok=cb(0,ctx); 486 ok=cb(0,ctx);
419 if (!ok) goto end; 487 if (!ok) goto end;
420 } 488 }
489 /* If this certificate is a proxy certificate, the next
490 certificate must be another proxy certificate or a EE
491 certificate. If not, the next certificate must be a
492 CA certificate. */
493 if (x->ex_flags & EXFLAG_PROXY)
494 {
495 PROXY_CERT_INFO_EXTENSION *pci =
496 X509_get_ext_d2i(x, NID_proxyCertInfo,
497 NULL, NULL);
498 if (pci->pcPathLengthConstraint &&
499 ASN1_INTEGER_get(pci->pcPathLengthConstraint)
500 < i)
501 {
502 PROXY_CERT_INFO_EXTENSION_free(pci);
503 ctx->error = X509_V_ERR_PROXY_PATH_LENGTH_EXCEEDED;
504 ctx->error_depth = i;
505 ctx->current_cert = x;
506 ok=cb(0,ctx);
507 if (!ok) goto end;
508 }
509 PROXY_CERT_INFO_EXTENSION_free(pci);
510 proxy_path_length++;
511 must_be_ca = 0;
512 }
513 else
514 must_be_ca = 1;
421 } 515 }
422 ok = 1; 516 ok = 1;
423 end: 517 end:
@@ -627,6 +721,15 @@ static int cert_crl(X509_STORE_CTX *ctx, X509_CRL *crl, X509 *x)
627 X509_EXTENSION *ext; 721 X509_EXTENSION *ext;
628 /* Look for serial number of certificate in CRL */ 722 /* Look for serial number of certificate in CRL */
629 rtmp.serialNumber = X509_get_serialNumber(x); 723 rtmp.serialNumber = X509_get_serialNumber(x);
724 /* Sort revoked into serial number order if not already sorted.
725 * Do this under a lock to avoid race condition.
726 */
727 if (!sk_X509_REVOKED_is_sorted(crl->crl->revoked))
728 {
729 CRYPTO_w_lock(CRYPTO_LOCK_X509_CRL);
730 sk_X509_REVOKED_sort(crl->crl->revoked);
731 CRYPTO_w_unlock(CRYPTO_LOCK_X509_CRL);
732 }
630 idx = sk_X509_REVOKED_find(crl->crl->revoked, &rtmp); 733 idx = sk_X509_REVOKED_find(crl->crl->revoked, &rtmp);
631 /* If found assume revoked: want something cleverer than 734 /* If found assume revoked: want something cleverer than
632 * this to handle entry extensions in V2 CRLs. 735 * this to handle entry extensions in V2 CRLs.
@@ -772,6 +875,7 @@ static int internal_verify(X509_STORE_CTX *ctx)
772 } 875 }
773 876
774 /* The last error (if any) is still in the error value */ 877 /* The last error (if any) is still in the error value */
878 ctx->current_issuer=xi;
775 ctx->current_cert=xs; 879 ctx->current_cert=xs;
776 ok=(*cb)(1,ctx); 880 ok=(*cb)(1,ctx);
777 if (!ok) goto end; 881 if (!ok) goto end;
@@ -851,7 +955,8 @@ int X509_cmp_time(ASN1_TIME *ctm, time_t *cmp_time)
851 atm.length=sizeof(buff2); 955 atm.length=sizeof(buff2);
852 atm.data=(unsigned char *)buff2; 956 atm.data=(unsigned char *)buff2;
853 957
854 X509_time_adj(&atm,-offset*60, cmp_time); 958 if (X509_time_adj(&atm,-offset*60, cmp_time) == NULL)
959 return 0;
855 960
856 if (ctm->type == V_ASN1_UTCTIME) 961 if (ctm->type == V_ASN1_UTCTIME)
857 { 962 {
diff --git a/src/lib/libcrypto/x509/x509_vfy.h b/src/lib/libcrypto/x509/x509_vfy.h
index 198495884c..7fd1f0bc4d 100644
--- a/src/lib/libcrypto/x509/x509_vfy.h
+++ b/src/lib/libcrypto/x509/x509_vfy.h
@@ -276,7 +276,7 @@ struct x509_store_ctx_st /* X509_STORE_CTX */
276#define X509_V_ERR_UNABLE_TO_DECODE_ISSUER_PUBLIC_KEY 6 276#define X509_V_ERR_UNABLE_TO_DECODE_ISSUER_PUBLIC_KEY 6
277#define X509_V_ERR_CERT_SIGNATURE_FAILURE 7 277#define X509_V_ERR_CERT_SIGNATURE_FAILURE 7
278#define X509_V_ERR_CRL_SIGNATURE_FAILURE 8 278#define X509_V_ERR_CRL_SIGNATURE_FAILURE 8
279#define X509_V_ERR_CERT_NOT_YET_VALID 9 279#define X509_V_ERR_CERT_NOT_YET_VALID 9
280#define X509_V_ERR_CERT_HAS_EXPIRED 10 280#define X509_V_ERR_CERT_HAS_EXPIRED 10
281#define X509_V_ERR_CRL_NOT_YET_VALID 11 281#define X509_V_ERR_CRL_NOT_YET_VALID 11
282#define X509_V_ERR_CRL_HAS_EXPIRED 12 282#define X509_V_ERR_CRL_HAS_EXPIRED 12
@@ -306,6 +306,10 @@ struct x509_store_ctx_st /* X509_STORE_CTX */
306#define X509_V_ERR_UNHANDLED_CRITICAL_EXTENSION 34 306#define X509_V_ERR_UNHANDLED_CRITICAL_EXTENSION 34
307#define X509_V_ERR_KEYUSAGE_NO_CRL_SIGN 35 307#define X509_V_ERR_KEYUSAGE_NO_CRL_SIGN 35
308#define X509_V_ERR_UNHANDLED_CRITICAL_CRL_EXTENSION 36 308#define X509_V_ERR_UNHANDLED_CRITICAL_CRL_EXTENSION 36
309#define X509_V_ERR_INVALID_NON_CA 37
310#define X509_V_ERR_PROXY_PATH_LENGTH_EXCEEDED 38
311#define X509_V_ERR_KEYUSAGE_NO_DIGITAL_SIGNATURE 39
312#define X509_V_ERR_PROXY_CERTIFICATES_NOT_ALLOWED 40
309 313
310/* The application is not happy */ 314/* The application is not happy */
311#define X509_V_ERR_APPLICATION_VERIFICATION 50 315#define X509_V_ERR_APPLICATION_VERIFICATION 50
@@ -324,6 +328,8 @@ struct x509_store_ctx_st /* X509_STORE_CTX */
324#define X509_V_FLAG_IGNORE_CRITICAL 0x10 328#define X509_V_FLAG_IGNORE_CRITICAL 0x10
325/* Disable workarounds for broken certificates */ 329/* Disable workarounds for broken certificates */
326#define X509_V_FLAG_X509_STRICT 0x20 330#define X509_V_FLAG_X509_STRICT 0x20
331/* Enable proxy certificate validation */
332#define X509_V_FLAG_ALLOW_PROXY_CERTS 0x40
327 333
328int X509_OBJECT_idx_by_subject(STACK_OF(X509_OBJECT) *h, int type, 334int X509_OBJECT_idx_by_subject(STACK_OF(X509_OBJECT) *h, int type,
329 X509_NAME *name); 335 X509_NAME *name);
diff --git a/src/lib/libcrypto/x509/x509cset.c b/src/lib/libcrypto/x509/x509cset.c
index 6cac440ea9..9d1646d5c8 100644
--- a/src/lib/libcrypto/x509/x509cset.c
+++ b/src/lib/libcrypto/x509/x509cset.c
@@ -129,6 +129,7 @@ int X509_CRL_sort(X509_CRL *c)
129 r=sk_X509_REVOKED_value(c->crl->revoked,i); 129 r=sk_X509_REVOKED_value(c->crl->revoked,i);
130 r->sequence=i; 130 r->sequence=i;
131 } 131 }
132 c->crl->enc.modified = 1;
132 return 1; 133 return 1;
133 } 134 }
134 135
diff --git a/src/lib/libcrypto/x509/x509name.c b/src/lib/libcrypto/x509/x509name.c
index 4c20e03ece..068abfe5f0 100644
--- a/src/lib/libcrypto/x509/x509name.c
+++ b/src/lib/libcrypto/x509/x509name.c
@@ -195,8 +195,8 @@ int X509_NAME_add_entry_by_NID(X509_NAME *name, int nid, int type,
195 return ret; 195 return ret;
196} 196}
197 197
198int X509_NAME_add_entry_by_txt(X509_NAME *name, char *field, int type, 198int X509_NAME_add_entry_by_txt(X509_NAME *name, const char *field, int type,
199 unsigned char *bytes, int len, int loc, int set) 199 const unsigned char *bytes, int len, int loc, int set)
200{ 200{
201 X509_NAME_ENTRY *ne; 201 X509_NAME_ENTRY *ne;
202 int ret; 202 int ret;
@@ -273,7 +273,7 @@ err:
273 } 273 }
274 274
275X509_NAME_ENTRY *X509_NAME_ENTRY_create_by_txt(X509_NAME_ENTRY **ne, 275X509_NAME_ENTRY *X509_NAME_ENTRY_create_by_txt(X509_NAME_ENTRY **ne,
276 char *field, int type, unsigned char *bytes, int len) 276 const char *field, int type, const unsigned char *bytes, int len)
277 { 277 {
278 ASN1_OBJECT *obj; 278 ASN1_OBJECT *obj;
279 X509_NAME_ENTRY *nentry; 279 X509_NAME_ENTRY *nentry;
@@ -309,7 +309,7 @@ X509_NAME_ENTRY *X509_NAME_ENTRY_create_by_NID(X509_NAME_ENTRY **ne, int nid,
309 } 309 }
310 310
311X509_NAME_ENTRY *X509_NAME_ENTRY_create_by_OBJ(X509_NAME_ENTRY **ne, 311X509_NAME_ENTRY *X509_NAME_ENTRY_create_by_OBJ(X509_NAME_ENTRY **ne,
312 ASN1_OBJECT *obj, int type, unsigned char *bytes, int len) 312 ASN1_OBJECT *obj, int type, const unsigned char *bytes, int len)
313 { 313 {
314 X509_NAME_ENTRY *ret; 314 X509_NAME_ENTRY *ret;
315 315
@@ -347,7 +347,7 @@ int X509_NAME_ENTRY_set_object(X509_NAME_ENTRY *ne, ASN1_OBJECT *obj)
347 } 347 }
348 348
349int X509_NAME_ENTRY_set_data(X509_NAME_ENTRY *ne, int type, 349int X509_NAME_ENTRY_set_data(X509_NAME_ENTRY *ne, int type,
350 unsigned char *bytes, int len) 350 const unsigned char *bytes, int len)
351 { 351 {
352 int i; 352 int i;
353 353
diff --git a/src/lib/libcrypto/x509/x_all.c b/src/lib/libcrypto/x509/x_all.c
index fb5015cd4d..ac6dea493a 100644
--- a/src/lib/libcrypto/x509/x_all.c
+++ b/src/lib/libcrypto/x509/x_all.c
@@ -103,6 +103,7 @@ int X509_REQ_sign(X509_REQ *x, EVP_PKEY *pkey, const EVP_MD *md)
103 103
104int X509_CRL_sign(X509_CRL *x, EVP_PKEY *pkey, const EVP_MD *md) 104int X509_CRL_sign(X509_CRL *x, EVP_PKEY *pkey, const EVP_MD *md)
105 { 105 {
106 x->crl->enc.modified = 1;
106 return(ASN1_item_sign(ASN1_ITEM_rptr(X509_CRL_INFO),x->crl->sig_alg, 107 return(ASN1_item_sign(ASN1_ITEM_rptr(X509_CRL_INFO),x->crl->sig_alg,
107 x->sig_alg, x->signature, x->crl,pkey,md)); 108 x->sig_alg, x->signature, x->crl,pkey,md));
108 } 109 }