@@ -515,35 +515,36 @@ static int s_get_ce_element(const ltc_asn1_list *oid, st_ce_value *ce)
515515
516516static int s_get_ce_value (const ltc_asn1_list * os , st_ce_value * ce )
517517{
518+ ltc_asn1_list * value = NULL ;
518519 int err = CRYPT_OK ;
519- ce -> value .asn1 = os ;
520520 if (ce -> ce == NULL ) {
521+ ce -> value .asn1 = os ;
521522 ce -> value .type = LTC_X509_UNKNOWN ;
522523 return CRYPT_OK ;
523524 }
525+ ce -> value .type = ce -> ce -> detail ;
524526 if (ce -> ce -> u .ce .type == LTC_ASN1_SEQUENCE ) {
525- ltc_asn1_list * value ;
526527 unsigned long len = os -> size ;
527528 if ((err = der_decode_sequence_flexi_limited (os -> data , & len , 2 , & value )) != CRYPT_OK ) {
528529 return err ;
529530 }
530- if (value -> type != LTC_ASN1_SEQUENCE ) {
531- der_free_sequence_flexi (value );
532- return CRYPT_INVALID_PACKET ;
533- } else {
531+ if (value -> type == LTC_ASN1_SEQUENCE ) {
534532 err = ce -> ce -> u .ce .handler (value , & ce -> value );
533+ } else {
534+ err = CRYPT_INVALID_PACKET ;
535535 }
536536 if (err != CRYPT_OK ) {
537537 der_free_sequence_flexi (value );
538538 return err ;
539539 }
540- /* store the flexi tree root so it can be freed in s_free_extension, handlers store pointers into this tree */
541- ce -> value .asn1 = value ;
542540 } else {
543541 err = ce -> ce -> u .ce .handler (os , & ce -> value );
542+ value = (ltc_asn1_list * )os ;
544543 }
545544 if (err == CRYPT_OK ) {
546- ce -> value .type = ce -> ce -> detail ;
545+ ce -> value .asn1 = value ;
546+ } else {
547+ ce -> value .type = LTC_X509_UNKNOWN ;
547548 }
548549 return err ;
549550}
@@ -555,23 +556,24 @@ static LTC_INLINE void s_free_extension(const ltc_x509_extension *ext)
555556 s_free (ext -> u .authority_key_id .key_identifier .str );
556557 s_free (ext -> u .authority_key_id .authority_cert_issuer .str );
557558 s_free (ext -> u .authority_key_id .authority_cert_serial_number .str );
558- der_free_sequence_flexi ((void * )ext -> asn1 );
559559 break ;
560560 case LTC_X509_CE_SUBJECT_KEY_ID :
561561 s_free (ext -> u .subject_key_identifier .str );
562562 break ;
563563 case LTC_X509_CE_SUBJECT_ALT_NAME :
564564 s_free_x509_string_array (ext -> u .subject_alt_name .names , ext -> u .subject_alt_name .names_num );
565- der_free_sequence_flexi ((void * )ext -> asn1 );
566565 break ;
567566 case LTC_X509_CE_BASIC_CONSTRAINTS :
568567 case LTC_X509_CE_EXT_KEY_USAGE :
569- der_free_sequence_flexi ((void * )ext -> asn1 );
570- break ;
571568 case LTC_X509_CE_KEY_USAGE :
572569 default :
573570 break ;
574571 }
572+ if (ext -> type != LTC_X509_UNKNOWN
573+ && ext -> asn1
574+ && ext -> asn1 -> type == LTC_ASN1_SEQUENCE ) {
575+ der_free_sequence_flexi ((void * )ext -> asn1 );
576+ }
575577}
576578
577579static LTC_INLINE void s_free_extensions (const ltc_x509_extension * extensions , unsigned long num )
@@ -588,6 +590,19 @@ void x509_free_extensions(const ltc_x509_extensions *extensions)
588590 s_free_extensions (extensions -> extensions , extensions -> extensions_num );
589591}
590592
593+ /* RFC 5280, Ch. 4.1. Basic Certificate Fields
594+ * [...]
595+ * Extensions ::= SEQUENCE SIZE (1..MAX) OF Extension
596+ *
597+ * Extension ::= SEQUENCE {
598+ * extnID OBJECT IDENTIFIER,
599+ * critical BOOLEAN DEFAULT FALSE,
600+ * extnValue OCTET STRING
601+ * -- contains the DER encoding of an ASN.1 value
602+ * -- corresponding to the extension type identified
603+ * -- by extnID
604+ * }
605+ */
591606int x509_get_extensions (const ltc_asn1_list * seq , ltc_x509_extensions * extensions )
592607{
593608 ltc_x509_extension * extensions_ ;
0 commit comments