Add accessor to retrieve SNI during handshake

Signed-off-by: Glenn Strauss <gstrauss@gluelogic.com>
This commit is contained in:
Glenn Strauss 2022-01-24 12:58:00 -05:00
parent 36872dbd0b
commit 6989407261
6 changed files with 44 additions and 5 deletions

View file

@ -3,3 +3,5 @@ Features
Register callback with mbedtls_ssl_conf_cert_cb(). Register callback with mbedtls_ssl_conf_cert_cb().
* Provide mechanism to reset handshake cert list by calling * Provide mechanism to reset handshake cert list by calling
mbedtls_ssl_set_hs_own_cert() with NULL value for own_cert param. mbedtls_ssl_set_hs_own_cert() with NULL value for own_cert param.
* Add accessor mbedtls_ssl_get_hs_sni() to retrieve SNI from within
cert callback (mbedtls_ssl_conf_cert_cb()) during handshake.

View file

@ -3540,6 +3540,27 @@ int mbedtls_ssl_set_hostname( mbedtls_ssl_context *ssl, const char *hostname );
#endif /* MBEDTLS_X509_CRT_PARSE_C */ #endif /* MBEDTLS_X509_CRT_PARSE_C */
#if defined(MBEDTLS_SSL_SERVER_NAME_INDICATION) #if defined(MBEDTLS_SSL_SERVER_NAME_INDICATION)
/**
* \brief Retrieve SNI extension value for the current handshake.
* Available in \p f_cert_cb of \c mbedtls_ssl_conf_cert_cb(),
* this is the same value passed to \p f_sni callback of
* \c mbedtls_ssl_conf_sni() and may be used instead of
* \c mbedtls_ssl_conf_sni().
*
* \param ssl SSL context
* \param name_len pointer into which to store length of returned value.
* 0 if SNI extension is not present or not yet processed.
*
* \return const pointer to SNI extension value.
* - value is valid only when called in \p f_cert_cb
* registered with \c mbedtls_ssl_conf_cert_cb().
* - value is NULL if SNI extension is not present.
* - value is not '\0'-terminated. Use \c name_len for len.
* - value must not be freed.
*/
const unsigned char *mbedtls_ssl_get_hs_sni( mbedtls_ssl_context *ssl,
size_t *name_len );
/** /**
* \brief Set own certificate and key for the current handshake * \brief Set own certificate and key for the current handshake
* *

View file

@ -849,6 +849,11 @@ struct mbedtls_ssl_handshake_params
* The library does not use it internally. */ * The library does not use it internally. */
void *user_async_ctx; void *user_async_ctx;
#endif /* MBEDTLS_SSL_ASYNC_PRIVATE */ #endif /* MBEDTLS_SSL_ASYNC_PRIVATE */
#if defined(MBEDTLS_SSL_SERVER_NAME_INDICATION)
const unsigned char *sni_name; /*!< raw SNI */
size_t sni_name_len; /*!< raw SNI len */
#endif /* MBEDTLS_SSL_SERVER_NAME_INDICATION */
}; };
typedef struct mbedtls_ssl_hs_buffer mbedtls_ssl_hs_buffer; typedef struct mbedtls_ssl_hs_buffer mbedtls_ssl_hs_buffer;

View file

