Auto-renegotiate before sequence number wrapping
diff --git a/library/ssl_tls.c b/library/ssl_tls.c
index df57bb1..0e97c11 100644
--- a/library/ssl_tls.c
+++ b/library/ssl_tls.c
@@ -4273,6 +4273,33 @@
return( ret );
}
+
+/*
+ * Check record counters and renegotiate if they're above the limit.
+ */
+static int ssl_check_ctr_renegotiate( ssl_context *ssl )
+{
+ static const unsigned char ctr_limit[8] = {
+ 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00
+ };
+
+ if( ssl->state != SSL_HANDSHAKE_OVER ||
+ ssl->renegotiation == SSL_RENEGOTIATION_PENDING ||
+ ssl->disable_renegotiation == SSL_RENEGOTIATION_DISABLED )
+ {
+ return( 0 );
+ }
+
+ // TODO: adapt for DTLS
+ if( memcmp( ssl->in_ctr, ctr_limit, 8 ) <= 0 &&
+ memcmp( ssl->out_ctr, ctr_limit, 8 ) <= 0 )
+ {
+ return( 0 );
+ }
+
+ SSL_DEBUG_MSG( 2, ( "record counter about to wrap: renegotiate" ) );
+ return( ssl_renegotiate( ssl ) );
+}
#endif /* POLARSSL_SSL_RENEGOTIATION */
/*
@@ -4285,6 +4312,14 @@
SSL_DEBUG_MSG( 2, ( "=> read" ) );
+#if defined(POLARSSL_SSL_RENEGOTIATION)
+ if( ( ret = ssl_check_ctr_renegotiate( ssl ) ) != 0 )
+ {
+ SSL_DEBUG_RET( 1, "ssl_check_ctr_renegotiate", ret );
+ return( ret );
+ }
+#endif
+
if( ssl->state != SSL_HANDSHAKE_OVER )
{
ret = ssl_handshake( ssl );
@@ -4457,6 +4492,14 @@
SSL_DEBUG_MSG( 2, ( "=> write" ) );
+#if defined(POLARSSL_SSL_RENEGOTIATION)
+ if( ( ret = ssl_check_ctr_renegotiate( ssl ) ) != 0 )
+ {
+ SSL_DEBUG_RET( 1, "ssl_check_ctr_renegotiate", ret );
+ return( ret );
+ }
+#endif
+
if( ssl->state != SSL_HANDSHAKE_OVER )
{
if( ( ret = ssl_handshake( ssl ) ) != 0 )