minor mbedtls update

This brings it in line with 2.6.0. Previously it had been taken from a
development branch somewhere between 2.5.1 and 2.6.0.

Only return VERIFY_FAILED from a single point

Everything else is a fatal error. Also improve documentation about that for
the vrfy callback.

Improve comments

Update doc of return value of verify()

Fix potential integer overflow parsing DER CRL

This patch prevents a potential signed integer overflow during the
CRL version verification checks.

Fix potential integer overflow parsing DER CRT

This patch prevents a potential signed integer overflow during the
certificate version verification checks.

Prevent signed integer overflow in CSR parsing

Modify the function mbedtls_x509_csr_parse_der() so that it checks the
parsed CSR version integer before it increments the value. This prevents
a potential signed integer overflow, as these have undefined behaviour
in the C standard.

Rename time and index parameter to avoid name conflict.

As noted in #557, several functions use 'index' resp. 'time'
as parameter names in their declaration and/or definition, causing name
conflicts with the functions in the C standard library of the same
name some compilers warn about.

This commit renames the arguments accordingly.

Update version number to 2.6.0
This commit is contained in:
Eric Warmenhoven 2025-06-09 10:42:37 -04:00
parent a21643b7fa
commit e8da8f8d29
11 changed files with 94 additions and 70 deletions

View File