@ -118,6 +118,11 @@ static int ssl_parse_servername_ext( mbedtls_ssl_context *ssl,
if( p[0] == MBEDTLS_TLS_EXT_SERVERNAME_HOSTNAME ) if( p[0] == MBEDTLS_TLS_EXT_SERVERNAME_HOSTNAME )
{ {
ssl->handshake->sni_name = p + 3;
ssl->handshake->sni_name_len = hostname_len;
if( ssl->conf->f_sni == NULL )
return( 0 );
ret = ssl->conf->f_sni( ssl->conf->p_sni, ret = ssl->conf->f_sni( ssl->conf->p_sni,
ssl, p + 3, hostname_len ); ssl, p + 3, hostname_len );
if( ret != 0 ) if( ret != 0 )
@ -1643,9 +1648,6 @@ read_record_header:
#if defined(MBEDTLS_SSL_SERVER_NAME_INDICATION) #if defined(MBEDTLS_SSL_SERVER_NAME_INDICATION)
case MBEDTLS_TLS_EXT_SERVERNAME: case MBEDTLS_TLS_EXT_SERVERNAME:
MBEDTLS_SSL_DEBUG_MSG( 3, ( "found ServerName extension" ) ); MBEDTLS_SSL_DEBUG_MSG( 3, ( "found ServerName extension" ) );
if( ssl->conf->f_sni == NULL )
break;
ret = ssl_parse_servername_ext( ssl, ext + 4, ext_size ); ret = ssl_parse_servername_ext( ssl, ext + 4, ext_size );
if( ret != 0 ) if( ret != 0 )
return( ret ); return( ret );
@ -1878,6 +1880,10 @@ read_record_header:
MBEDTLS_SSL_DEBUG_RET( 1, "f_cert_cb", ret ); MBEDTLS_SSL_DEBUG_RET( 1, "f_cert_cb", ret );
return( ret ); return( ret );
} }
#if defined(MBEDTLS_SSL_SERVER_NAME_INDICATION)
ssl->handshake->sni_name = NULL;
ssl->handshake->sni_name_len = 0;
#endif
/* /*
* Search for a matching ciphersuite * Search for a matching ciphersuite

View file

@ -1389,6 +1389,13 @@ void mbedtls_ssl_conf_ca_cb( mbedtls_ssl_config *conf,
#endif /* MBEDTLS_X509_CRT_PARSE_C */ #endif /* MBEDTLS_X509_CRT_PARSE_C */
#if defined(MBEDTLS_SSL_SERVER_NAME_INDICATION) #if defined(MBEDTLS_SSL_SERVER_NAME_INDICATION)
const unsigned char *mbedtls_ssl_get_hs_sni( mbedtls_ssl_context *ssl,
size_t *name_len )
{
*name_len = ssl->handshake->sni_name_len;
return( ssl->handshake->sni_name );
}
int mbedtls_ssl_set_hs_own_cert( mbedtls_ssl_context *ssl, int mbedtls_ssl_set_hs_own_cert( mbedtls_ssl_context *ssl,
mbedtls_x509_crt *own_cert, mbedtls_x509_crt *own_cert,
mbedtls_pk_context *pk_key ) mbedtls_pk_context *pk_key )

View file

@ -5025,7 +5025,6 @@ run_test "SNI: no SNI callback" \
crt_file=data_files/server5.crt key_file=data_files/server5.key" \ crt_file=data_files/server5.crt key_file=data_files/server5.key" \
"$P_CLI server_name=localhost" \ "$P_CLI server_name=localhost" \
0 \ 0 \
-S "parse ServerName extension" \
-c "issuer name *: C=NL, O=PolarSSL, CN=Polarssl Test EC CA" \ -c "issuer name *: C=NL, O=PolarSSL, CN=Polarssl Test EC CA" \
-c "subject name *: C=NL, O=PolarSSL, CN=localhost" -c "subject name *: C=NL, O=PolarSSL, CN=localhost"
@ -5175,7 +5174,6 @@ run_test "SNI: DTLS, no SNI callback" \
crt_file=data_files/server5.crt key_file=data_files/server5.key" \ crt_file=data_files/server5.crt key_file=data_files/server5.key" \
"$P_CLI server_name=localhost dtls=1" \ "$P_CLI server_name=localhost dtls=1" \
0 \ 0 \
-S "parse ServerName extension" \
-c "issuer name *: C=NL, O=PolarSSL, CN=Polarssl Test EC CA" \ -c "issuer name *: C=NL, O=PolarSSL, CN=Polarssl Test EC CA" \
-c "subject name *: C=NL, O=PolarSSL, CN=localhost" -c "subject name *: C=NL, O=PolarSSL, CN=localhost"