Split x509_crl_parse_der() out of x509_crl_parse()

This commit is contained in:
Manuel Pégourié-Gonnard 2014-11-19 16:58:28 +01:00
parent 57a5d60abb
commit 426d4ae7ff
3 changed files with 86 additions and 76 deletions

View file

@ -15,6 +15,7 @@ Security
Features Features
* Add function pk_check_pair() to test if public and private keys match. * Add function pk_check_pair() to test if public and private keys match.
* Add x509_crl_parse_der().
Bugfix Bugfix
* User set CFLAGS were ignore by Cmake with gcc (introduced in 1.3.9, found * User set CFLAGS were ignore by Cmake with gcc (introduced in 1.3.9, found

View file

@ -100,11 +100,23 @@ typedef struct _x509_crl
x509_crl; x509_crl;
/** /**
* \brief Parse one or more CRLs and add them * \brief Parse a DER-encoded CRL and append it to the chained list
* to the chained list
* *
* \param chain points to the start of the chain * \param chain points to the start of the chain
* \param buf buffer holding the CRL data * \param buf buffer holding the CRL data in DER format
* \param buflen size of the buffer
*
* \return 0 if successful, or a specific X509 or PEM error code
*/
int x509_crl_parse_der( x509_crl *chain,
const unsigned char *buf, size_t buflen );
/**
* \brief Parse one or more CRLs and append them to the chained list
*
* \note Mutliple CRLs are accepted only if using PEM format
*
* \param chain points to the start of the chain
* \param buf buffer holding the CRL data in PEM or DER format
* \param buflen size of the buffer * \param buflen size of the buffer
* *
* \return 0 if successful, or a specific X509 or PEM error code * \return 0 if successful, or a specific X509 or PEM error code
@ -113,11 +125,12 @@ int x509_crl_parse( x509_crl *chain, const unsigned char *buf, size_t buflen );
#if defined(POLARSSL_FS_IO) #if defined(POLARSSL_FS_IO)
/** /**
* \brief Load one or more CRLs and add them * \brief Load one or more CRLs and append them to the chained list
* to the chained list *
* \note Mutliple CRLs are accepted only if using PEM format
* *
* \param chain points to the start of the chain * \param chain points to the start of the chain
* \param path filename to read the CRLs from * \param path filename to read the CRLs from (in PEM or DER encoding)
* *
* \return 0 if successful, or a specific X509 or PEM error code * \return 0 if successful, or a specific X509 or PEM error code
*/ */

View file

@ -252,25 +252,16 @@ static int x509_get_entries( unsigned char **p,
} }
/* /*
* Parse one or more CRLs and add them to the chained list * Parse one CRLs in DER format and append it to the chained list
*/ */
int x509_crl_parse( x509_crl *chain, const unsigned char *buf, size_t buflen ) int x509_crl_parse_der( x509_crl *chain,
const unsigned char *buf, size_t buflen )
{ {
int ret; int ret;
size_t len; size_t len;
unsigned char *p, *end; unsigned char *p, *end;
x509_crl *crl;
x509_buf sig_params1, sig_params2; x509_buf sig_params1, sig_params2;
x509_crl *crl = chain;
#if defined(POLARSSL_PEM_PARSE_C)
size_t use_len;
pem_context pem;
#endif
memset( &sig_params1, 0, sizeof( x509_buf ) );
memset( &sig_params2, 0, sizeof( x509_buf ) );
crl = chain;
/* /*
* Check for valid input * Check for valid input
@ -278,12 +269,15 @@ int x509_crl_parse( x509_crl *chain, const unsigned char *buf, size_t buflen )
if( crl == NULL || buf == NULL ) if( crl == NULL || buf == NULL )
return( POLARSSL_ERR_X509_BAD_INPUT_DATA ); return( POLARSSL_ERR_X509_BAD_INPUT_DATA );
while( crl->version != 0 && crl->next != NULL ) memset( &sig_params1, 0, sizeof( x509_buf ) );
crl = crl->next; memset( &sig_params2, 0, sizeof( x509_buf ) );
/* /*
* Add new CRL on the end of the chain if needed. * Add new CRL on the end of the chain if needed.
*/ */
while( crl->version != 0 && crl->next != NULL )
crl = crl->next;
if( crl->version != 0 && crl->next == NULL ) if( crl->version != 0 && crl->next == NULL )
{ {
crl->next = (x509_crl *) polarssl_malloc( sizeof( x509_crl ) ); crl->next = (x509_crl *) polarssl_malloc( sizeof( x509_crl ) );
@ -298,53 +292,18 @@ int x509_crl_parse( x509_crl *chain, const unsigned char *buf, size_t buflen )
crl = crl->next; crl = crl->next;
} }
#if defined(POLARSSL_PEM_PARSE_C) /*
pem_init( &pem ); * Copy raw DER-encoded CRL
ret = pem_read_buffer( &pem, */
"-----BEGIN X509 CRL-----", if( ( p = polarssl_malloc( buflen ) ) == NULL )
"-----END X509 CRL-----", return( POLARSSL_ERR_X509_MALLOC_FAILED );
buf, NULL, 0, &use_len );
if( ret == 0 ) memcpy( p, buf, buflen );
{
/*
* Was PEM encoded
*/
buflen -= use_len;
buf += use_len;
/*
* Steal PEM buffer
*/
p = pem.buf;
pem.buf = NULL;
len = pem.buflen;
pem_free( &pem );
}
else if( ret != POLARSSL_ERR_PEM_NO_HEADER_FOOTER_PRESENT )
{
pem_free( &pem );
return( ret );
}
else
#endif /* POLARSSL_PEM_PARSE_C */
{
/*
* nope, copy the raw DER data
*/
p = (unsigned char *) polarssl_malloc( len = buflen );
if( p == NULL )
return( POLARSSL_ERR_X509_MALLOC_FAILED );
memcpy( p, buf, buflen );
buflen = 0;
}
crl->raw.p = p; crl->raw.p = p;
crl->raw.len = len; crl->raw.len = buflen;
end = p + len;
end = p + buflen;
/* /*
* CertificateList ::= SEQUENCE { * CertificateList ::= SEQUENCE {
@ -522,21 +481,58 @@ int x509_crl_parse( x509_crl *chain, const unsigned char *buf, size_t buflen )
POLARSSL_ERR_ASN1_LENGTH_MISMATCH ); POLARSSL_ERR_ASN1_LENGTH_MISMATCH );
} }
if( buflen > 0 ) return( 0 );
}
/*
* Parse one or more CRLs and add them to the chained list
*/
int x509_crl_parse( x509_crl *chain, const unsigned char *buf, size_t buflen )
{
int ret;
if( chain == NULL || buf == NULL )
return( POLARSSL_ERR_X509_BAD_INPUT_DATA );
#if defined(POLARSSL_PEM_PARSE_C)
size_t use_len;
pem_context pem;
pem_init( &pem );
ret = pem_read_buffer( &pem,
"-----BEGIN X509 CRL-----",
"-----END X509 CRL-----",
buf, NULL, 0, &use_len );
if( ret == 0 )
{ {
crl->next = (x509_crl *) polarssl_malloc( sizeof( x509_crl ) ); /*
* Was PEM encoded
*/
buflen -= use_len;
buf += use_len;
if( crl->next == NULL ) if( ( ret = x509_crl_parse_der( chain, pem.buf, pem.buflen ) ) != 0 )
{ return( ret );
x509_crl_free( crl );
return( POLARSSL_ERR_X509_MALLOC_FAILED );
}
x509_crl_init( crl->next ); pem_free( &pem );
crl = crl->next;
return( x509_crl_parse( crl, buf, buflen ) );
} }
else if( ret != POLARSSL_ERR_PEM_NO_HEADER_FOOTER_PRESENT )
{
pem_free( &pem );
return( ret );
}
else
#endif /* POLARSSL_PEM_PARSE_C */
{
if( ( ret = x509_crl_parse_der( chain, buf, buflen ) ) != 0 )
return( ret );
buflen = 0;
}
if( buflen > 0 )
return( x509_crl_parse( chain, buf, buflen ) );
return( 0 ); return( 0 );
} }