diff options
| author | djm <> | 2005-04-29 05:39:33 +0000 |
|---|---|---|
| committer | djm <> | 2005-04-29 05:39:33 +0000 |
| commit | 68edd00d9258df93b1366c71ac124e0cadf7bc08 (patch) | |
| tree | 3ce4ae2a9747bbc11aed1f95f9bbea92c41f8683 /src/lib/libcrypto/x509 | |
| parent | f396ed0f5ce0af56bfde2e75e15cf1f52924c779 (diff) | |
| download | openbsd-68edd00d9258df93b1366c71ac124e0cadf7bc08.tar.gz openbsd-68edd00d9258df93b1366c71ac124e0cadf7bc08.tar.bz2 openbsd-68edd00d9258df93b1366c71ac124e0cadf7bc08.zip | |
resolve conflicts
Diffstat (limited to 'src/lib/libcrypto/x509')
| -rw-r--r-- | src/lib/libcrypto/x509/by_file.c | 4 | ||||
| -rw-r--r-- | src/lib/libcrypto/x509/x509.h | 11 | ||||
| -rw-r--r-- | src/lib/libcrypto/x509/x509_cmp.c | 48 | ||||
| -rw-r--r-- | src/lib/libcrypto/x509/x509_r2x.c | 6 | ||||
| -rw-r--r-- | src/lib/libcrypto/x509/x509_req.c | 35 | ||||
| -rw-r--r-- | src/lib/libcrypto/x509/x509_txt.c | 13 | ||||
| -rw-r--r-- | src/lib/libcrypto/x509/x509_vfy.c | 131 | ||||
| -rw-r--r-- | src/lib/libcrypto/x509/x509_vfy.h | 8 | ||||
| -rw-r--r-- | src/lib/libcrypto/x509/x509cset.c | 1 | ||||
| -rw-r--r-- | src/lib/libcrypto/x509/x509name.c | 10 | ||||
| -rw-r--r-- | src/lib/libcrypto/x509/x_all.c | 1 |
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 | ||
| 415 | struct X509_crl_st | 416 | struct X509_crl_st |
| @@ -1037,18 +1038,18 @@ int X509_NAME_add_entry_by_OBJ(X509_NAME *name, ASN1_OBJECT *obj, int type, | |||
| 1037 | int X509_NAME_add_entry_by_NID(X509_NAME *name, int nid, int type, | 1038 | int 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); |
| 1039 | X509_NAME_ENTRY *X509_NAME_ENTRY_create_by_txt(X509_NAME_ENTRY **ne, | 1040 | X509_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); |
| 1041 | X509_NAME_ENTRY *X509_NAME_ENTRY_create_by_NID(X509_NAME_ENTRY **ne, int nid, | 1042 | X509_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); |
| 1043 | int X509_NAME_add_entry_by_txt(X509_NAME *name, char *field, int type, | 1044 | int 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); |
| 1045 | X509_NAME_ENTRY *X509_NAME_ENTRY_create_by_OBJ(X509_NAME_ENTRY **ne, | 1046 | X509_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); |
| 1048 | int X509_NAME_ENTRY_set_object(X509_NAME_ENTRY *ne, | 1049 | int X509_NAME_ENTRY_set_object(X509_NAME_ENTRY *ne, |
| 1049 | ASN1_OBJECT *obj); | 1050 | ASN1_OBJECT *obj); |
| 1050 | int X509_NAME_ENTRY_set_data(X509_NAME_ENTRY *ne, int type, | 1051 | int X509_NAME_ENTRY_set_data(X509_NAME_ENTRY *ne, int type, |
| 1051 | unsigned char *bytes, int len); | 1052 | const unsigned char *bytes, int len); |
| 1052 | ASN1_OBJECT * X509_NAME_ENTRY_get_object(X509_NAME_ENTRY *ne); | 1053 | ASN1_OBJECT * X509_NAME_ENTRY_get_object(X509_NAME_ENTRY *ne); |
| 1053 | ASN1_STRING * X509_NAME_ENTRY_get_data(X509_NAME_ENTRY *ne); | 1054 | ASN1_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 | ||
| 257 | static 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 | |||
| 257 | int X509_NAME_cmp(const X509_NAME *a, const X509_NAME *b) | 268 | int 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 | ||
| 121 | static int ext_nid_list[] = { NID_ms_ext_req, NID_ext_req, NID_undef}; | 121 | static int ext_nid_list[] = { NID_ext_req, NID_ms_ext_req, NID_undef}; |
| 122 | 122 | ||
| 123 | static int *ext_nids = ext_nid_list; | 123 | static int *ext_nids = ext_nid_list; |
| 124 | 124 | ||
| @@ -143,32 +143,33 @@ void X509_REQ_set_extension_nids(int *nids) | |||
| 143 | } | 143 | } |
| 144 | 144 | ||
| 145 | STACK_OF(X509_EXTENSION) *X509_REQ_get_extensions(X509_REQ *req) | 145 | STACK_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 @@ | |||
| 73 | static int null_callback(int ok,X509_STORE_CTX *e); | 73 | static int null_callback(int ok,X509_STORE_CTX *e); |
| 74 | static int check_issued(X509_STORE_CTX *ctx, X509 *x, X509 *issuer); | 74 | static int check_issued(X509_STORE_CTX *ctx, X509 *x, X509 *issuer); |
| 75 | static X509 *find_issuer(X509_STORE_CTX *ctx, STACK_OF(X509) *sk, X509 *x); | 75 | static X509 *find_issuer(X509_STORE_CTX *ctx, STACK_OF(X509) *sk, X509 *x); |
| 76 | static int check_chain_purpose(X509_STORE_CTX *ctx); | 76 | static int check_chain_extensions(X509_STORE_CTX *ctx); |
| 77 | static int check_trust(X509_STORE_CTX *ctx); | 77 | static int check_trust(X509_STORE_CTX *ctx); |
| 78 | static int check_revocation(X509_STORE_CTX *ctx); | 78 | static int check_revocation(X509_STORE_CTX *ctx); |
| 79 | static int check_cert(X509_STORE_CTX *ctx); | 79 | static 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 | ||
| 374 | static int check_chain_purpose(X509_STORE_CTX *ctx) | 374 | static 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 | ||
| 328 | int X509_OBJECT_idx_by_subject(STACK_OF(X509_OBJECT) *h, int type, | 334 | int 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 | ||
| 198 | int X509_NAME_add_entry_by_txt(X509_NAME *name, char *field, int type, | 198 | int 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 | ||
| 275 | X509_NAME_ENTRY *X509_NAME_ENTRY_create_by_txt(X509_NAME_ENTRY **ne, | 275 | X509_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 | ||
| 311 | X509_NAME_ENTRY *X509_NAME_ENTRY_create_by_OBJ(X509_NAME_ENTRY **ne, | 311 | X509_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 | ||
| 349 | int X509_NAME_ENTRY_set_data(X509_NAME_ENTRY *ne, int type, | 349 | int 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 | ||
| 104 | int X509_CRL_sign(X509_CRL *x, EVP_PKEY *pkey, const EVP_MD *md) | 104 | int 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 | } |
