@@ -305,44 +305,62 @@ int X509_supported_extension(X509_EXTENSION *ex)
305
305
return 0 ;
306
306
}
307
307
308
- static int setup_dp (X509 * x , DIST_POINT * dp )
308
+ /* return 1 on success, 0 if x is invalid, -1 on (internal) error */
309
+ static int setup_dp (const X509 * x , DIST_POINT * dp )
309
310
{
310
311
const X509_NAME * iname = NULL ;
311
312
int i ;
312
313
313
- if (dp -> reasons ) {
314
+ if (dp -> distpoint == NULL && sk_GENERAL_NAME_num (dp -> CRLissuer ) <= 0 ) {
315
+ X509err (0 , X509_R_INVALID_DISTPOINT );
316
+ return 0 ;
317
+ }
318
+ if (dp -> reasons != NULL ) {
314
319
if (dp -> reasons -> length > 0 )
315
320
dp -> dp_reasons = dp -> reasons -> data [0 ];
316
321
if (dp -> reasons -> length > 1 )
317
322
dp -> dp_reasons |= (dp -> reasons -> data [1 ] << 8 );
318
323
dp -> dp_reasons &= CRLDP_ALL_REASONS ;
319
- } else
324
+ } else {
320
325
dp -> dp_reasons = CRLDP_ALL_REASONS ;
321
- if (!dp -> distpoint || (dp -> distpoint -> type != 1 ))
326
+ }
327
+ if (dp -> distpoint == NULL || dp -> distpoint -> type != 1 )
322
328
return 1 ;
329
+
330
+ /* handle name fragment given by nameRelativeToCRLIssuer */
331
+ /*
332
+ * Note that the below way of determining iname is not really compliant
333
+ * with https://tools.ietf.org/html/rfc5280#section-4.2.1.13
334
+ * According to it, sk_GENERAL_NAME_num(dp->CRLissuer) MUST be <= 1
335
+ * and any CRLissuer could be of type different to GEN_DIRNAME.
336
+ */
323
337
for (i = 0 ; i < sk_GENERAL_NAME_num (dp -> CRLissuer ); i ++ ) {
324
338
GENERAL_NAME * gen = sk_GENERAL_NAME_value (dp -> CRLissuer , i );
339
+
325
340
if (gen -> type == GEN_DIRNAME ) {
326
341
iname = gen -> d .directoryName ;
327
342
break ;
328
343
}
329
344
}
330
- if (! iname )
345
+ if (iname == NULL )
331
346
iname = X509_get_issuer_name (x );
332
-
333
- return DIST_POINT_set_dpname (dp -> distpoint , iname );
347
+ return DIST_POINT_set_dpname (dp -> distpoint , iname ) ? 1 : -1 ;
334
348
}
335
349
350
+ /* return 1 on success, 0 if x is invalid, -1 on (internal) error */
336
351
static int setup_crldp (X509 * x )
337
352
{
338
353
int i ;
339
354
340
355
x -> crldp = X509_get_ext_d2i (x , NID_crl_distribution_points , & i , NULL );
341
356
if (x -> crldp == NULL && i != -1 )
342
357
return 0 ;
358
+
343
359
for (i = 0 ; i < sk_DIST_POINT_num (x -> crldp ); i ++ ) {
344
- if (!setup_dp (x , sk_DIST_POINT_value (x -> crldp , i )))
345
- return 0 ;
360
+ int res = setup_dp (x , sk_DIST_POINT_value (x -> crldp , i ));
361
+
362
+ if (res < 1 )
363
+ return res ;
346
364
}
347
365
return 1 ;
348
366
}
@@ -373,6 +391,7 @@ static int check_sig_alg_match(const EVP_PKEY *pkey, const X509 *subject)
373
391
/*
374
392
* Cache info on various X.509v3 extensions and further derived information,
375
393
* e.g., if cert 'x' is self-issued, in x->ex_flags and other internal fields.
394
+ * X509_SIG_INFO_VALID is set in x->flags if x->siginf was filled successfully.
376
395
* Set EXFLAG_INVALID and return 0 in case the certificate is invalid.
377
396
*/
378
397
int x509v3_cache_extensions (X509 * x )
@@ -384,6 +403,7 @@ int x509v3_cache_extensions(X509 *x)
384
403
EXTENDED_KEY_USAGE * extusage ;
385
404
X509_EXTENSION * ex ;
386
405
int i ;
406
+ int res ;
387
407
388
408
#ifdef tsan_ld_acq
389
409
/* fast lock-free check, see end of the function for details. */
@@ -398,30 +418,34 @@ int x509v3_cache_extensions(X509 *x)
398
418
}
399
419
ERR_set_mark ();
400
420
421
+ /* Cache the SHA1 digest of the cert */
401
422
if (!X509_digest (x , EVP_sha1 (), x -> sha1_hash , NULL ))
402
- x -> ex_flags |= EXFLAG_INVALID ;
423
+ /*
424
+ * Note that the cert is marked invalid also on internal malloc failure
425
+ * or on failure of EVP_MD_fetch(), potentially called by X509_digest().
426
+ */
427
+ x -> ex_flags |= EXFLAG_INVALID ;
403
428
404
429
/* V1 should mean no extensions ... */
405
430
if (X509_get_version (x ) == 0 )
406
431
x -> ex_flags |= EXFLAG_V1 ;
407
432
408
433
/* Handle basic constraints */
434
+ x -> ex_pathlen = -1 ;
409
435
if ((bs = X509_get_ext_d2i (x , NID_basic_constraints , & i , NULL )) != NULL ) {
410
436
if (bs -> ca )
411
437
x -> ex_flags |= EXFLAG_CA ;
412
438
if (bs -> pathlen != NULL ) {
439
+ /*
440
+ * the error case !bs->ca is checked by check_chain_extensions()
441
+ * in case ctx->param->flags & X509_V_FLAG_X509_STRICT
442
+ */
413
443
if (bs -> pathlen -> type == V_ASN1_NEG_INTEGER ) {
444
+ X509err (0 , X509V3_R_NEGATIVE_PATHLEN );
414
445
x -> ex_flags |= EXFLAG_INVALID ;
415
- x -> ex_pathlen = 0 ;
416
446
} else {
417
447
x -> ex_pathlen = ASN1_INTEGER_get (bs -> pathlen );
418
- if (!bs -> ca && x -> ex_pathlen != 0 ) {
419
- x -> ex_flags |= EXFLAG_INVALID ;
420
- x -> ex_pathlen = 0 ;
421
- }
422
448
}
423
- } else {
424
- x -> ex_pathlen = -1 ;
425
449
}
426
450
BASIC_CONSTRAINTS_free (bs );
427
451
x -> ex_flags |= EXFLAG_BCONS ;
@@ -436,17 +460,17 @@ int x509v3_cache_extensions(X509 *x)
436
460
|| X509_get_ext_by_NID (x , NID_issuer_alt_name , -1 ) >= 0 ) {
437
461
x -> ex_flags |= EXFLAG_INVALID ;
438
462
}
439
- if (pci -> pcPathLengthConstraint ) {
463
+ if (pci -> pcPathLengthConstraint != NULL )
440
464
x -> ex_pcpathlen = ASN1_INTEGER_get (pci -> pcPathLengthConstraint );
441
- } else
465
+ else
442
466
x -> ex_pcpathlen = -1 ;
443
467
PROXY_CERT_INFO_EXTENSION_free (pci );
444
468
x -> ex_flags |= EXFLAG_PROXY ;
445
469
} else if (i != -1 ) {
446
470
x -> ex_flags |= EXFLAG_INVALID ;
447
471
}
448
472
449
- /* Handle ( basic and extended) key usage */
473
+ /* Handle basic key usage */
450
474
if ((usage = X509_get_ext_d2i (x , NID_key_usage , & i , NULL )) != NULL ) {
451
475
x -> ex_kusage = 0 ;
452
476
if (usage -> length > 0 ) {
@@ -456,9 +480,16 @@ int x509v3_cache_extensions(X509 *x)
456
480
}
457
481
x -> ex_flags |= EXFLAG_KUSAGE ;
458
482
ASN1_BIT_STRING_free (usage );
483
+ /* Check for empty key usage according to RFC 5280 section 4.2.1.3 */
484
+ if (x -> ex_kusage == 0 ) {
485
+ X509err (0 , X509V3_R_EMPTY_KEY_USAGE );
486
+ x -> ex_flags |= EXFLAG_INVALID ;
487
+ }
459
488
} else if (i != -1 ) {
460
489
x -> ex_flags |= EXFLAG_INVALID ;
461
490
}
491
+
492
+ /* Handle extended key usage */
462
493
x -> ex_xkusage = 0 ;
463
494
if ((extusage = X509_get_ext_d2i (x , NID_ext_key_usage , & i , NULL )) != NULL ) {
464
495
x -> ex_flags |= EXFLAG_XKUSAGE ;
@@ -493,6 +524,7 @@ int x509v3_cache_extensions(X509 *x)
493
524
x -> ex_xkusage |= XKU_ANYEKU ;
494
525
break ;
495
526
default :
527
+ /* ignore unknown extended key usage */
496
528
break ;
497
529
}
498
530
}
@@ -517,6 +549,7 @@ int x509v3_cache_extensions(X509 *x)
517
549
x -> skid = X509_get_ext_d2i (x , NID_subject_key_identifier , & i , NULL );
518
550
if (x -> skid == NULL && i != -1 )
519
551
x -> ex_flags |= EXFLAG_INVALID ;
552
+
520
553
x -> akid = X509_get_ext_d2i (x , NID_authority_key_identifier , & i , NULL );
521
554
if (x -> akid == NULL && i != -1 )
522
555
x -> ex_flags |= EXFLAG_INVALID ;
@@ -538,8 +571,13 @@ int x509v3_cache_extensions(X509 *x)
538
571
x -> nc = X509_get_ext_d2i (x , NID_name_constraints , & i , NULL );
539
572
if (x -> nc == NULL && i != -1 )
540
573
x -> ex_flags |= EXFLAG_INVALID ;
541
- if (!setup_crldp (x ))
574
+
575
+ /* Handle CRL distribution point entries */
576
+ res = setup_crldp (x );
577
+ if (res == 0 )
542
578
x -> ex_flags |= EXFLAG_INVALID ;
579
+ else if (res < 0 )
580
+ goto err ;
543
581
544
582
#ifndef OPENSSL_NO_RFC3779
545
583
x -> rfc3779_addr = X509_get_ext_d2i (x , NID_sbgp_ipAddrBlock , & i , NULL );
@@ -551,8 +589,7 @@ int x509v3_cache_extensions(X509 *x)
551
589
#endif
552
590
for (i = 0 ; i < X509_get_ext_count (x ); i ++ ) {
553
591
ex = X509_get_ext (x , i );
554
- if (OBJ_obj2nid (X509_EXTENSION_get_object (ex ))
555
- == NID_freshest_crl )
592
+ if (OBJ_obj2nid (X509_EXTENSION_get_object (ex )) == NID_freshest_crl )
556
593
x -> ex_flags |= EXFLAG_FRESHEST ;
557
594
if (!X509_EXTENSION_get_critical (ex ))
558
595
continue ;
@@ -562,7 +599,8 @@ int x509v3_cache_extensions(X509 *x)
562
599
}
563
600
}
564
601
565
- x509_init_sig_info (x );
602
+ /* Set x->siginf, ignoring errors due to unsupported algos */
603
+ (void )x509_init_sig_info (x );
566
604
567
605
x -> ex_flags |= EXFLAG_SET ; /* indicate that cert has been processed */
568
606
#ifdef tsan_st_rel
@@ -574,9 +612,16 @@ int x509v3_cache_extensions(X509 *x)
574
612
*/
575
613
#endif
576
614
ERR_pop_to_mark ();
577
- CRYPTO_THREAD_unlock (x -> lock );
615
+ if ((x -> ex_flags & EXFLAG_INVALID ) == 0 ) {
616
+ CRYPTO_THREAD_unlock (x -> lock );
617
+ return 1 ;
618
+ }
619
+ X509err (0 , X509V3_R_INVALID_CERTIFICATE );
578
620
579
- return (x -> ex_flags & EXFLAG_INVALID ) == 0 ;
621
+ err :
622
+ x -> ex_flags |= EXFLAG_SET ; /* indicate that cert has been processed */
623
+ CRYPTO_THREAD_unlock (x -> lock );
624
+ return 0 ;
580
625
}
581
626
582
627
/*-
0 commit comments