@ -81,24 +81,24 @@ int mbedtls_entropy_add_source( mbedtls_entropy_context *ctx,
mbedtls_entropy_f_source_ptr f_source, void *p_source,
size_t threshold, int strong )
{
int index, ret = 0;
int idx, ret = 0;
#if defined(MBEDTLS_THREADING_C)
if( ( ret = mbedtls_mutex_lock( &ctx->mutex ) ) != 0 )
return( ret );
#endif
index = ctx->source_count;
if( index >= MBEDTLS_ENTROPY_MAX_SOURCES )
idx = ctx->source_count;
if( idx >= MBEDTLS_ENTROPY_MAX_SOURCES )
{
ret = MBEDTLS_ERR_ENTROPY_MAX_SOURCES;
goto exit;
}
ctx->source[index].f_source = f_source;
ctx->source[index].p_source = p_source;
ctx->source[index].threshold = threshold;
ctx->source[index].strong = strong;
ctx->source[idx].f_source = f_source;
ctx->source[idx].p_source = p_source;
ctx->source[idx].threshold = threshold;
ctx->source[idx].strong = strong;
ctx->source_count++;

View File

@ -461,7 +461,7 @@ int mbedtls_ecp_tls_write_point( const mbedtls_ecp_group *grp, const mbedtls_ecp
* \brief Set a group using well-known domain parameters
*
* \param grp Destination group
* \param index Index in the list of well-known domain parameters
* \param id Index in the list of well-known domain parameters
*
* \return 0 if successful,
* MBEDTLS_ERR_MPI_XXX if initialization failed
@ -470,7 +470,7 @@ int mbedtls_ecp_tls_write_point( const mbedtls_ecp_group *grp, const mbedtls_ecp
* \note Index should be a value of RFC 4492's enum NamedCurve,
* usually in the form of a MBEDTLS_ECP_DP_XXX macro.
*/
int mbedtls_ecp_group_load( mbedtls_ecp_group *grp, mbedtls_ecp_group_id index );
int mbedtls_ecp_group_load( mbedtls_ecp_group *grp, mbedtls_ecp_group_id id );
/**
* \brief Set a group from a TLS ECParameters record

View File

@ -1041,7 +1041,7 @@ void mbedtls_ssl_conf_authmode( mbedtls_ssl_config *conf, int authmode );
*
* If set, the verify callback is called for each
* certificate in the chain. For implementation
* information, please see \c x509parse_verify()
* information, please see \c mbedtls_x509_crt_verify()
*
* \param conf SSL configuration
* \param f_vrfy verification function

View File

@ -38,17 +38,17 @@
* Major, Minor, Patchlevel
*/
#define MBEDTLS_VERSION_MAJOR 2
#define MBEDTLS_VERSION_MINOR 5
#define MBEDTLS_VERSION_PATCH 1
#define MBEDTLS_VERSION_MINOR 6
#define MBEDTLS_VERSION_PATCH 0
/**
* The single version number has the following structure:
* MMNNPP00
* Major version | Minor version | Patch version
*/
#define MBEDTLS_VERSION_NUMBER 0x02050100
#define MBEDTLS_VERSION_STRING "2.5.1"
#define MBEDTLS_VERSION_STRING_FULL "mbed TLS 2.5.1"
#define MBEDTLS_VERSION_NUMBER 0x02060000
#define MBEDTLS_VERSION_STRING "2.6.0"
#define MBEDTLS_VERSION_STRING_FULL "mbed TLS 2.6.0"
#if defined(MBEDTLS_VERSION_C)

View File

@ -76,6 +76,7 @@
#define MBEDTLS_ERR_X509_ALLOC_FAILED -0x2880 /**< Allocation of memory failed. */
#define MBEDTLS_ERR_X509_FILE_IO_ERROR -0x2900 /**< Read/write of file failed. */
#define MBEDTLS_ERR_X509_BUFFER_TOO_SMALL -0x2980 /**< Destination buffer is too small. */
#define MBEDTLS_ERR_X509_FATAL_ERROR -0x3000 /**< A fatal error occured, eg the chain is too long or the vrfy callback failed. */
/* \} name */
/**
@ -246,12 +247,12 @@ int mbedtls_x509_serial_gets( char *buf, size_t size, const mbedtls_x509_buf *se
* \note Intended usage is "if( is_past( valid_to ) ) ERROR".
* Hence the return value of 1 if on internal errors.
*
* \param time mbedtls_x509_time to check
* \param to mbedtls_x509_time to check
*
* \return 1 if the given time is in the past or an error occured,
* 0 otherwise.
*/
int mbedtls_x509_time_is_past( const mbedtls_x509_time *time );
int mbedtls_x509_time_is_past( const mbedtls_x509_time *to );
/**
* \brief Check a given mbedtls_x509_time against the system time
@ -260,12 +261,12 @@ int mbedtls_x509_time_is_past( const mbedtls_x509_time *time );
* \note Intended usage is "if( is_future( valid_from ) ) ERROR".
* Hence the return value of 1 if on internal errors.
*
* \param time mbedtls_x509_time to check
* \param from mbedtls_x509_time to check
*
* \return 1 if the given time is in the future or an error occured,
* 0 otherwise.
*/
int mbedtls_x509_time_is_future( const mbedtls_x509_time *time );
int mbedtls_x509_time_is_future( const mbedtls_x509_time *from );
/**
* \brief Checkup routine
@ -294,7 +295,7 @@ int mbedtls_x509_get_sig_alg( const mbedtls_x509_buf *sig_oid, const mbedtls_x50
mbedtls_md_type_t *md_alg, mbedtls_pk_type_t *pk_alg,
void **sig_opts );
int mbedtls_x509_get_time( unsigned char **p, const unsigned char *end,
mbedtls_x509_time *time );
mbedtls_x509_time *t );
int mbedtls_x509_get_serial( unsigned char **p, const unsigned char *end,
mbedtls_x509_buf *serial );
int mbedtls_x509_get_ext( unsigned char **p, const unsigned char *end,

View File

@ -267,7 +267,13 @@ int mbedtls_x509_crt_verify_info( char *buf, size_t size, const char *prefix,
*
* All flags left after returning from the callback
* are also returned to the application. The function should
* return 0 for anything but a fatal error.
* return 0 for anything (including invalid certificates)
* other than fatal error, as a non-zero return code
* immediately aborts the verification process. For fatal
* errors, a specific error code should be used (different
* from MBEDTLS_ERR_X509_CERT_VERIFY_FAILED which should not
* be returned at this point), or MBEDTLS_ERR_X509_FATAL_ERROR
* can be used if no better code is available.
*
* \note In case verification failed, the results can be displayed
* using \c mbedtls_x509_crt_verify_info()
@ -289,12 +295,13 @@ int mbedtls_x509_crt_verify_info( char *buf, size_t size, const char *prefix,
* \param f_vrfy verification function
* \param p_vrfy verification parameter
*
* \return 0 if successful or MBEDTLS_ERR_X509_CERT_VERIFY_FAILED
* in which case *flags will have one or more
* MBEDTLS_X509_BADCERT_XXX or MBEDTLS_X509_BADCRL_XXX flags
* set,
* or another error in case of a fatal error encountered
* during the verification process.
* \return 0 (and flags set to 0) if the chain was verified and valid,
* MBEDTLS_ERR_X509_CERT_VERIFY_FAILED if the chain was verified
* but found to be invalid, in which case *flags will have one
* or more MBEDTLS_X509_BADCERT_XXX or MBEDTLS_X509_BADCRL_XXX
* flags set, or another error (and flags set to 0xffffffff)
* in case of a fatal error encountered during the
* verification process.
*/
int mbedtls_x509_crt_verify( mbedtls_x509_crt *crt,
mbedtls_x509_crt *trust_ca,

44
deps/mbedtls/x509.c vendored
View File

@ -487,25 +487,25 @@ static int x509_parse_int( unsigned char **p, size_t n, int *res )
return( 0 );
}
static int x509_date_is_valid(const mbedtls_x509_time *time)
static int x509_date_is_valid(const mbedtls_x509_time *t)
{
int ret = MBEDTLS_ERR_X509_INVALID_DATE;
CHECK_RANGE( 0, 9999, time->year );
CHECK_RANGE( 0, 23, time->hour );
CHECK_RANGE( 0, 59, time->min );
CHECK_RANGE( 0, 59, time->sec );
CHECK_RANGE( 0, 9999, t->year );
CHECK_RANGE( 0, 23, t->hour );
CHECK_RANGE( 0, 59, t->min );
CHECK_RANGE( 0, 59, t->sec );
switch( time->mon )
switch( t->mon )
{
case 1: case 3: case 5: case 7: case 8: case 10: case 12:
CHECK_RANGE( 1, 31, time->day );
CHECK_RANGE( 1, 31, t->day );
break;
case 4: case 6: case 9: case 11:
CHECK_RANGE( 1, 30, time->day );
CHECK_RANGE( 1, 30, t->day );
break;
case 2:
CHECK_RANGE( 1, 28 + (time->year % 4 == 0), time->day );
CHECK_RANGE( 1, 28 + (t->year % 4 == 0), t->day );
break;
default:
return( ret );
@ -519,7 +519,7 @@ static int x509_date_is_valid(const mbedtls_x509_time *time)
* field.
*/
static int x509_parse_time( unsigned char **p, size_t len, size_t yearlen,
mbedtls_x509_time *time )
mbedtls_x509_time *tm )
{
int ret;
@ -533,26 +533,26 @@ static int x509_parse_time( unsigned char **p, size_t len, size_t yearlen,
/*
* Parse year, month, day, hour, minute
*/
CHECK( x509_parse_int( p, yearlen, &time->year ) );
CHECK( x509_parse_int( p, yearlen, &tm->year ) );
if ( 2 == yearlen )
{
if ( time->year < 50 )
time->year += 100;
if ( tm->year < 50 )
tm->year += 100;
time->year += 1900;
tm->year += 1900;
}
CHECK( x509_parse_int( p, 2, &time->mon ) );
CHECK( x509_parse_int( p, 2, &time->day ) );
CHECK( x509_parse_int( p, 2, &time->hour ) );
CHECK( x509_parse_int( p, 2, &time->min ) );
CHECK( x509_parse_int( p, 2, &tm->mon ) );
CHECK( x509_parse_int( p, 2, &tm->day ) );
CHECK( x509_parse_int( p, 2, &tm->hour ) );
CHECK( x509_parse_int( p, 2, &tm->min ) );
/*
* Parse seconds if present
*/
if ( len >= 2 )
{
CHECK( x509_parse_int( p, 2, &time->sec ) );
CHECK( x509_parse_int( p, 2, &tm->sec ) );
len -= 2;
}
else
@ -573,7 +573,7 @@ static int x509_parse_time( unsigned char **p, size_t len, size_t yearlen,
if ( 0 != len )
return ( MBEDTLS_ERR_X509_INVALID_DATE );
CHECK( x509_date_is_valid( time ) );
CHECK( x509_date_is_valid( tm ) );
return ( 0 );
}
@ -584,7 +584,7 @@ static int x509_parse_time( unsigned char **p, size_t len, size_t yearlen,
* generalTime GeneralizedTime }
*/
int mbedtls_x509_get_time( unsigned char **p, const unsigned char *end,
mbedtls_x509_time *time )
mbedtls_x509_time *tm )
{
int ret;
size_t len, year_len;
@ -610,7 +610,7 @@ int mbedtls_x509_get_time( unsigned char **p, const unsigned char *end,
if( ret != 0 )
return( MBEDTLS_ERR_X509_INVALID_DATE + ret );
return x509_parse_time( p, len, year_len, time );
return x509_parse_time( p, len, year_len, tm );
}
int mbedtls_x509_get_sig( unsigned char **p, const unsigned char *end, mbedtls_x509_buf *sig )

View File

@ -342,14 +342,14 @@ int mbedtls_x509_crl_parse_der( mbedtls_x509_crl *chain,
return( ret );
}
crl->version++;
if( crl->version > 2 )
if( crl->version < 0 || crl->version > 1 )
{
mbedtls_x509_crl_free( crl );
return( MBEDTLS_ERR_X509_UNKNOWN_VERSION );
}
crl->version++;
if( ( ret = mbedtls_x509_get_sig_alg( &crl->sig_oid, &sig_params1,
&crl->sig_md, &crl->sig_pk,
&crl->sig_opts ) ) != 0 )

View File

@ -740,14 +740,14 @@ static int x509_crt_parse_der_core( mbedtls_x509_crt *crt, const unsigned char *
return( ret );
}
crt->version++;
if( crt->version > 3 )
if( crt->version < 0 || crt->version > 2 )
{
mbedtls_x509_crt_free( crt );
return( MBEDTLS_ERR_X509_UNKNOWN_VERSION );
}
crt->version++;
if( ( ret = mbedtls_x509_get_sig_alg( &crt->sig_oid, &sig_params1,
&crt->sig_md, &crt->sig_pk,
&crt->sig_opts ) ) != 0 )
@ -2052,8 +2052,8 @@ static int x509_crt_verify_child(
/* path_cnt is 0 for the first intermediate CA */
if( 1 + path_cnt > MBEDTLS_X509_MAX_INTERMEDIATE_CA )
{
*flags |= MBEDTLS_X509_BADCERT_NOT_TRUSTED;
return( MBEDTLS_ERR_X509_CERT_VERIFY_FAILED );
/* return immediately as the goal is to avoid unbounded recursion */
return( MBEDTLS_ERR_X509_FATAL_ERROR );
}
if( mbedtls_x509_time_is_past( &child->valid_to ) )
@ -2197,11 +2197,14 @@ int mbedtls_x509_crt_verify_with_profile( mbedtls_x509_crt *crt,
mbedtls_x509_sequence *cur = NULL;
mbedtls_pk_type_t pk_type;
if( profile == NULL )
return( MBEDTLS_ERR_X509_BAD_INPUT_DATA );
*flags = 0;
if( profile == NULL )
{
ret = MBEDTLS_ERR_X509_BAD_INPUT_DATA;
goto exit;
}
if( cn != NULL )
{
name = &crt->subject;
@ -2275,7 +2278,7 @@ int mbedtls_x509_crt_verify_with_profile( mbedtls_x509_crt *crt,
ret = x509_crt_verify_top( crt, parent, ca_crl, profile,
pathlen, selfsigned, flags, f_vrfy, p_vrfy );
if( ret != 0 )
return( ret );
goto exit;
}
else
{
@ -2290,17 +2293,30 @@ int mbedtls_x509_crt_verify_with_profile( mbedtls_x509_crt *crt,
ret = x509_crt_verify_child( crt, parent, trust_ca, ca_crl, profile,
pathlen, selfsigned, flags, f_vrfy, p_vrfy );
if( ret != 0 )
return( ret );
goto exit;
}
else
{
ret = x509_crt_verify_top( crt, trust_ca, ca_crl, profile,
pathlen, selfsigned, flags, f_vrfy, p_vrfy );
if( ret != 0 )
return( ret );
goto exit;
}
}
exit:
/* prevent misuse of the vrfy callback - VERIFY_FAILED would be ignored by
* the SSL module for authmode optional, but non-zero return from the
* callback means a fatal error so it shouldn't be ignored */
if( ret == MBEDTLS_ERR_X509_CERT_VERIFY_FAILED )
ret = MBEDTLS_ERR_X509_FATAL_ERROR;
if( ret != 0 )
{
*flags = (uint32_t) -1;
return( ret );
}
if( *flags != 0 )
return( MBEDTLS_ERR_X509_CERT_VERIFY_FAILED );

View File

@ -158,14 +158,14 @@ int mbedtls_x509_csr_parse_der( mbedtls_x509_csr *csr,
return( ret );
}
csr->version++;
if( csr->version != 1 )
if( csr->version != 0 )
{
mbedtls_x509_csr_free( csr );
return( MBEDTLS_ERR_X509_UNKNOWN_VERSION );
}
csr->version++;
/*
* subject Name
*/

View File

@ -261,7 +261,7 @@ int mbedtls_x509write_crt_set_ns_cert_type( mbedtls_x509write_cert *ctx,
}
static int x509_write_time( unsigned char **p, unsigned char *start,
const char *time, size_t size )
const char *t, size_t size )
{
int ret;
size_t len = 0;
@ -269,10 +269,10 @@ static int x509_write_time( unsigned char **p, unsigned char *start,
/*
* write MBEDTLS_ASN1_UTC_TIME if year < 2050 (2 bytes shorter)
*/
if( time[0] == '2' && time[1] == '0' && time [2] < '5' )
if( t[0] == '2' && t[1] == '0' && t[2] < '5' )
{
MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_raw_buffer( p, start,
(const unsigned char *) time + 2,
(const unsigned char *) t + 2,
size - 2 ) );
MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_len( p, start, len ) );
MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_tag( p, start, MBEDTLS_ASN1_UTC_TIME ) );
@ -280,7 +280,7 @@ static int x509_write_time( unsigned char **p, unsigned char *start,
else
{
MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_raw_buffer( p, start,
(const unsigned char *) time,
(const unsigned char *) t,
size ) );
MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_len( p, start, len ) );
MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_tag( p, start, MBEDTLS_ASN1_GENERALIZED_TIME ) );