mirror of
https://github.com/yuzu-emu/mbedtls.git
synced 2024-12-23 12:55:30 +00:00
Merge pull request #616 from mpg/context-s11n
[baremetal] Implement context serialization
This commit is contained in:
commit
cdb83e7c88
|
@ -3903,6 +3903,7 @@ int mbedtls_ssl_close_notify( mbedtls_ssl_context *ssl );
|
||||||
*/
|
*/
|
||||||
void mbedtls_ssl_free( mbedtls_ssl_context *ssl );
|
void mbedtls_ssl_free( mbedtls_ssl_context *ssl );
|
||||||
|
|
||||||
|
#if defined(MBEDTLS_SSL_CONTEXT_SERIALIZATION)
|
||||||
/**
|
/**
|
||||||
* \brief Save an active connection as serialized data in a buffer.
|
* \brief Save an active connection as serialized data in a buffer.
|
||||||
* This allows the freeing or re-using of the SSL context
|
* This allows the freeing or re-using of the SSL context
|
||||||
|
@ -3918,10 +3919,10 @@ void mbedtls_ssl_free( mbedtls_ssl_context *ssl );
|
||||||
* \note When this function succeeds, it calls
|
* \note When this function succeeds, it calls
|
||||||
* mbedtls_ssl_session_reset() on \p ssl which as a result is
|
* mbedtls_ssl_session_reset() on \p ssl which as a result is
|
||||||
* no longer associated with the connection that has been
|
* no longer associated with the connection that has been
|
||||||
* serialized. This avoids creating copies of the session
|
* serialized. This avoids creating copies of the connection
|
||||||
* state. You're then free to either re-use the context
|
* state. You're then free to either re-use the context
|
||||||
* structure for a different connection, or call
|
* structure for a different connection, or call
|
||||||
* mbedtls_ssl_session_free() on it. See the documentation of
|
* mbedtls_ssl_free() on it. See the documentation of
|
||||||
* mbedtls_ssl_session_reset() for more details.
|
* mbedtls_ssl_session_reset() for more details.
|
||||||
*
|
*
|
||||||
* \param ssl The SSL context to save. On success, it is no longer
|
* \param ssl The SSL context to save. On success, it is no longer
|
||||||
|
@ -3936,19 +3937,26 @@ void mbedtls_ssl_free( mbedtls_ssl_context *ssl );
|
||||||
* \note \p olen is updated to the correct value regardless of
|
* \note \p olen is updated to the correct value regardless of
|
||||||
* whether \p buf_len was large enough. This makes it possible
|
* whether \p buf_len was large enough. This makes it possible
|
||||||
* to determine the necessary size by calling this function
|
* to determine the necessary size by calling this function
|
||||||
* with \p buf set to \c NULL and \p buf_len to \c 0.
|
* with \p buf set to \c NULL and \p buf_len to \c 0. However,
|
||||||
|
* the value of \p olen is only guaranteed to be correct when
|
||||||
|
* the function returns #MBEDTLS_ERR_SSL_BUFFER_TOO_SMALL or
|
||||||
|
* \c 0. If the return value is different, then the value of
|
||||||
|
* \p olen is undefined.
|
||||||
*
|
*
|
||||||
* \return \c 0 if successful.
|
* \return \c 0 if successful.
|
||||||
* \return #MBEDTLS_ERR_SSL_BUFFER_TOO_SMALL if \p buf is too small.
|
* \return #MBEDTLS_ERR_SSL_BUFFER_TOO_SMALL if \p buf is too small.
|
||||||
|
* \return #MBEDTLS_ERR_SSL_ALLOC_FAILED if memory allocation failed
|
||||||
|
* while reseting the context.
|
||||||
* \return #MBEDTLS_ERR_SSL_BAD_INPUT_DATA if a handshake is in
|
* \return #MBEDTLS_ERR_SSL_BAD_INPUT_DATA if a handshake is in
|
||||||
* progress, or there is pending data for reading or sending,
|
* progress, or there is pending data for reading or sending,
|
||||||
* or the connection does not use DTLS 1.2 with and AEAD
|
* or the connection does not use DTLS 1.2 with an AEAD
|
||||||
* ciphersuite, or renegotiation is enabled.
|
* ciphersuite, or renegotiation is enabled.
|
||||||
*/
|
*/
|
||||||
int mbedtls_ssl_context_save( mbedtls_ssl_context *ssl,
|
int mbedtls_ssl_context_save( mbedtls_ssl_context *ssl,
|
||||||
unsigned char *buf,
|
unsigned char *buf,
|
||||||
size_t buf_len,
|
size_t buf_len,
|
||||||
size_t *olen );
|
size_t *olen );
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* \brief Load serialized connection data to an SSL context.
|
* \brief Load serialized connection data to an SSL context.
|
||||||
*
|
*
|
||||||
|
@ -3982,15 +3990,12 @@ int mbedtls_ssl_context_save( mbedtls_ssl_context *ssl,
|
||||||
* (unless they were already set before calling
|
* (unless they were already set before calling
|
||||||
* mbedtls_ssl_session_reset() and the values are suitable for
|
* mbedtls_ssl_session_reset() and the values are suitable for
|
||||||
* the present connection). Specifically, you want to call
|
* the present connection). Specifically, you want to call
|
||||||
* at least mbedtls_ssl_set_bio(). If you're using a read
|
* at least mbedtls_ssl_set_bio() and
|
||||||
* timeout (that is, you called
|
* mbedtls_ssl_set_timer_cb(). All other SSL setter functions
|
||||||
* mbedtls_ssl_conf_read_timeout() with a non-zero timeout)
|
* are not necessary to call, either because they're only used
|
||||||
* and non-blocking I/O, you also need to set timer callbacks
|
* in handshakes, or because the setting is already saved. You
|
||||||
* by calling mbedtls_ssl_set_timer_cb(). All other SSL setter
|
* might choose to call them anyway, for example in order to
|
||||||
* functions are not necessary to call, either because they're
|
* share code between the cases of establishing a new
|
||||||
* only used in handshakes, or because the setting is already
|
|
||||||
* saved. You might choose to call them anyway, for example in
|
|
||||||
* order to share code between the cases of establishing a new
|
|
||||||
* connection and the case of loading an already-established
|
* connection and the case of loading an already-established
|
||||||
* connection.
|
* connection.
|
||||||
*
|
*
|
||||||
|
@ -4000,6 +4005,11 @@ int mbedtls_ssl_context_save( mbedtls_ssl_context *ssl,
|
||||||
* newly-configured value with the value that was active when
|
* newly-configured value with the value that was active when
|
||||||
* the context was saved.
|
* the context was saved.
|
||||||
*
|
*
|
||||||
|
* \note When this function returns an error code, it calls
|
||||||
|
* mbedtls_ssl_free() on \p ssl. In this case, you need to
|
||||||
|
* prepare the context with the usual sequence starting with a
|
||||||
|
* call to mbedtls_ssl_init() if you want to use it again.
|
||||||
|
*
|
||||||
* \param ssl The SSL context structure to be populated. It must have
|
* \param ssl The SSL context structure to be populated. It must have
|
||||||
* been prepared as described in the note above.
|
* been prepared as described in the note above.
|
||||||
* \param buf The buffer holding the serialized connection data. It must
|
* \param buf The buffer holding the serialized connection data. It must
|
||||||
|
@ -4008,11 +4018,14 @@ int mbedtls_ssl_context_save( mbedtls_ssl_context *ssl,
|
||||||
*
|
*
|
||||||
* \return \c 0 if successful.
|
* \return \c 0 if successful.
|
||||||
* \return #MBEDTLS_ERR_SSL_ALLOC_FAILED if memory allocation failed.
|
* \return #MBEDTLS_ERR_SSL_ALLOC_FAILED if memory allocation failed.
|
||||||
|
* \return #MBEDTLS_ERR_SSL_VERSION_MISMATCH if the serialized data
|
||||||
|
* comes from a different Mbed TLS version or build.
|
||||||
* \return #MBEDTLS_ERR_SSL_BAD_INPUT_DATA if input data is invalid.
|
* \return #MBEDTLS_ERR_SSL_BAD_INPUT_DATA if input data is invalid.
|
||||||
*/
|
*/
|
||||||
int mbedtls_ssl_context_load( mbedtls_ssl_context *ssl,
|
int mbedtls_ssl_context_load( mbedtls_ssl_context *ssl,
|
||||||
const unsigned char *buf,
|
const unsigned char *buf,
|
||||||
size_t len );
|
size_t len );
|
||||||
|
#endif /* MBEDTLS_SSL_CONTEXT_SERIALIZATION */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* \brief Initialize an SSL configuration context
|
* \brief Initialize an SSL configuration context
|
||||||
|
|
|
@ -728,6 +728,12 @@ struct mbedtls_ssl_transform
|
||||||
z_stream ctx_deflate; /*!< compression context */
|
z_stream ctx_deflate; /*!< compression context */
|
||||||
z_stream ctx_inflate; /*!< decompression context */
|
z_stream ctx_inflate; /*!< decompression context */
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#if defined(MBEDTLS_SSL_CONTEXT_SERIALIZATION)
|
||||||
|
/* We need the Hello random bytes in order to re-derive keys from the
|
||||||
|
* Master Secret and other session info, see ssl_populate_transform() */
|
||||||
|
unsigned char randbytes[64]; /*!< ServerHello.random+ClientHello.random */
|
||||||
|
#endif /* MBEDTLS_SSL_CONTEXT_SERIALIZATION */
|
||||||
};
|
};
|
||||||
|
|
||||||
static inline int mbedtls_ssl_transform_get_minor_ver( mbedtls_ssl_transform const *transform )
|
static inline int mbedtls_ssl_transform_get_minor_ver( mbedtls_ssl_transform const *transform )
|
||||||
|
@ -740,6 +746,21 @@ static inline int mbedtls_ssl_transform_get_minor_ver( mbedtls_ssl_transform con
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Return 1 if the transform uses an AEAD cipher, 0 otherwise.
|
||||||
|
* Equivalently, return 0 if a separate MAC is used, 1 otherwise.
|
||||||
|
*/
|
||||||
|
static inline int mbedtls_ssl_transform_uses_aead(
|
||||||
|
const mbedtls_ssl_transform *transform )
|
||||||
|
{
|
||||||
|
#if defined(MBEDTLS_SSL_SOME_MODES_USE_MAC)
|
||||||
|
return( transform->maclen == 0 && transform->taglen != 0 );
|
||||||
|
#else
|
||||||
|
(void) transform;
|
||||||
|
return( 1 );
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Internal representation of record frames
|
* Internal representation of record frames
|
||||||
*
|
*
|
||||||
|
@ -1222,6 +1243,17 @@ static inline int mbedtls_ssl_get_renego_status(
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static inline int mbedtls_ssl_conf_is_renegotiation_enabled(
|
||||||
|
const mbedtls_ssl_config *conf )
|
||||||
|
{
|
||||||
|
#if defined(MBEDTLS_SSL_RENEGOTIATION)
|
||||||
|
return( conf->disable_renegotiation ==
|
||||||
|
MBEDTLS_SSL_RENEGOTIATION_ENABLED );
|
||||||
|
#else
|
||||||
|
(void) conf;
|
||||||
|
return( 0 );
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Getter functions for fields in mbedtls_ssl_config which may
|
* Getter functions for fields in mbedtls_ssl_config which may
|
||||||
|
|
|
@ -823,7 +823,9 @@ static int ssl_populate_transform( mbedtls_ssl_transform *transform,
|
||||||
(void) ssl;
|
(void) ssl;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/* Copy info about negotiated version and extensions */
|
/*
|
||||||
|
* Some data just needs copying into the structure
|
||||||
|
*/
|
||||||
#if defined(MBEDTLS_SSL_ENCRYPT_THEN_MAC) && \
|
#if defined(MBEDTLS_SSL_ENCRYPT_THEN_MAC) && \
|
||||||
defined(MBEDTLS_SSL_SOME_MODES_USE_MAC)
|
defined(MBEDTLS_SSL_SOME_MODES_USE_MAC)
|
||||||
transform->encrypt_then_mac = encrypt_then_mac;
|
transform->encrypt_then_mac = encrypt_then_mac;
|
||||||
|
@ -835,6 +837,10 @@ static int ssl_populate_transform( mbedtls_ssl_transform *transform,
|
||||||
((void) minor_ver);
|
((void) minor_ver);
|
||||||
#endif /* !MBEDTLS_SSL_CONF_FIXED_MINOR_VER */
|
#endif /* !MBEDTLS_SSL_CONF_FIXED_MINOR_VER */
|
||||||
|
|
||||||
|
#if defined(MBEDTLS_SSL_CONTEXT_SERIALIZATION)
|
||||||
|
memcpy( transform->randbytes, randbytes, sizeof( transform->randbytes ) );
|
||||||
|
#endif
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Get various info structures
|
* Get various info structures
|
||||||
*/
|
*/
|
||||||
|
@ -9375,10 +9381,11 @@ static unsigned char ssl_serialized_session_header[] = {
|
||||||
* verify_result is put before peer_cert so that all mandatory fields come
|
* verify_result is put before peer_cert so that all mandatory fields come
|
||||||
* together in one block.
|
* together in one block.
|
||||||
*/
|
*/
|
||||||
int mbedtls_ssl_session_save( const mbedtls_ssl_session *session,
|
static int ssl_session_save( const mbedtls_ssl_session *session,
|
||||||
unsigned char *buf,
|
unsigned char omit_header,
|
||||||
size_t buf_len,
|
unsigned char *buf,
|
||||||
size_t *olen )
|
size_t buf_len,
|
||||||
|
size_t *olen )
|
||||||
{
|
{
|
||||||
unsigned char *p = buf;
|
unsigned char *p = buf;
|
||||||
size_t used = 0;
|
size_t used = 0;
|
||||||
|
@ -9391,17 +9398,20 @@ int mbedtls_ssl_session_save( const mbedtls_ssl_session *session,
|
||||||
#endif
|
#endif
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/*
|
if( !omit_header )
|
||||||
* Add version identifier
|
|
||||||
*/
|
|
||||||
|
|
||||||
used += sizeof( ssl_serialized_session_header );
|
|
||||||
|
|
||||||
if( used <= buf_len )
|
|
||||||
{
|
{
|
||||||
memcpy( p, ssl_serialized_session_header,
|
/*
|
||||||
sizeof( ssl_serialized_session_header ) );
|
* Add version identifier
|
||||||
p += sizeof( ssl_serialized_session_header );
|
*/
|
||||||
|
|
||||||
|
used += sizeof( ssl_serialized_session_header );
|
||||||
|
|
||||||
|
if( used <= buf_len )
|
||||||
|
{
|
||||||
|
memcpy( p, ssl_serialized_session_header,
|
||||||
|
sizeof( ssl_serialized_session_header ) );
|
||||||
|
p += sizeof( ssl_serialized_session_header );
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -9567,12 +9577,24 @@ int mbedtls_ssl_session_save( const mbedtls_ssl_session *session,
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Unserialize session, see mbedtls_ssl_session_save() for format.
|
* Public wrapper for ssl_session_save()
|
||||||
|
*/
|
||||||
|
int mbedtls_ssl_session_save( const mbedtls_ssl_session *session,
|
||||||
|
unsigned char *buf,
|
||||||
|
size_t buf_len,
|
||||||
|
size_t *olen )
|
||||||
|
{
|
||||||
|
return( ssl_session_save( session, 0, buf, buf_len, olen ) );
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Deserialize session, see mbedtls_ssl_session_save() for format.
|
||||||
*
|
*
|
||||||
* This internal version is wrapped by a public function that cleans up in
|
* This internal version is wrapped by a public function that cleans up in
|
||||||
* case of error.
|
* case of error, and has an extra option omit_header.
|
||||||
*/
|
*/
|
||||||
static int ssl_session_load( mbedtls_ssl_session *session,
|
static int ssl_session_load( mbedtls_ssl_session *session,
|
||||||
|
unsigned char omit_header,
|
||||||
const unsigned char *buf,
|
const unsigned char *buf,
|
||||||
size_t len )
|
size_t len )
|
||||||
{
|
{
|
||||||
|
@ -9588,19 +9610,22 @@ static int ssl_session_load( mbedtls_ssl_session *session,
|
||||||
#endif
|
#endif
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/*
|
if( !omit_header )
|
||||||
* Check version identifier
|
|
||||||
*/
|
|
||||||
|
|
||||||
if( (size_t)( end - p ) < sizeof( ssl_serialized_session_header ) )
|
|
||||||
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
|
||||||
|
|
||||||
if( memcmp( p, ssl_serialized_session_header,
|
|
||||||
sizeof( ssl_serialized_session_header ) ) != 0 )
|
|
||||||
{
|
{
|
||||||
return( MBEDTLS_ERR_SSL_VERSION_MISMATCH );
|
/*
|
||||||
|
* Check version identifier
|
||||||
|
*/
|
||||||
|
|
||||||
|
if( (size_t)( end - p ) < sizeof( ssl_serialized_session_header ) )
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
|
||||||
|
if( memcmp( p, ssl_serialized_session_header,
|
||||||
|
sizeof( ssl_serialized_session_header ) ) != 0 )
|
||||||
|
{
|
||||||
|
return( MBEDTLS_ERR_SSL_VERSION_MISMATCH );
|
||||||
|
}
|
||||||
|
p += sizeof( ssl_serialized_session_header );
|
||||||
}
|
}
|
||||||
p += sizeof( ssl_serialized_session_header );
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Time
|
* Time
|
||||||
|
@ -9807,13 +9832,13 @@ static int ssl_session_load( mbedtls_ssl_session *session,
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Unserialize session: public wrapper for error cleaning
|
* Deserialize session: public wrapper for error cleaning
|
||||||
*/
|
*/
|
||||||
int mbedtls_ssl_session_load( mbedtls_ssl_session *session,
|
int mbedtls_ssl_session_load( mbedtls_ssl_session *session,
|
||||||
const unsigned char *buf,
|
const unsigned char *buf,
|
||||||
size_t len )
|
size_t len )
|
||||||
{
|
{
|
||||||
int ret = ssl_session_load( session, buf, len );
|
int ret = ssl_session_load( session, 0, buf, len );
|
||||||
|
|
||||||
if( ret != 0 )
|
if( ret != 0 )
|
||||||
mbedtls_ssl_session_free( session );
|
mbedtls_ssl_session_free( session );
|
||||||
|
@ -10014,7 +10039,7 @@ static int ssl_check_ctr_renegotiate( mbedtls_ssl_context *ssl )
|
||||||
|
|
||||||
if( ssl->state != MBEDTLS_SSL_HANDSHAKE_OVER ||
|
if( ssl->state != MBEDTLS_SSL_HANDSHAKE_OVER ||
|
||||||
ssl->renego_status == MBEDTLS_SSL_RENEGOTIATION_PENDING ||
|
ssl->renego_status == MBEDTLS_SSL_RENEGOTIATION_PENDING ||
|
||||||
ssl->conf->disable_renegotiation == MBEDTLS_SSL_RENEGOTIATION_DISABLED )
|
! mbedtls_ssl_conf_is_renegotiation_enabled( ssl->conf ) )
|
||||||
{
|
{
|
||||||
return( 0 );
|
return( 0 );
|
||||||
}
|
}
|
||||||
|
@ -10721,39 +10746,616 @@ void mbedtls_ssl_session_free( mbedtls_ssl_session *session )
|
||||||
mbedtls_platform_zeroize( session, sizeof( mbedtls_ssl_session ) );
|
mbedtls_platform_zeroize( session, sizeof( mbedtls_ssl_session ) );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#if defined(MBEDTLS_SSL_CONTEXT_SERIALIZATION)
|
||||||
|
|
||||||
|
#if defined(MBEDTLS_SSL_DTLS_CONNECTION_ID)
|
||||||
|
#define SSL_SERIALIZED_CONTEXT_CONFIG_DTLS_CONNECTION_ID 1u
|
||||||
|
#else
|
||||||
|
#define SSL_SERIALIZED_CONTEXT_CONFIG_DTLS_CONNECTION_ID 0u
|
||||||
|
#endif /* MBEDTLS_SSL_DTLS_CONNECTION_ID */
|
||||||
|
|
||||||
|
#if defined(MBEDTLS_SSL_DTLS_BADMAC_LIMIT)
|
||||||
|
#define SSL_SERIALIZED_CONTEXT_CONFIG_DTLS_BADMAC_LIMIT 1u
|
||||||
|
#else
|
||||||
|
#define SSL_SERIALIZED_CONTEXT_CONFIG_DTLS_BADMAC_LIMIT 0u
|
||||||
|
#endif /* MBEDTLS_SSL_DTLS_BADMAC_LIMIT */
|
||||||
|
|
||||||
|
#if defined(MBEDTLS_SSL_DTLS_ANTI_REPLAY)
|
||||||
|
#define SSL_SERIALIZED_CONTEXT_CONFIG_DTLS_ANTI_REPLAY 1u
|
||||||
|
#else
|
||||||
|
#define SSL_SERIALIZED_CONTEXT_CONFIG_DTLS_ANTI_REPLAY 0u
|
||||||
|
#endif /* MBEDTLS_SSL_DTLS_ANTI_REPLAY */
|
||||||
|
|
||||||
|
#if defined(MBEDTLS_SSL_ALPN)
|
||||||
|
#define SSL_SERIALIZED_CONTEXT_CONFIG_ALPN 1u
|
||||||
|
#else
|
||||||
|
#define SSL_SERIALIZED_CONTEXT_CONFIG_ALPN 0u
|
||||||
|
#endif /* MBEDTLS_SSL_ALPN */
|
||||||
|
|
||||||
|
#define SSL_SERIALIZED_CONTEXT_CONFIG_DTLS_CONNECTION_ID_BIT 0
|
||||||
|
#define SSL_SERIALIZED_CONTEXT_CONFIG_DTLS_BADMAC_LIMIT_BIT 1
|
||||||
|
#define SSL_SERIALIZED_CONTEXT_CONFIG_DTLS_ANTI_REPLAY_BIT 2
|
||||||
|
#define SSL_SERIALIZED_CONTEXT_CONFIG_ALPN_BIT 3
|
||||||
|
|
||||||
|
#define SSL_SERIALIZED_CONTEXT_CONFIG_BITFLAG \
|
||||||
|
( (uint32_t) ( \
|
||||||
|
( SSL_SERIALIZED_CONTEXT_CONFIG_DTLS_CONNECTION_ID << SSL_SERIALIZED_CONTEXT_CONFIG_DTLS_CONNECTION_ID_BIT ) | \
|
||||||
|
( SSL_SERIALIZED_CONTEXT_CONFIG_DTLS_BADMAC_LIMIT << SSL_SERIALIZED_CONTEXT_CONFIG_DTLS_BADMAC_LIMIT_BIT ) | \
|
||||||
|
( SSL_SERIALIZED_CONTEXT_CONFIG_DTLS_ANTI_REPLAY << SSL_SERIALIZED_CONTEXT_CONFIG_DTLS_ANTI_REPLAY_BIT ) | \
|
||||||
|
( SSL_SERIALIZED_CONTEXT_CONFIG_ALPN << SSL_SERIALIZED_CONTEXT_CONFIG_ALPN_BIT ) | \
|
||||||
|
0u ) )
|
||||||
|
|
||||||
|
static unsigned char ssl_serialized_context_header[] = {
|
||||||
|
MBEDTLS_VERSION_MAJOR,
|
||||||
|
MBEDTLS_VERSION_MINOR,
|
||||||
|
MBEDTLS_VERSION_PATCH,
|
||||||
|
( SSL_SERIALIZED_SESSION_CONFIG_BITFLAG >> 8 ) & 0xFF,
|
||||||
|
( SSL_SERIALIZED_SESSION_CONFIG_BITFLAG >> 0 ) & 0xFF,
|
||||||
|
( SSL_SERIALIZED_CONTEXT_CONFIG_BITFLAG >> 16 ) & 0xFF,
|
||||||
|
( SSL_SERIALIZED_CONTEXT_CONFIG_BITFLAG >> 8 ) & 0xFF,
|
||||||
|
( SSL_SERIALIZED_CONTEXT_CONFIG_BITFLAG >> 0 ) & 0xFF,
|
||||||
|
};
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Serialize a full SSL context
|
* Serialize a full SSL context
|
||||||
|
*
|
||||||
|
* The format of the serialized data is:
|
||||||
|
* (in the presentation language of TLS, RFC 8446 section 3)
|
||||||
|
*
|
||||||
|
* // header
|
||||||
|
* opaque mbedtls_version[3]; // major, minor, patch
|
||||||
|
* opaque context_format[5]; // version-specific field determining
|
||||||
|
* // the format of the remaining
|
||||||
|
* // serialized data.
|
||||||
|
* Note: When updating the format, remember to keep these
|
||||||
|
* version+format bytes. (We may make their size part of the API.)
|
||||||
|
*
|
||||||
|
* // session sub-structure
|
||||||
|
* opaque session<1..2^32-1>; // see mbedtls_ssl_session_save()
|
||||||
|
* // transform sub-structure
|
||||||
|
* uint8 random[64]; // ServerHello.random+ClientHello.random
|
||||||
|
* uint8 in_cid<0..2^8-1> // Connection ID: expected incoming value
|
||||||
|
* uint8 out_cid<0..2^8-1> // Connection ID: outgoing value to use
|
||||||
|
* // fields from ssl_context
|
||||||
|
* uint32 badmac_seen; // DTLS: number of records with failing MAC
|
||||||
|
* uint64 in_window_top; // DTLS: last validated record seq_num
|
||||||
|
* uint64 in_window; // DTLS: bitmask for replay protection
|
||||||
|
* uint8 disable_datagram_packing; // DTLS: only one record per datagram
|
||||||
|
* uint64 cur_out_ctr; // Record layer: outgoing sequence number
|
||||||
|
* uint16 mtu; // DTLS: path mtu (max outgoing fragment size)
|
||||||
|
* uint8 alpn_chosen<0..2^8-1> // ALPN: negotiated application protocol
|
||||||
|
*
|
||||||
|
* Note that many fields of the ssl_context or sub-structures are not
|
||||||
|
* serialized, as they fall in one of the following categories:
|
||||||
|
*
|
||||||
|
* 1. forced value (eg in_left must be 0)
|
||||||
|
* 2. pointer to dynamically-allocated memory (eg session, transform)
|
||||||
|
* 3. value can be re-derived from other data (eg session keys from MS)
|
||||||
|
* 4. value was temporary (eg content of input buffer)
|
||||||
|
* 5. value will be provided by the user again (eg I/O callbacks and context)
|
||||||
*/
|
*/
|
||||||
int mbedtls_ssl_context_save( mbedtls_ssl_context *ssl,
|
int mbedtls_ssl_context_save( mbedtls_ssl_context *ssl,
|
||||||
unsigned char *buf,
|
unsigned char *buf,
|
||||||
size_t buf_len,
|
size_t buf_len,
|
||||||
size_t *olen )
|
size_t *olen )
|
||||||
{
|
{
|
||||||
/* Unimplemented */
|
unsigned char *p = buf;
|
||||||
(void) ssl;
|
size_t used = 0;
|
||||||
|
size_t session_len;
|
||||||
|
int ret = 0;
|
||||||
|
|
||||||
if( buf != NULL )
|
/*
|
||||||
memset( buf, 0, buf_len );
|
* Enforce usage restrictions, see "return BAD_INPUT_DATA" in
|
||||||
|
* this function's documentation.
|
||||||
|
*
|
||||||
|
* These are due to assumptions/limitations in the implementation. Some of
|
||||||
|
* them are likely to stay (no handshake in progress) some might go away
|
||||||
|
* (only DTLS) but are currently used to simplify the implementation.
|
||||||
|
*/
|
||||||
|
/* The initial handshake must be over */
|
||||||
|
if( ssl->state != MBEDTLS_SSL_HANDSHAKE_OVER )
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
if( ssl->handshake != NULL )
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
/* Double-check that sub-structures are indeed ready */
|
||||||
|
if( ssl->transform == NULL || ssl->session == NULL )
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
/* There must be no pending incoming or outgoing data */
|
||||||
|
if( mbedtls_ssl_check_pending( ssl ) != 0 )
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
if( ssl->out_left != 0 )
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
/* Protocol must be DLTS, not TLS */
|
||||||
|
if( MBEDTLS_SSL_TRANSPORT_IS_TLS( ssl->conf->transport ) )
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
/* Version must be 1.2 */
|
||||||
|
if( mbedtls_ssl_get_major_ver( ssl ) != MBEDTLS_SSL_MAJOR_VERSION_3 )
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
if( mbedtls_ssl_get_minor_ver( ssl ) != MBEDTLS_SSL_MINOR_VERSION_3 )
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
/* We must be using an AEAD ciphersuite */
|
||||||
|
if( mbedtls_ssl_transform_uses_aead( ssl->transform ) != 1 )
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
/* Renegotiation must not be enabled */
|
||||||
|
if( mbedtls_ssl_conf_is_renegotiation_enabled( ssl->conf ) )
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
|
||||||
*olen = 0;
|
/*
|
||||||
|
* Version and format identifier
|
||||||
|
*/
|
||||||
|
used += sizeof( ssl_serialized_context_header );
|
||||||
|
|
||||||
|
if( used <= buf_len )
|
||||||
|
{
|
||||||
|
memcpy( p, ssl_serialized_context_header,
|
||||||
|
sizeof( ssl_serialized_context_header ) );
|
||||||
|
p += sizeof( ssl_serialized_context_header );
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Session (length + data)
|
||||||
|
*/
|
||||||
|
ret = ssl_session_save( ssl->session, 1, NULL, 0, &session_len );
|
||||||
|
if( ret != MBEDTLS_ERR_SSL_BUFFER_TOO_SMALL )
|
||||||
|
return( ret );
|
||||||
|
|
||||||
|
used += 4 + session_len;
|
||||||
|
if( used <= buf_len )
|
||||||
|
{
|
||||||
|
*p++ = (unsigned char)( ( session_len >> 24 ) & 0xFF );
|
||||||
|
*p++ = (unsigned char)( ( session_len >> 16 ) & 0xFF );
|
||||||
|
*p++ = (unsigned char)( ( session_len >> 8 ) & 0xFF );
|
||||||
|
*p++ = (unsigned char)( ( session_len ) & 0xFF );
|
||||||
|
|
||||||
|
ret = ssl_session_save( ssl->session, 1,
|
||||||
|
p, session_len, &session_len );
|
||||||
|
if( ret != 0 )
|
||||||
|
return( ret );
|
||||||
|
|
||||||
|
p += session_len;
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Transform
|
||||||
|
*/
|
||||||
|
used += sizeof( ssl->transform->randbytes );
|
||||||
|
if( used <= buf_len )
|
||||||
|
{
|
||||||
|
memcpy( p, ssl->transform->randbytes,
|
||||||
|
sizeof( ssl->transform->randbytes ) );
|
||||||
|
p += sizeof( ssl->transform->randbytes );
|
||||||
|
}
|
||||||
|
|
||||||
|
#if defined(MBEDTLS_SSL_DTLS_CONNECTION_ID)
|
||||||
|
used += 2 + ssl->transform->in_cid_len + ssl->transform->out_cid_len;
|
||||||
|
if( used <= buf_len )
|
||||||
|
{
|
||||||
|
*p++ = ssl->transform->in_cid_len;
|
||||||
|
memcpy( p, ssl->transform->in_cid, ssl->transform->in_cid_len );
|
||||||
|
p += ssl->transform->in_cid_len;
|
||||||
|
|
||||||
|
*p++ = ssl->transform->out_cid_len;
|
||||||
|
memcpy( p, ssl->transform->out_cid, ssl->transform->out_cid_len );
|
||||||
|
p += ssl->transform->out_cid_len;
|
||||||
|
}
|
||||||
|
#endif /* MBEDTLS_SSL_DTLS_CONNECTION_ID */
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Saved fields from top-level ssl_context structure
|
||||||
|
*/
|
||||||
|
#if defined(MBEDTLS_SSL_DTLS_BADMAC_LIMIT)
|
||||||
|
used += 4;
|
||||||
|
if( used <= buf_len )
|
||||||
|
{
|
||||||
|
*p++ = (unsigned char)( ( ssl->badmac_seen >> 24 ) & 0xFF );
|
||||||
|
*p++ = (unsigned char)( ( ssl->badmac_seen >> 16 ) & 0xFF );
|
||||||
|
*p++ = (unsigned char)( ( ssl->badmac_seen >> 8 ) & 0xFF );
|
||||||
|
*p++ = (unsigned char)( ( ssl->badmac_seen ) & 0xFF );
|
||||||
|
}
|
||||||
|
#endif /* MBEDTLS_SSL_DTLS_BADMAC_LIMIT */
|
||||||
|
|
||||||
|
#if defined(MBEDTLS_SSL_DTLS_ANTI_REPLAY)
|
||||||
|
used += 16;
|
||||||
|
if( used <= buf_len )
|
||||||
|
{
|
||||||
|
*p++ = (unsigned char)( ( ssl->in_window_top >> 56 ) & 0xFF );
|
||||||
|
*p++ = (unsigned char)( ( ssl->in_window_top >> 48 ) & 0xFF );
|
||||||
|
*p++ = (unsigned char)( ( ssl->in_window_top >> 40 ) & 0xFF );
|
||||||
|
*p++ = (unsigned char)( ( ssl->in_window_top >> 32 ) & 0xFF );
|
||||||
|
*p++ = (unsigned char)( ( ssl->in_window_top >> 24 ) & 0xFF );
|
||||||
|
*p++ = (unsigned char)( ( ssl->in_window_top >> 16 ) & 0xFF );
|
||||||
|
*p++ = (unsigned char)( ( ssl->in_window_top >> 8 ) & 0xFF );
|
||||||
|
*p++ = (unsigned char)( ( ssl->in_window_top ) & 0xFF );
|
||||||
|
|
||||||
|
*p++ = (unsigned char)( ( ssl->in_window >> 56 ) & 0xFF );
|
||||||
|
*p++ = (unsigned char)( ( ssl->in_window >> 48 ) & 0xFF );
|
||||||
|
*p++ = (unsigned char)( ( ssl->in_window >> 40 ) & 0xFF );
|
||||||
|
*p++ = (unsigned char)( ( ssl->in_window >> 32 ) & 0xFF );
|
||||||
|
*p++ = (unsigned char)( ( ssl->in_window >> 24 ) & 0xFF );
|
||||||
|
*p++ = (unsigned char)( ( ssl->in_window >> 16 ) & 0xFF );
|
||||||
|
*p++ = (unsigned char)( ( ssl->in_window >> 8 ) & 0xFF );
|
||||||
|
*p++ = (unsigned char)( ( ssl->in_window ) & 0xFF );
|
||||||
|
}
|
||||||
|
#endif /* MBEDTLS_SSL_DTLS_ANTI_REPLAY */
|
||||||
|
|
||||||
|
#if defined(MBEDTLS_SSL_PROTO_DTLS)
|
||||||
|
used += 1;
|
||||||
|
if( used <= buf_len )
|
||||||
|
{
|
||||||
|
*p++ = ssl->disable_datagram_packing;
|
||||||
|
}
|
||||||
|
#endif /* MBEDTLS_SSL_PROTO_DTLS */
|
||||||
|
|
||||||
|
used += 8;
|
||||||
|
if( used <= buf_len )
|
||||||
|
{
|
||||||
|
memcpy( p, ssl->cur_out_ctr, 8 );
|
||||||
|
p += 8;
|
||||||
|
}
|
||||||
|
|
||||||
|
#if defined(MBEDTLS_SSL_PROTO_DTLS)
|
||||||
|
used += 2;
|
||||||
|
if( used <= buf_len )
|
||||||
|
{
|
||||||
|
*p++ = (unsigned char)( ( ssl->mtu >> 8 ) & 0xFF );
|
||||||
|
*p++ = (unsigned char)( ( ssl->mtu ) & 0xFF );
|
||||||
|
}
|
||||||
|
#endif /* MBEDTLS_SSL_PROTO_DTLS */
|
||||||
|
|
||||||
|
#if defined(MBEDTLS_SSL_ALPN)
|
||||||
|
{
|
||||||
|
const uint8_t alpn_len = ssl->alpn_chosen
|
||||||
|
? (uint8_t) strlen( ssl->alpn_chosen )
|
||||||
|
: 0;
|
||||||
|
|
||||||
|
used += 1 + alpn_len;
|
||||||
|
if( used <= buf_len )
|
||||||
|
{
|
||||||
|
*p++ = alpn_len;
|
||||||
|
|
||||||
|
if( ssl->alpn_chosen != NULL )
|
||||||
|
{
|
||||||
|
memcpy( p, ssl->alpn_chosen, alpn_len );
|
||||||
|
p += alpn_len;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#endif /* MBEDTLS_SSL_ALPN */
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Done
|
||||||
|
*/
|
||||||
|
*olen = used;
|
||||||
|
|
||||||
|
if( used > buf_len )
|
||||||
|
return( MBEDTLS_ERR_SSL_BUFFER_TOO_SMALL );
|
||||||
|
|
||||||
|
MBEDTLS_SSL_DEBUG_BUF( 4, "saved context", buf, used );
|
||||||
|
|
||||||
|
return( ssl_session_reset_int( ssl, 0 ) );
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Helper to get TLS 1.2 PRF from ciphersuite
|
||||||
|
* (Duplicates bits of logic from ssl_set_handshake_prfs().)
|
||||||
|
*/
|
||||||
|
typedef int (*tls_prf_fn)( const unsigned char *secret, size_t slen,
|
||||||
|
const char *label,
|
||||||
|
const unsigned char *random, size_t rlen,
|
||||||
|
unsigned char *dstbuf, size_t dlen );
|
||||||
|
static tls_prf_fn ssl_tls12prf_from_cs( int ciphersuite_id )
|
||||||
|
{
|
||||||
|
mbedtls_ssl_ciphersuite_handle_t const info =
|
||||||
|
mbedtls_ssl_ciphersuite_from_id( ciphersuite_id );
|
||||||
|
const mbedtls_md_type_t hash = mbedtls_ssl_suite_get_mac( info );
|
||||||
|
|
||||||
|
#if defined(MBEDTLS_SHA512_C)
|
||||||
|
if( hash == MBEDTLS_MD_SHA384 )
|
||||||
|
return( tls_prf_sha384 );
|
||||||
|
#else
|
||||||
|
(void) hash;
|
||||||
|
#endif
|
||||||
|
return( tls_prf_sha256 );
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Deserialize context, see mbedtls_ssl_context_save() for format.
|
||||||
|
*
|
||||||
|
* This internal version is wrapped by a public function that cleans up in
|
||||||
|
* case of error.
|
||||||
|
*/
|
||||||
|
static int ssl_context_load( mbedtls_ssl_context *ssl,
|
||||||
|
const unsigned char *buf,
|
||||||
|
size_t len )
|
||||||
|
{
|
||||||
|
const unsigned char *p = buf;
|
||||||
|
const unsigned char * const end = buf + len;
|
||||||
|
size_t session_len;
|
||||||
|
int ret;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* The context should have been freshly setup or reset.
|
||||||
|
* Give the user an error in case of obvious misuse.
|
||||||
|
* (Checking session is useful because it won't be NULL if we're
|
||||||
|
* renegotiating, or if the user mistakenly loaded a session first.)
|
||||||
|
*/
|
||||||
|
if( ssl->state != MBEDTLS_SSL_HELLO_REQUEST ||
|
||||||
|
ssl->session != NULL )
|
||||||
|
{
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* We can't check that the config matches the initial one, but we can at
|
||||||
|
* least check it matches the requirements for serializing.
|
||||||
|
*/
|
||||||
|
if( MBEDTLS_SSL_TRANSPORT_IS_TLS( ssl->conf->transport ) ||
|
||||||
|
mbedtls_ssl_conf_get_max_major_ver( ssl->conf ) <
|
||||||
|
MBEDTLS_SSL_MAJOR_VERSION_3 ||
|
||||||
|
mbedtls_ssl_conf_get_min_major_ver( ssl->conf ) >
|
||||||
|
MBEDTLS_SSL_MAJOR_VERSION_3 ||
|
||||||
|
mbedtls_ssl_conf_get_max_minor_ver( ssl->conf ) <
|
||||||
|
MBEDTLS_SSL_MINOR_VERSION_3 ||
|
||||||
|
mbedtls_ssl_conf_get_min_minor_ver( ssl->conf ) >
|
||||||
|
MBEDTLS_SSL_MINOR_VERSION_3 ||
|
||||||
|
mbedtls_ssl_conf_is_renegotiation_enabled( ssl->conf ) )
|
||||||
|
{
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
}
|
||||||
|
|
||||||
|
MBEDTLS_SSL_DEBUG_BUF( 4, "context to load", buf, len );
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Check version identifier
|
||||||
|
*/
|
||||||
|
if( (size_t)( end - p ) < sizeof( ssl_serialized_context_header ) )
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
|
||||||
|
if( memcmp( p, ssl_serialized_context_header,
|
||||||
|
sizeof( ssl_serialized_context_header ) ) != 0 )
|
||||||
|
{
|
||||||
|
return( MBEDTLS_ERR_SSL_VERSION_MISMATCH );
|
||||||
|
}
|
||||||
|
p += sizeof( ssl_serialized_context_header );
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Session
|
||||||
|
*/
|
||||||
|
if( (size_t)( end - p ) < 4 )
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
|
||||||
|
session_len = ( (size_t) p[0] << 24 ) |
|
||||||
|
( (size_t) p[1] << 16 ) |
|
||||||
|
( (size_t) p[2] << 8 ) |
|
||||||
|
( (size_t) p[3] );
|
||||||
|
p += 4;
|
||||||
|
|
||||||
|
/* This has been allocated by ssl_handshake_init(), called by
|
||||||
|
* by either ssl_session_reset_int() or mbedtls_ssl_setup(). */
|
||||||
|
ssl->session = ssl->session_negotiate;
|
||||||
|
ssl->session_in = ssl->session;
|
||||||
|
ssl->session_out = ssl->session;
|
||||||
|
ssl->session_negotiate = NULL;
|
||||||
|
|
||||||
|
if( (size_t)( end - p ) < session_len )
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
|
||||||
|
ret = ssl_session_load( ssl->session, 1, p, session_len );
|
||||||
|
if( ret != 0 )
|
||||||
|
{
|
||||||
|
mbedtls_ssl_session_free( ssl->session );
|
||||||
|
return( ret );
|
||||||
|
}
|
||||||
|
|
||||||
|
p += session_len;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Transform
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* This has been allocated by ssl_handshake_init(), called by
|
||||||
|
* by either ssl_session_reset_int() or mbedtls_ssl_setup(). */
|
||||||
|
ssl->transform = ssl->transform_negotiate;
|
||||||
|
ssl->transform_in = ssl->transform;
|
||||||
|
ssl->transform_out = ssl->transform;
|
||||||
|
ssl->transform_negotiate = NULL;
|
||||||
|
|
||||||
|
/* Read random bytes and populate structure */
|
||||||
|
if( (size_t)( end - p ) < sizeof( ssl->transform->randbytes ) )
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
|
||||||
|
ret = ssl_populate_transform( ssl->transform,
|
||||||
|
mbedtls_ssl_session_get_ciphersuite( ssl->session ),
|
||||||
|
ssl->session->master,
|
||||||
|
#if defined(MBEDTLS_SSL_SOME_MODES_USE_MAC)
|
||||||
|
#if defined(MBEDTLS_SSL_ENCRYPT_THEN_MAC)
|
||||||
|
ssl->session->encrypt_then_mac,
|
||||||
|
#endif
|
||||||
|
#if defined(MBEDTLS_SSL_TRUNCATED_HMAC)
|
||||||
|
ssl->session->trunc_hmac,
|
||||||
|
#endif
|
||||||
|
#endif /* MBEDTLS_SSL_SOME_MODES_USE_MAC */
|
||||||
|
#if defined(MBEDTLS_ZLIB_SUPPORT)
|
||||||
|
ssl->session->compression,
|
||||||
|
#endif
|
||||||
|
ssl_tls12prf_from_cs(
|
||||||
|
mbedtls_ssl_session_get_ciphersuite( ssl->session) ),
|
||||||
|
p, /* currently pointing to randbytes */
|
||||||
|
MBEDTLS_SSL_MINOR_VERSION_3, /* (D)TLS 1.2 is forced */
|
||||||
|
mbedtls_ssl_conf_get_endpoint( ssl->conf ),
|
||||||
|
ssl );
|
||||||
|
if( ret != 0 )
|
||||||
|
return( ret );
|
||||||
|
|
||||||
|
p += sizeof( ssl->transform->randbytes );
|
||||||
|
|
||||||
|
#if defined(MBEDTLS_SSL_DTLS_CONNECTION_ID)
|
||||||
|
/* Read connection IDs and store them */
|
||||||
|
if( (size_t)( end - p ) < 1 )
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
|
||||||
|
ssl->transform->in_cid_len = *p++;
|
||||||
|
|
||||||
|
if( (size_t)( end - p ) < ssl->transform->in_cid_len + 1u )
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
|
||||||
|
memcpy( ssl->transform->in_cid, p, ssl->transform->in_cid_len );
|
||||||
|
p += ssl->transform->in_cid_len;
|
||||||
|
|
||||||
|
ssl->transform->out_cid_len = *p++;
|
||||||
|
|
||||||
|
if( (size_t)( end - p ) < ssl->transform->out_cid_len )
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
|
||||||
|
memcpy( ssl->transform->out_cid, p, ssl->transform->out_cid_len );
|
||||||
|
p += ssl->transform->out_cid_len;
|
||||||
|
#endif /* MBEDTLS_SSL_DTLS_CONNECTION_ID */
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Saved fields from top-level ssl_context structure
|
||||||
|
*/
|
||||||
|
#if defined(MBEDTLS_SSL_DTLS_BADMAC_LIMIT)
|
||||||
|
if( (size_t)( end - p ) < 4 )
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
|
||||||
|
ssl->badmac_seen = ( (uint32_t) p[0] << 24 ) |
|
||||||
|
( (uint32_t) p[1] << 16 ) |
|
||||||
|
( (uint32_t) p[2] << 8 ) |
|
||||||
|
( (uint32_t) p[3] );
|
||||||
|
p += 4;
|
||||||
|
#endif /* MBEDTLS_SSL_DTLS_BADMAC_LIMIT */
|
||||||
|
|
||||||
|
#if defined(MBEDTLS_SSL_DTLS_ANTI_REPLAY)
|
||||||
|
if( (size_t)( end - p ) < 16 )
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
|
||||||
|
ssl->in_window_top = ( (uint64_t) p[0] << 56 ) |
|
||||||
|
( (uint64_t) p[1] << 48 ) |
|
||||||
|
( (uint64_t) p[2] << 40 ) |
|
||||||
|
( (uint64_t) p[3] << 32 ) |
|
||||||
|
( (uint64_t) p[4] << 24 ) |
|
||||||
|
( (uint64_t) p[5] << 16 ) |
|
||||||
|
( (uint64_t) p[6] << 8 ) |
|
||||||
|
( (uint64_t) p[7] );
|
||||||
|
p += 8;
|
||||||
|
|
||||||
|
ssl->in_window = ( (uint64_t) p[0] << 56 ) |
|
||||||
|
( (uint64_t) p[1] << 48 ) |
|
||||||
|
( (uint64_t) p[2] << 40 ) |
|
||||||
|
( (uint64_t) p[3] << 32 ) |
|
||||||
|
( (uint64_t) p[4] << 24 ) |
|
||||||
|
( (uint64_t) p[5] << 16 ) |
|
||||||
|
( (uint64_t) p[6] << 8 ) |
|
||||||
|
( (uint64_t) p[7] );
|
||||||
|
p += 8;
|
||||||
|
#endif /* MBEDTLS_SSL_DTLS_ANTI_REPLAY */
|
||||||
|
|
||||||
|
#if defined(MBEDTLS_SSL_PROTO_DTLS)
|
||||||
|
if( (size_t)( end - p ) < 1 )
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
|
||||||
|
ssl->disable_datagram_packing = *p++;
|
||||||
|
#endif /* MBEDTLS_SSL_PROTO_DTLS */
|
||||||
|
|
||||||
|
if( (size_t)( end - p ) < 8 )
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
|
||||||
|
memcpy( ssl->cur_out_ctr, p, 8 );
|
||||||
|
p += 8;
|
||||||
|
|
||||||
|
#if defined(MBEDTLS_SSL_PROTO_DTLS)
|
||||||
|
if( (size_t)( end - p ) < 2 )
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
|
||||||
|
ssl->mtu = ( p[0] << 8 ) | p[1];
|
||||||
|
p += 2;
|
||||||
|
#endif /* MBEDTLS_SSL_PROTO_DTLS */
|
||||||
|
|
||||||
|
#if defined(MBEDTLS_SSL_ALPN)
|
||||||
|
{
|
||||||
|
uint8_t alpn_len;
|
||||||
|
const char **cur;
|
||||||
|
|
||||||
|
if( (size_t)( end - p ) < 1 )
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
|
||||||
|
alpn_len = *p++;
|
||||||
|
|
||||||
|
if( alpn_len != 0 && ssl->conf->alpn_list != NULL )
|
||||||
|
{
|
||||||
|
/* alpn_chosen should point to an item in the configured list */
|
||||||
|
for( cur = ssl->conf->alpn_list; *cur != NULL; cur++ )
|
||||||
|
{
|
||||||
|
if( strlen( *cur ) == alpn_len &&
|
||||||
|
memcmp( p, cur, alpn_len ) == 0 )
|
||||||
|
{
|
||||||
|
ssl->alpn_chosen = *cur;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* can only happen on conf mismatch */
|
||||||
|
if( alpn_len != 0 && ssl->alpn_chosen == NULL )
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
|
||||||
|
p += alpn_len;
|
||||||
|
}
|
||||||
|
#endif /* MBEDTLS_SSL_ALPN */
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Forced fields from top-level ssl_context structure
|
||||||
|
*
|
||||||
|
* Most of them already set to the correct value by mbedtls_ssl_init() and
|
||||||
|
* mbedtls_ssl_reset(), so we only need to set the remaining ones.
|
||||||
|
*/
|
||||||
|
ssl->state = MBEDTLS_SSL_HANDSHAKE_OVER;
|
||||||
|
|
||||||
|
#if !defined(MBEDTLS_SSL_CONF_FIXED_MAJOR_VER)
|
||||||
|
ssl->major_ver = MBEDTLS_SSL_MAJOR_VERSION_3;
|
||||||
|
#endif /* !MBEDTLS_SSL_CONF_FIXED_MAJOR_VER */
|
||||||
|
#if !defined(MBEDTLS_SSL_CONF_FIXED_MINOR_VER)
|
||||||
|
ssl->minor_ver = MBEDTLS_SSL_MINOR_VERSION_3;
|
||||||
|
#endif /* !MBEDTLS_SSL_CONF_FIXED_MINOR_VER */
|
||||||
|
|
||||||
|
#if defined(MBEDTLS_SSL_PROTO_DTLS)
|
||||||
|
ssl->in_epoch = 1;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/* mbedtls_ssl_reset() leaves the handshake sub-structure allocated,
|
||||||
|
* which we don't want - otherwise we'd end up freeing the wrong transform
|
||||||
|
* by calling ssl_handshake_wrapup_free_hs_transform() inappropriately. */
|
||||||
|
if( ssl->handshake != NULL )
|
||||||
|
{
|
||||||
|
mbedtls_ssl_handshake_free( ssl );
|
||||||
|
mbedtls_free( ssl->handshake );
|
||||||
|
ssl->handshake = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Done - should have consumed entire buffer
|
||||||
|
*/
|
||||||
|
if( p != end )
|
||||||
|
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
|
||||||
|
|
||||||
return( 0 );
|
return( 0 );
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Deserialize a full SSL context
|
* Deserialize context: public wrapper for error cleaning
|
||||||
*/
|
*/
|
||||||
int mbedtls_ssl_context_load( mbedtls_ssl_context *ssl,
|
int mbedtls_ssl_context_load( mbedtls_ssl_context *context,
|
||||||
const unsigned char *buf,
|
const unsigned char *buf,
|
||||||
size_t len )
|
size_t len )
|
||||||
{
|
{
|
||||||
/* Unimplemented */
|
int ret = ssl_context_load( context, buf, len );
|
||||||
(void) ssl;
|
|
||||||
(void) buf;
|
|
||||||
(void) len;
|
|
||||||
|
|
||||||
return( 0 );
|
if( ret != 0 )
|
||||||
|
mbedtls_ssl_free( context );
|
||||||
|
|
||||||
|
return( ret );
|
||||||
}
|
}
|
||||||
|
#endif /* MBEDTLS_SSL_CONTEXT_SERIALIZATION */
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Free an SSL context
|
* Free an SSL context
|
||||||
|
|
|
@ -807,6 +807,10 @@ int main( int argc, char *argv[] )
|
||||||
#endif
|
#endif
|
||||||
char *p, *q;
|
char *p, *q;
|
||||||
const int *list;
|
const int *list;
|
||||||
|
#if defined(MBEDTLS_SSL_CONTEXT_SERIALIZATION)
|
||||||
|
unsigned char *context_buf = NULL;
|
||||||
|
size_t context_buf_len;
|
||||||
|
#endif
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Make sure memory references are valid.
|
* Make sure memory references are valid.
|
||||||
|
@ -2493,16 +2497,11 @@ send_request:
|
||||||
if( opt.serialize != 0 )
|
if( opt.serialize != 0 )
|
||||||
{
|
{
|
||||||
size_t buf_len;
|
size_t buf_len;
|
||||||
unsigned char *context_buf = NULL;
|
|
||||||
|
|
||||||
opt.serialize = 0;
|
mbedtls_printf( " . Serializing live connection..." );
|
||||||
mbedtls_printf( " Serializing live connection..." );
|
|
||||||
|
|
||||||
ret = mbedtls_ssl_context_save( &ssl, NULL, 0, &buf_len );
|
ret = mbedtls_ssl_context_save( &ssl, NULL, 0, &buf_len );
|
||||||
|
if( ret != MBEDTLS_ERR_SSL_BUFFER_TOO_SMALL )
|
||||||
/* Allow stub implementation returning 0 for now */
|
|
||||||
if( ret != MBEDTLS_ERR_SSL_BUFFER_TOO_SMALL &&
|
|
||||||
ret != 0 )
|
|
||||||
{
|
{
|
||||||
mbedtls_printf( " failed\n ! mbedtls_ssl_context_save returned "
|
mbedtls_printf( " failed\n ! mbedtls_ssl_context_save returned "
|
||||||
"-0x%x\n\n", -ret );
|
"-0x%x\n\n", -ret );
|
||||||
|
@ -2517,18 +2516,29 @@ send_request:
|
||||||
|
|
||||||
goto exit;
|
goto exit;
|
||||||
}
|
}
|
||||||
|
context_buf_len = buf_len;
|
||||||
|
|
||||||
if( ( ret = mbedtls_ssl_context_save( &ssl, context_buf,
|
if( ( ret = mbedtls_ssl_context_save( &ssl, context_buf,
|
||||||
buf_len, &buf_len ) ) != 0 )
|
buf_len, &buf_len ) ) != 0 )
|
||||||
{
|
{
|
||||||
mbedtls_printf( "failed\n ! mbedtls_ssl_context_save returned "
|
mbedtls_printf( " failed\n ! mbedtls_ssl_context_save returned "
|
||||||
"-0x%x\n\n", -ret );
|
"-0x%x\n\n", -ret );
|
||||||
|
|
||||||
goto exit;
|
goto exit;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
mbedtls_printf( " ok\n" );
|
||||||
|
|
||||||
|
if( opt.serialize == 1 )
|
||||||
|
{
|
||||||
|
/* nothing to do here, done by context_save() already */
|
||||||
|
mbedtls_printf( " . Context has been reset... ok" );
|
||||||
|
}
|
||||||
|
|
||||||
if( opt.serialize == 2 )
|
if( opt.serialize == 2 )
|
||||||
{
|
{
|
||||||
|
mbedtls_printf( " . Freeing and reinitializing context..." );
|
||||||
|
|
||||||
mbedtls_ssl_free( &ssl );
|
mbedtls_ssl_free( &ssl );
|
||||||
|
|
||||||
mbedtls_ssl_init( &ssl );
|
mbedtls_ssl_init( &ssl );
|
||||||
|
@ -2536,7 +2546,7 @@ send_request:
|
||||||
if( ( ret = mbedtls_ssl_setup( &ssl, &conf ) ) != 0 )
|
if( ( ret = mbedtls_ssl_setup( &ssl, &conf ) ) != 0 )
|
||||||
{
|
{
|
||||||
mbedtls_printf( " failed\n ! mbedtls_ssl_setup returned "
|
mbedtls_printf( " failed\n ! mbedtls_ssl_setup returned "
|
||||||
" -0x%x\n\n", -ret );
|
"-0x%x\n\n", -ret );
|
||||||
goto exit;
|
goto exit;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2544,26 +2554,25 @@ send_request:
|
||||||
mbedtls_ssl_set_bio( &ssl, &server_fd, my_send, my_recv,
|
mbedtls_ssl_set_bio( &ssl, &server_fd, my_send, my_recv,
|
||||||
NULL );
|
NULL );
|
||||||
else
|
else
|
||||||
mbedtls_ssl_set_bio( &ssl, &server_fd,
|
mbedtls_ssl_set_bio( &ssl, &server_fd, mbedtls_net_send,
|
||||||
mbedtls_net_send, mbedtls_net_recv,
|
mbedtls_net_recv,
|
||||||
opt.nbio == 0 ? mbedtls_net_recv_timeout : NULL );
|
opt.nbio == 0 ? mbedtls_net_recv_timeout : NULL );
|
||||||
|
|
||||||
#if defined(MBEDTLS_TIMING_C)
|
#if defined(MBEDTLS_TIMING_C)
|
||||||
if( opt.nbio != 0 && opt.read_timeout != 0 )
|
|
||||||
{
|
|
||||||
#if !defined(MBEDTLS_SSL_CONF_SET_TIMER) && \
|
#if !defined(MBEDTLS_SSL_CONF_SET_TIMER) && \
|
||||||
!defined(MBEDTLS_SSL_CONF_GET_TIMER)
|
!defined(MBEDTLS_SSL_CONF_GET_TIMER)
|
||||||
mbedtls_ssl_set_timer_cb( &ssl, &timer,
|
mbedtls_ssl_set_timer_cb( &ssl, &timer,
|
||||||
mbedtls_timing_set_delay,
|
mbedtls_timing_set_delay,
|
||||||
mbedtls_timing_get_delay );
|
mbedtls_timing_get_delay );
|
||||||
#else
|
#else
|
||||||
mbedtls_ssl_set_timer_cb_ctx( &ssl, &timer );
|
mbedtls_ssl_set_timer_cb_ctx( &ssl, &timer );
|
||||||
#endif
|
#endif
|
||||||
}
|
|
||||||
#endif /* MBEDTLS_TIMING_C */
|
#endif /* MBEDTLS_TIMING_C */
|
||||||
|
|
||||||
|
mbedtls_printf( " ok\n" );
|
||||||
}
|
}
|
||||||
|
|
||||||
mbedtls_printf( " Deserializing connection..." );
|
mbedtls_printf( " . Deserializing connection..." );
|
||||||
|
|
||||||
if( ( ret = mbedtls_ssl_context_load( &ssl, context_buf,
|
if( ( ret = mbedtls_ssl_context_load( &ssl, context_buf,
|
||||||
buf_len ) ) != 0 )
|
buf_len ) ) != 0 )
|
||||||
|
@ -2573,6 +2582,12 @@ send_request:
|
||||||
|
|
||||||
goto exit;
|
goto exit;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
mbedtls_free( context_buf );
|
||||||
|
context_buf = NULL;
|
||||||
|
context_buf_len = 0;
|
||||||
|
|
||||||
|
mbedtls_printf( " ok\n" );
|
||||||
}
|
}
|
||||||
#endif /* MBEDTLS_SSL_CONTEXT_SERIALIZATION */
|
#endif /* MBEDTLS_SSL_CONTEXT_SERIALIZATION */
|
||||||
|
|
||||||
|
@ -2711,6 +2726,11 @@ exit:
|
||||||
if( session_data != NULL )
|
if( session_data != NULL )
|
||||||
mbedtls_platform_zeroize( session_data, session_data_len );
|
mbedtls_platform_zeroize( session_data, session_data_len );
|
||||||
mbedtls_free( session_data );
|
mbedtls_free( session_data );
|
||||||
|
#if defined(MBEDTLS_SSL_CONTEXT_SERIALIZATION)
|
||||||
|
if( context_buf != NULL )
|
||||||
|
mbedtls_platform_zeroize( context_buf, context_buf_len );
|
||||||
|
mbedtls_free( context_buf );
|
||||||
|
#endif
|
||||||
|
|
||||||
#if defined(_WIN32)
|
#if defined(_WIN32)
|
||||||
mbedtls_printf( " + Press Enter to exit this program.\n" );
|
mbedtls_printf( " + Press Enter to exit this program.\n" );
|
||||||
|
|
|
@ -1443,6 +1443,10 @@ int main( int argc, char *argv[] )
|
||||||
size_t cid_len = 0;
|
size_t cid_len = 0;
|
||||||
size_t cid_renego_len = 0;
|
size_t cid_renego_len = 0;
|
||||||
#endif
|
#endif
|
||||||
|
#if defined(MBEDTLS_SSL_CONTEXT_SERIALIZATION)
|
||||||
|
unsigned char *context_buf = NULL;
|
||||||
|
size_t context_buf_len;
|
||||||
|
#endif
|
||||||
|
|
||||||
int i;
|
int i;
|
||||||
char *p, *q;
|
char *p, *q;
|
||||||
|
@ -3508,16 +3512,11 @@ data_exchange:
|
||||||
if( opt.serialize != 0 )
|
if( opt.serialize != 0 )
|
||||||
{
|
{
|
||||||
size_t buf_len;
|
size_t buf_len;
|
||||||
unsigned char *context_buf = NULL;
|
|
||||||
|
|
||||||
opt.serialize = 0;
|
mbedtls_printf( " . Serializing live connection..." );
|
||||||
mbedtls_printf( " Serializing live connection..." );
|
|
||||||
|
|
||||||
ret = mbedtls_ssl_context_save( &ssl, NULL, 0, &buf_len );
|
ret = mbedtls_ssl_context_save( &ssl, NULL, 0, &buf_len );
|
||||||
|
if( ret != MBEDTLS_ERR_SSL_BUFFER_TOO_SMALL )
|
||||||
/* Allow stub implementation returning 0 for now */
|
|
||||||
if( ret != MBEDTLS_ERR_SSL_BUFFER_TOO_SMALL &&
|
|
||||||
ret != 0 )
|
|
||||||
{
|
{
|
||||||
mbedtls_printf( " failed\n ! mbedtls_ssl_context_save returned "
|
mbedtls_printf( " failed\n ! mbedtls_ssl_context_save returned "
|
||||||
"-0x%x\n\n", -ret );
|
"-0x%x\n\n", -ret );
|
||||||
|
@ -3532,18 +3531,44 @@ data_exchange:
|
||||||
|
|
||||||
goto exit;
|
goto exit;
|
||||||
}
|
}
|
||||||
|
context_buf_len = buf_len;
|
||||||
|
|
||||||
if( ( ret = mbedtls_ssl_context_save( &ssl, context_buf,
|
if( ( ret = mbedtls_ssl_context_save( &ssl, context_buf,
|
||||||
buf_len, &buf_len ) ) != 0 )
|
buf_len, &buf_len ) ) != 0 )
|
||||||
{
|
{
|
||||||
mbedtls_printf( "failed\n ! mbedtls_ssl_context_save returned "
|
mbedtls_printf( " failed\n ! mbedtls_ssl_context_save returned "
|
||||||
"-0x%x\n\n", -ret );
|
"-0x%x\n\n", -ret );
|
||||||
|
|
||||||
goto exit;
|
goto exit;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
mbedtls_printf( " ok\n" );
|
||||||
|
|
||||||
|
/*
|
||||||
|
* This simulates a workflow where you have a long-lived server
|
||||||
|
* instance, potentially with a pool of ssl_context objects, and you
|
||||||
|
* just want to re-use one while the connection is inactive: in that
|
||||||
|
* case you can just reset() it, and then it's ready to receive
|
||||||
|
* serialized data from another connection (or the same here).
|
||||||
|
*/
|
||||||
|
if( opt.serialize == 1 )
|
||||||
|
{
|
||||||
|
/* nothing to do here, done by context_save() already */
|
||||||
|
mbedtls_printf( " . Context has been reset... ok" );
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* This simulates a workflow where you have one server instance per
|
||||||
|
* connection, and want to release it entire when the connection is
|
||||||
|
* inactive, and spawn it again when needed again - this would happen
|
||||||
|
* between ssl_free() and ssl_init() below, together with any other
|
||||||
|
* teardown/startup code needed - for example, preparing the
|
||||||
|
* ssl_config again (see section 3 "setup stuff" in this file).
|
||||||
|
*/
|
||||||
if( opt.serialize == 2 )
|
if( opt.serialize == 2 )
|
||||||
{
|
{
|
||||||
|
mbedtls_printf( " . Freeing and reinitializing context..." );
|
||||||
|
|
||||||
mbedtls_ssl_free( &ssl );
|
mbedtls_ssl_free( &ssl );
|
||||||
|
|
||||||
mbedtls_ssl_init( &ssl );
|
mbedtls_ssl_init( &ssl );
|
||||||
|
@ -3555,6 +3580,12 @@ data_exchange:
|
||||||
goto exit;
|
goto exit;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* This illustrates the minimum amount of things you need to set
|
||||||
|
* up, however you could set up much more if desired, for example
|
||||||
|
* if you want to share your set up code between the case of
|
||||||
|
* establishing a new connection and this case.
|
||||||
|
*/
|
||||||
if( opt.nbio == 2 )
|
if( opt.nbio == 2 )
|
||||||
mbedtls_ssl_set_bio( &ssl, &client_fd, my_send, my_recv,
|
mbedtls_ssl_set_bio( &ssl, &client_fd, my_send, my_recv,
|
||||||
NULL );
|
NULL );
|
||||||
|
@ -3564,21 +3595,20 @@ data_exchange:
|
||||||
opt.nbio == 0 ? mbedtls_net_recv_timeout : NULL );
|
opt.nbio == 0 ? mbedtls_net_recv_timeout : NULL );
|
||||||
|
|
||||||
#if defined(MBEDTLS_TIMING_C)
|
#if defined(MBEDTLS_TIMING_C)
|
||||||
if( opt.nbio != 0 && opt.read_timeout != 0 )
|
|
||||||
{
|
|
||||||
#if !defined(MBEDTLS_SSL_CONF_SET_TIMER) && \
|
#if !defined(MBEDTLS_SSL_CONF_SET_TIMER) && \
|
||||||
!defined(MBEDTLS_SSL_CONF_GET_TIMER)
|
!defined(MBEDTLS_SSL_CONF_GET_TIMER)
|
||||||
mbedtls_ssl_set_timer_cb( &ssl, &timer,
|
mbedtls_ssl_set_timer_cb( &ssl, &timer,
|
||||||
mbedtls_timing_set_delay,
|
mbedtls_timing_set_delay,
|
||||||
mbedtls_timing_get_delay );
|
mbedtls_timing_get_delay );
|
||||||
#else
|
#else
|
||||||
mbedtls_ssl_set_timer_cb_ctx( &ssl, &timer );
|
mbedtls_ssl_set_timer_cb_ctx( &ssl, &timer );
|
||||||
#endif
|
#endif
|
||||||
}
|
|
||||||
#endif /* MBEDTLS_TIMING_C */
|
#endif /* MBEDTLS_TIMING_C */
|
||||||
|
|
||||||
|
mbedtls_printf( " ok\n" );
|
||||||
}
|
}
|
||||||
|
|
||||||
mbedtls_printf( " Deserializing connection..." );
|
mbedtls_printf( " . Deserializing connection..." );
|
||||||
|
|
||||||
if( ( ret = mbedtls_ssl_context_load( &ssl, context_buf,
|
if( ( ret = mbedtls_ssl_context_load( &ssl, context_buf,
|
||||||
buf_len ) ) != 0 )
|
buf_len ) ) != 0 )
|
||||||
|
@ -3588,6 +3618,12 @@ data_exchange:
|
||||||
|
|
||||||
goto exit;
|
goto exit;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
mbedtls_free( context_buf );
|
||||||
|
context_buf = NULL;
|
||||||
|
context_buf_len = 0;
|
||||||
|
|
||||||
|
mbedtls_printf( " ok\n" );
|
||||||
}
|
}
|
||||||
#endif /* MBEDTLS_SSL_CONTEXT_SERIALIZATION */
|
#endif /* MBEDTLS_SSL_CONTEXT_SERIALIZATION */
|
||||||
|
|
||||||
|
@ -3679,6 +3715,12 @@ exit:
|
||||||
|
|
||||||
mbedtls_free( buf );
|
mbedtls_free( buf );
|
||||||
|
|
||||||
|
#if defined(MBEDTLS_SSL_CONTEXT_SERIALIZATION)
|
||||||
|
if( context_buf != NULL )
|
||||||
|
mbedtls_platform_zeroize( context_buf, context_buf_len );
|
||||||
|
mbedtls_free( context_buf );
|
||||||
|
#endif
|
||||||
|
|
||||||
#if defined(MBEDTLS_MEMORY_BUFFER_ALLOC_C)
|
#if defined(MBEDTLS_MEMORY_BUFFER_ALLOC_C)
|
||||||
#if defined(MBEDTLS_MEMORY_DEBUG)
|
#if defined(MBEDTLS_MEMORY_DEBUG)
|
||||||
mbedtls_memory_buffer_alloc_status();
|
mbedtls_memory_buffer_alloc_status();
|
||||||
|
|
|
@ -1322,56 +1322,50 @@ run_test "Truncated HMAC, DTLS: client enabled, server enabled" \
|
||||||
|
|
||||||
# Tests for Context serialization
|
# Tests for Context serialization
|
||||||
|
|
||||||
skip_next_test
|
|
||||||
requires_config_enabled MBEDTLS_SSL_CONTEXT_SERIALIZATION
|
requires_config_enabled MBEDTLS_SSL_CONTEXT_SERIALIZATION
|
||||||
run_test "(STUB) Context serialization, client serializes" \
|
run_test "Context serialization, client serializes" \
|
||||||
"$P_SRV serialize=0 exchanges=2" \
|
"$P_SRV dtls=1 serialize=0 exchanges=2" \
|
||||||
"$P_CLI serialize=1 exchanges=2" \
|
"$P_CLI dtls=1 serialize=1 exchanges=2" \
|
||||||
0 \
|
0 \
|
||||||
-c "Deserializing connection..." \
|
-c "Deserializing connection..." \
|
||||||
-S "Deserializing connection..."
|
-S "Deserializing connection..."
|
||||||
|
|
||||||
skip_next_test
|
|
||||||
requires_config_enabled MBEDTLS_SSL_CONTEXT_SERIALIZATION
|
requires_config_enabled MBEDTLS_SSL_CONTEXT_SERIALIZATION
|
||||||
run_test "(STUB) Context serialization, server serializes" \
|
run_test "Context serialization, server serializes" \
|
||||||
"$P_SRV serialize=1 exchanges=2" \
|
"$P_SRV dtls=1 serialize=1 exchanges=2" \
|
||||||
"$P_CLI serialize=0 exchanges=2" \
|
"$P_CLI dtls=1 serialize=0 exchanges=2" \
|
||||||
0 \
|
0 \
|
||||||
-C "Deserializing connection..." \
|
-C "Deserializing connection..." \
|
||||||
-s "Deserializing connection..."
|
-s "Deserializing connection..."
|
||||||
|
|
||||||
skip_next_test
|
|
||||||
requires_config_enabled MBEDTLS_SSL_CONTEXT_SERIALIZATION
|
requires_config_enabled MBEDTLS_SSL_CONTEXT_SERIALIZATION
|
||||||
run_test "(STUB) Context serialization, both serialize" \
|
run_test "Context serialization, both serialize" \
|
||||||
"$P_SRV serialize=1 exchanges=2" \
|
"$P_SRV dtls=1 serialize=1 exchanges=2" \
|
||||||
"$P_CLI serialize=1 exchanges=2" \
|
"$P_CLI dtls=1 serialize=1 exchanges=2" \
|
||||||
0 \
|
0 \
|
||||||
-c "Deserializing connection..." \
|
-c "Deserializing connection..." \
|
||||||
-s "Deserializing connection..."
|
-s "Deserializing connection..."
|
||||||
|
|
||||||
skip_next_test
|
|
||||||
requires_config_enabled MBEDTLS_SSL_CONTEXT_SERIALIZATION
|
requires_config_enabled MBEDTLS_SSL_CONTEXT_SERIALIZATION
|
||||||
run_test "(STUB) Context serialization, re-init, client serializes" \
|
run_test "Context serialization, re-init, client serializes" \
|
||||||
"$P_SRV serialize=0 exchanges=2" \
|
"$P_SRV dtls=1 serialize=0 exchanges=2" \
|
||||||
"$P_CLI serialize=2 exchanges=2" \
|
"$P_CLI dtls=1 serialize=2 exchanges=2" \
|
||||||
0 \
|
0 \
|
||||||
-c "Deserializing connection..." \
|
-c "Deserializing connection..." \
|
||||||
-S "Deserializing connection..."
|
-S "Deserializing connection..."
|
||||||
|
|
||||||
skip_next_test
|
|
||||||
requires_config_enabled MBEDTLS_SSL_CONTEXT_SERIALIZATION
|
requires_config_enabled MBEDTLS_SSL_CONTEXT_SERIALIZATION
|
||||||
run_test "(STUB) Context serialization, re-init, server serializes" \
|
run_test "Context serialization, re-init, server serializes" \
|
||||||
"$P_SRV serialize=2 exchanges=2" \
|
"$P_SRV dtls=1 serialize=2 exchanges=2" \
|
||||||
"$P_CLI serialize=0 exchanges=2" \
|
"$P_CLI dtls=1 serialize=0 exchanges=2" \
|
||||||
0 \
|
0 \
|
||||||
-C "Deserializing connection..." \
|
-C "Deserializing connection..." \
|
||||||
-s "Deserializing connection..."
|
-s "Deserializing connection..."
|
||||||
|
|
||||||
skip_next_test
|
|
||||||
requires_config_enabled MBEDTLS_SSL_CONTEXT_SERIALIZATION
|
requires_config_enabled MBEDTLS_SSL_CONTEXT_SERIALIZATION
|
||||||
run_test "(STUB) Context serialization, re-init, both serialize" \
|
run_test "Context serialization, re-init, both serialize" \
|
||||||
"$P_SRV serialize=2 exchanges=2" \
|
"$P_SRV dtls=1 serialize=2 exchanges=2" \
|
||||||
"$P_CLI serialize=2 exchanges=2" \
|
"$P_CLI dtls=1 serialize=2 exchanges=2" \
|
||||||
0 \
|
0 \
|
||||||
-c "Deserializing connection..." \
|
-c "Deserializing connection..." \
|
||||||
-s "Deserializing connection..."
|
-s "Deserializing connection..."
|
||||||
|
|
Loading…
Reference in a new issue