Merge pull request #6087 from yuhaoth/pr/add-tls13-serialize_session_save_load

TLS 1.3: Add serialize session save load
I can see that https://github.com/Mbed-TLS/mbedtls/pull/6087#discussion_r927935696 and https://github.com/Mbed-TLS/mbedtls/pull/6087#discussion_r924252403 are addressed in  #6123. Thus I am ok to merge it as it is.
diff --git a/include/mbedtls/ssl.h b/include/mbedtls/ssl.h
index c6a54f7..ebb3f51 100644
--- a/include/mbedtls/ssl.h
+++ b/include/mbedtls/ssl.h
@@ -1184,6 +1184,8 @@
 #endif /* MBEDTLS_SSL_SESSION_TICKETS && MBEDTLS_SSL_CLI_C */
 
 #if defined(MBEDTLS_SSL_PROTO_TLS1_3) && defined(MBEDTLS_SSL_SESSION_TICKETS)
+    uint8_t MBEDTLS_PRIVATE(endpoint);          /*!< 0: client, 1: server */
+    uint8_t MBEDTLS_PRIVATE(ticket_flags);      /*!< Ticket flags */
     uint32_t MBEDTLS_PRIVATE(ticket_age_add);               /*!< Randomly generated value used to obscure the age of the ticket */
     uint8_t MBEDTLS_PRIVATE(resumption_key_len);            /*!< resumption_key length */
     unsigned char MBEDTLS_PRIVATE(resumption_key)[MBEDTLS_SSL_TLS1_3_TICKET_RESUMPTION_KEY_LEN];
diff --git a/library/ssl_tls.c b/library/ssl_tls.c
index 887daf8..ca8d6ff 100644
--- a/library/ssl_tls.c
+++ b/library/ssl_tls.c
@@ -440,12 +440,12 @@
 static void ssl_calc_finished_tls_sha384( mbedtls_ssl_context *, unsigned char *, int );
 #endif /* MBEDTLS_SHA384_C */
 
-static size_t ssl_session_save_tls12( const mbedtls_ssl_session *session,
+static size_t ssl_tls12_session_save( const mbedtls_ssl_session *session,
                                       unsigned char *buf,
                                       size_t buf_len );
 
 MBEDTLS_CHECK_RETURN_CRITICAL
-static int ssl_session_load_tls12( mbedtls_ssl_session *session,
+static int ssl_tls12_session_load( mbedtls_ssl_session *session,
                                    const unsigned char *buf,
                                    size_t len );
 #endif /* MBEDTLS_SSL_PROTO_TLS1_2 */
@@ -1893,7 +1893,170 @@
 #if defined(MBEDTLS_USE_PSA_CRYPTO) || defined(MBEDTLS_SSL_PROTO_TLS1_3)
 
 #if defined(MBEDTLS_SSL_PROTO_TLS1_3)
-static size_t ssl_session_save_tls13( const mbedtls_ssl_session *session,
+/* Serialization of TLS 1.3 sessions:
+ *
+ *     struct {
+ *       uint64 ticket_received;
+ *       uint32 ticket_lifetime;
+ *       opaque ticket<0..2^16>;
+ *     } ClientOnlyData;
+ *
+ *     struct {
+ *       uint8 endpoint;
+ *       uint8 ciphersuite[2];
+ *       uint32 ticket_age_add;
+ *       uint8 ticket_flags;
+ *       opaque resumption_key<0..255>;
+ *       select ( endpoint ) {
+ *            case client: ClientOnlyData;
+ *            case server: uint64 start_time;
+ *        };
+ *     } serialized_session_tls13;
+ *
+ */
+#if defined(MBEDTLS_SSL_SESSION_TICKETS)
+static size_t ssl_tls13_session_save( const mbedtls_ssl_session *session,
+                                      unsigned char *buf,
+                                      size_t buf_len )
+{
+    unsigned char *p = buf;
+    size_t needed =   1                             /* endpoint */
+                    + 2                             /* ciphersuite */
+                    + 4                             /* ticket_age_add */
+                    + 2                             /* resumption_key length */
+                    + session->resumption_key_len;  /* resumption_key */
+
+#if defined(MBEDTLS_HAVE_TIME)
+    needed += 8; /* start_time or ticket_received */
+#endif
+
+#if defined(MBEDTLS_SSL_CLI_C)
+    if( session->endpoint == MBEDTLS_SSL_IS_CLIENT )
+    {
+        needed +=   4                       /* ticket_lifetime */
+                  + 2                       /* ticket_len */
+                  + session->ticket_len;    /* ticket */
+    }
+#endif /* MBEDTLS_SSL_CLI_C */
+
+    if( needed > buf_len )
+        return( needed );
+
+    p[0] = session->endpoint;
+    MBEDTLS_PUT_UINT16_BE( session->ciphersuite, p, 1 );
+    MBEDTLS_PUT_UINT32_BE( session->ticket_age_add, p, 3 );
+    p[7] = session->ticket_flags;
+
+    /* save resumption_key */
+    p[8] = session->resumption_key_len;
+    p += 9;
+    memcpy( p, session->resumption_key, session->resumption_key_len );
+    p += session->resumption_key_len;
+
+#if defined(MBEDTLS_HAVE_TIME) && defined(MBEDTLS_SSL_SRV_C)
+    if( session->endpoint == MBEDTLS_SSL_IS_SERVER )
+    {
+        MBEDTLS_PUT_UINT64_BE( (uint64_t) session->start, p, 0 );
+        p += 8;
+    }
+#endif /* MBEDTLS_HAVE_TIME */
+
+#if defined(MBEDTLS_SSL_CLI_C)
+    if( session->endpoint == MBEDTLS_SSL_IS_CLIENT )
+    {
+#if defined(MBEDTLS_HAVE_TIME)
+        MBEDTLS_PUT_UINT64_BE( (uint64_t) session->ticket_received, p, 0 );
+        p += 8;
+#endif
+        MBEDTLS_PUT_UINT32_BE( session->ticket_lifetime, p, 0 );
+        p += 4;
+
+        MBEDTLS_PUT_UINT16_BE( session->ticket_len, p, 0 );
+        p += 2;
+        if( session->ticket_len > 0 )
+        {
+            memcpy( p, session->ticket, session->ticket_len );
+            p += session->ticket_len;
+        }
+    }
+#endif /* MBEDTLS_SSL_CLI_C */
+    return( needed );
+}
+
+MBEDTLS_CHECK_RETURN_CRITICAL
+static int ssl_tls13_session_load( mbedtls_ssl_session *session,
+                                   const unsigned char *buf,
+                                   size_t len )
+{
+    const unsigned char *p = buf;
+    const unsigned char *end = buf + len;
+
+    if( end - p < 9 )
+        return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
+    session->endpoint = p[0];
+    session->ciphersuite = MBEDTLS_GET_UINT16_BE( p, 1 );
+    session->ticket_age_add = MBEDTLS_GET_UINT32_BE( p, 3 );
+    session->ticket_flags = p[7];
+
+    /* load resumption_key */
+    session->resumption_key_len = p[8];
+    p += 9;
+
+    if( end - p < session->resumption_key_len )
+        return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
+
+    if( sizeof( session->resumption_key ) < session->resumption_key_len )
+        return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
+    memcpy( session->resumption_key, p, session->resumption_key_len );
+    p += session->resumption_key_len;
+
+#if defined(MBEDTLS_HAVE_TIME) && defined(MBEDTLS_SSL_SRV_C)
+    if( session->endpoint == MBEDTLS_SSL_IS_SERVER )
+    {
+        if( end - p < 8 )
+            return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
+        session->start = MBEDTLS_GET_UINT64_BE( p, 0 );
+        p += 8;
+    }
+#endif /* MBEDTLS_HAVE_TIME */
+
+#if defined(MBEDTLS_SSL_CLI_C)
+    if( session->endpoint == MBEDTLS_SSL_IS_CLIENT )
+    {
+#if defined(MBEDTLS_HAVE_TIME)
+        if( end - p < 8 )
+            return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
+        session->ticket_received = MBEDTLS_GET_UINT64_BE( p, 0 );
+        p += 8;
+#endif
+        if( end - p < 4 )
+            return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
+        session->ticket_lifetime = MBEDTLS_GET_UINT32_BE( p, 0 );
+        p += 4;
+
+        if( end - p <  2 )
+            return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
+        session->ticket_len = MBEDTLS_GET_UINT16_BE( p, 0 );
+        p += 2;
+
+        if( end - p < ( long int )session->ticket_len )
+            return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
+        if( session->ticket_len > 0 )
+        {
+            session->ticket = mbedtls_calloc( 1, session->ticket_len );
+            if( session->ticket == NULL )
+                return( MBEDTLS_ERR_SSL_ALLOC_FAILED );
+            memcpy( session->ticket, p, session->ticket_len );
+            p += session->ticket_len;
+        }
+    }
+#endif /* MBEDTLS_SSL_CLI_C */
+
+    return( 0 );
+
+}
+#else /* MBEDTLS_SSL_SESSION_TICKETS */
+static size_t ssl_tls13_session_save( const mbedtls_ssl_session *session,
                                       unsigned char *buf,
                                       size_t buf_len )
 {
@@ -1902,6 +2065,17 @@
     ((void) buf_len);
     return( 0 );
 }
+
+static int ssl_tls13_session_load( const mbedtls_ssl_session *session,
+                                   unsigned char *buf,
+                                   size_t buf_len )
+{
+    ((void) session);
+    ((void) buf);
+    ((void) buf_len);
+    return( MBEDTLS_ERR_SSL_FEATURE_UNAVAILABLE );
+}
+#endif /* !MBEDTLS_SSL_SESSION_TICKETS */
 #endif /* MBEDTLS_SSL_PROTO_TLS1_3 */
 
 psa_status_t mbedtls_ssl_cipher_to_psa( mbedtls_cipher_type_t mbedtls_cipher_type,
@@ -2832,12 +3006,14 @@
     size_t used = 0;
     size_t remaining_len;
 
+    if( session == NULL )
+        return( MBEDTLS_ERR_SSL_INTERNAL_ERROR );
+
     if( !omit_header )
     {
         /*
          * Add Mbed TLS version identifier
          */
-
         used += sizeof( ssl_serialized_session_header );
 
         if( used <= buf_len )
@@ -2863,18 +3039,14 @@
     {
 #if defined(MBEDTLS_SSL_PROTO_TLS1_2)
     case MBEDTLS_SSL_VERSION_TLS1_2:
-    {
-        used += ssl_session_save_tls12( session, p, remaining_len );
+        used += ssl_tls12_session_save( session, p, remaining_len );
         break;
-    }
 #endif /* MBEDTLS_SSL_PROTO_TLS1_2 */
 
 #if defined(MBEDTLS_SSL_PROTO_TLS1_3)
     case MBEDTLS_SSL_VERSION_TLS1_3:
-    {
-        used += ssl_session_save_tls13( session, p, remaining_len );
+        used += ssl_tls13_session_save( session, p, remaining_len );
         break;
-    }
 #endif /* MBEDTLS_SSL_PROTO_TLS1_3 */
 
     default:
@@ -2913,6 +3085,11 @@
 {
     const unsigned char *p = buf;
     const unsigned char * const end = buf + len;
+    size_t remaining_len;
+
+
+    if( session == NULL )
+        return( MBEDTLS_ERR_SSL_INTERNAL_ERROR );
 
     if( !omit_header )
     {
@@ -2939,16 +3116,19 @@
     session->tls_version = 0x0300 | *p++;
 
     /* Dispatch according to TLS version. */
+    remaining_len = ( end - p );
     switch( session->tls_version )
     {
 #if defined(MBEDTLS_SSL_PROTO_TLS1_2)
     case MBEDTLS_SSL_VERSION_TLS1_2:
-    {
-        size_t remaining_len = ( end - p );
-        return( ssl_session_load_tls12( session, p, remaining_len ) );
-    }
+        return( ssl_tls12_session_load( session, p, remaining_len ) );
 #endif /* MBEDTLS_SSL_PROTO_TLS1_2 */
 
+#if defined(MBEDTLS_SSL_PROTO_TLS1_3)
+    case MBEDTLS_SSL_VERSION_TLS1_3:
+        return( ssl_tls13_session_load( session, p, remaining_len ) );
+#endif /* MBEDTLS_SSL_PROTO_TLS1_3 */
+
     default:
         return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
     }
@@ -7831,7 +8011,7 @@
  * } serialized_session_tls12;
  *
  */
-static size_t ssl_session_save_tls12( const mbedtls_ssl_session *session,
+static size_t ssl_tls12_session_save( const mbedtls_ssl_session *session,
                                       unsigned char *buf,
                                       size_t buf_len )
 {
@@ -7983,7 +8163,7 @@
 }
 
 MBEDTLS_CHECK_RETURN_CRITICAL
-static int ssl_session_load_tls12( mbedtls_ssl_session *session,
+static int ssl_tls12_session_load( mbedtls_ssl_session *session,
                                    const unsigned char *buf,
                                    size_t len )
 {
diff --git a/library/ssl_tls13_client.c b/library/ssl_tls13_client.c
index cd3be46..91c2058 100644
--- a/library/ssl_tls13_client.c
+++ b/library/ssl_tls13_client.c
@@ -1110,6 +1110,7 @@
 
     MBEDTLS_SSL_PROC_CHK_NEG( ssl_tls13_is_supported_versions_ext_present(
                                   ssl, buf, end ) );
+
     if( ret == 0 )
     {
         MBEDTLS_SSL_PROC_CHK_NEG(
@@ -1143,6 +1144,11 @@
         return( SSL_SERVER_HELLO_TLS1_2 );
     }
 
+#if defined(MBEDTLS_SSL_SESSION_TICKETS)
+    ssl->session_negotiate->endpoint = ssl->conf->endpoint;
+    ssl->session_negotiate->tls_version = ssl->tls_version;
+#endif /* MBEDTLS_SSL_SESSION_TICKETS */
+
     handshake->extensions_present = MBEDTLS_SSL_EXT_NONE;
 
     ret = ssl_server_hello_is_hrr( ssl, buf, end );
diff --git a/library/ssl_tls13_server.c b/library/ssl_tls13_server.c
index 3bfffb1..701d044 100644
--- a/library/ssl_tls13_server.c
+++ b/library/ssl_tls13_server.c
@@ -1006,6 +1006,7 @@
 #if defined(MBEDTLS_SSL_SESSION_TICKETS)
     /* Store minor version for later use with ticket serialization. */
     ssl->session_negotiate->tls_version = MBEDTLS_SSL_VERSION_TLS1_3;
+    ssl->session_negotiate->endpoint = ssl->conf->endpoint;
 #endif
 
     /* ...
diff --git a/tests/ssl-opt.sh b/tests/ssl-opt.sh
index 852ae52..7a2b58e 100755
--- a/tests/ssl-opt.sh
+++ b/tests/ssl-opt.sh
@@ -12658,11 +12658,12 @@
 requires_config_enabled MBEDTLS_SSL_TLS1_3_COMPATIBILITY_MODE
 run_test    "TLS 1.3: NewSessionTicket: Basic check, m->O" \
             "$O_NEXT_SRV -msg -tls1_3 -no_resume_ephemeral -no_cache " \
-            "$P_CLI debug_level=4" \
+            "$P_CLI debug_level=4 reco_mode=1 reconnect=1" \
             0 \
             -c "Protocol is TLSv1.3" \
             -c "MBEDTLS_SSL_NEW_SESSION_TICKET" \
             -c "got new session ticket." \
+            -c "Saving session for reuse... ok" \
             -c "HTTP/1.0 200 ok"
 
 requires_gnutls_tls1_3
@@ -12672,11 +12673,12 @@
 requires_config_enabled MBEDTLS_SSL_CLI_C
 run_test    "TLS 1.3: NewSessionTicket: Basic check, m->G" \
             "$G_NEXT_SRV --priority=NORMAL:-VERS-ALL:+VERS-TLS1.3:+CIPHER-ALL:+PSK --disable-client-cert" \
-            "$P_CLI debug_level=4" \
+            "$P_CLI debug_level=4 reco_mode=1 reconnect=1" \
             0 \
             -c "Protocol is TLSv1.3" \
             -c "MBEDTLS_SSL_NEW_SESSION_TICKET" \
             -c "got new session ticket." \
+            -c "Saving session for reuse... ok" \
             -c "HTTP/1.0 200 OK"
 
 requires_openssl_tls1_3
@@ -12713,11 +12715,12 @@
 requires_config_enabled MBEDTLS_DEBUG_C
 run_test    "TLS 1.3: NewSessionTicket: Basic check, m->m" \
             "$P_SRV debug_level=4 crt_file=data_files/server5.crt key_file=data_files/server5.key force_version=tls13 tickets=1" \
-            "$P_CLI debug_level=4" \
+            "$P_CLI debug_level=4 reco_mode=1 reconnect=1" \
             0 \
             -c "Protocol is TLSv1.3" \
             -c "MBEDTLS_SSL_NEW_SESSION_TICKET" \
             -c "got new session ticket." \
+            -c "Saving session for reuse... ok" \
             -c "HTTP/1.0 200 OK"    \
             -s "=> write NewSessionTicket msg" \
             -s "server state: MBEDTLS_SSL_NEW_SESSION_TICKET" \
diff --git a/tests/suites/test_suite_ssl.data b/tests/suites/test_suite_ssl.data
index 34f4d66..d7b2fdf 100644
--- a/tests/suites/test_suite_ssl.data
+++ b/tests/suites/test_suite_ssl.data
@@ -796,19 +796,51 @@
 
 SSL session serialization: Wrong major version
 depends_on:MBEDTLS_SSL_PROTO_TLS1_2
-ssl_session_serialize_version_check:1:0:0:0
+ssl_session_serialize_version_check:1:0:0:0:0:MBEDTLS_SSL_VERSION_TLS1_2
 
 SSL session serialization: Wrong minor version
 depends_on:MBEDTLS_SSL_PROTO_TLS1_2
-ssl_session_serialize_version_check:0:1:0:0
+ssl_session_serialize_version_check:0:1:0:0:0:MBEDTLS_SSL_VERSION_TLS1_2
 
 SSL session serialization: Wrong patch version
 depends_on:MBEDTLS_SSL_PROTO_TLS1_2
-ssl_session_serialize_version_check:0:0:1:0
+ssl_session_serialize_version_check:0:0:1:0:0:MBEDTLS_SSL_VERSION_TLS1_2
 
 SSL session serialization: Wrong config
 depends_on:MBEDTLS_SSL_PROTO_TLS1_2
-ssl_session_serialize_version_check:0:0:0:1
+ssl_session_serialize_version_check:0:0:0:1:0:MBEDTLS_SSL_VERSION_TLS1_2
+
+TLS 1.3: CLI: session serialization: Wrong major version
+depends_on:MBEDTLS_SSL_PROTO_TLS1_3:MBEDTLS_SSL_CLI_C
+ssl_session_serialize_version_check:1:0:0:0:MBEDTLS_SSL_IS_CLIENT:MBEDTLS_SSL_VERSION_TLS1_3
+
+TLS 1.3: CLI: session serialization: Wrong minor version
+depends_on:MBEDTLS_SSL_PROTO_TLS1_3:MBEDTLS_SSL_CLI_C
+ssl_session_serialize_version_check:0:1:0:0:MBEDTLS_SSL_IS_CLIENT:MBEDTLS_SSL_VERSION_TLS1_3
+
+TLS 1.3: CLI: session serialization: Wrong patch version
+depends_on:MBEDTLS_SSL_PROTO_TLS1_3:MBEDTLS_SSL_CLI_C
+ssl_session_serialize_version_check:0:0:1:0:MBEDTLS_SSL_IS_CLIENT:MBEDTLS_SSL_VERSION_TLS1_3
+
+TLS 1.3: CLI: session serialization: Wrong config
+depends_on:MBEDTLS_SSL_PROTO_TLS1_3:MBEDTLS_SSL_CLI_C
+ssl_session_serialize_version_check:0:0:0:1:MBEDTLS_SSL_IS_CLIENT:MBEDTLS_SSL_VERSION_TLS1_3
+
+TLS 1.3: SRV: session serialization: Wrong major version
+depends_on:MBEDTLS_SSL_PROTO_TLS1_3:MBEDTLS_SSL_SRV_C
+ssl_session_serialize_version_check:1:0:0:0:MBEDTLS_SSL_IS_SERVER:MBEDTLS_SSL_VERSION_TLS1_3
+
+TLS 1.3: SRV: session serialization: Wrong minor version
+depends_on:MBEDTLS_SSL_PROTO_TLS1_3:MBEDTLS_SSL_SRV_C
+ssl_session_serialize_version_check:0:1:0:0:MBEDTLS_SSL_IS_SERVER:MBEDTLS_SSL_VERSION_TLS1_3
+
+TLS 1.3: SRV: session serialization: Wrong patch version
+depends_on:MBEDTLS_SSL_PROTO_TLS1_3:MBEDTLS_SSL_SRV_C
+ssl_session_serialize_version_check:0:0:1:0:MBEDTLS_SSL_IS_SERVER:MBEDTLS_SSL_VERSION_TLS1_3
+
+TLS 1.3: SRV: session serialization: Wrong config
+depends_on:MBEDTLS_SSL_PROTO_TLS1_3:MBEDTLS_SSL_SRV_C
+ssl_session_serialize_version_check:0:0:0:1:MBEDTLS_SSL_IS_SERVER:MBEDTLS_SSL_VERSION_TLS1_3
 
 Record crypt, AES-128-CBC, 1.2, SHA-384
 depends_on:MBEDTLS_CIPHER_MODE_CBC:MBEDTLS_AES_C:MBEDTLS_SSL_PROTO_TLS1_2:MBEDTLS_SHA384_C
@@ -3169,99 +3201,163 @@
 
 Session serialization, save-load: no ticket, no cert
 depends_on:MBEDTLS_SSL_PROTO_TLS1_2
-ssl_serialize_session_save_load:0:""
+ssl_serialize_session_save_load:0:"":0:MBEDTLS_SSL_VERSION_TLS1_2
 
 Session serialization, save-load: small ticket, no cert
 depends_on:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_CLI_C:MBEDTLS_SSL_PROTO_TLS1_2
-ssl_serialize_session_save_load:42:""
+ssl_serialize_session_save_load:42:"":0:MBEDTLS_SSL_VERSION_TLS1_2
 
 Session serialization, save-load: large ticket, no cert
 depends_on:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_CLI_C:MBEDTLS_SSL_PROTO_TLS1_2
-ssl_serialize_session_save_load:1023:""
+ssl_serialize_session_save_load:1023:"":0:MBEDTLS_SSL_VERSION_TLS1_2
 
 Session serialization, save-load: no ticket, cert
 depends_on:MBEDTLS_X509_USE_C:MBEDTLS_PEM_PARSE_C:MBEDTLS_ECDSA_C:MBEDTLS_ECP_DP_SECP256R1_ENABLED:MBEDTLS_SHA256_C:MBEDTLS_FS_IO:MBEDTLS_SSL_PROTO_TLS1_2
-ssl_serialize_session_save_load:0:"data_files/server5.crt"
+ssl_serialize_session_save_load:0:"data_files/server5.crt":0:MBEDTLS_SSL_VERSION_TLS1_2
 
 Session serialization, save-load: small ticket, cert
 depends_on:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_CLI_C:MBEDTLS_X509_USE_C:MBEDTLS_PEM_PARSE_C:MBEDTLS_ECDSA_C:MBEDTLS_ECP_DP_SECP256R1_ENABLED:MBEDTLS_SHA256_C:MBEDTLS_FS_IO:MBEDTLS_SSL_PROTO_TLS1_2
-ssl_serialize_session_save_load:42:"data_files/server5.crt"
+ssl_serialize_session_save_load:42:"data_files/server5.crt":0:MBEDTLS_SSL_VERSION_TLS1_2
 
 Session serialization, save-load: large ticket, cert
 depends_on:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_CLI_C:MBEDTLS_X509_USE_C:MBEDTLS_PEM_PARSE_C:MBEDTLS_ECDSA_C:MBEDTLS_ECP_DP_SECP256R1_ENABLED:MBEDTLS_SHA256_C:MBEDTLS_FS_IO:MBEDTLS_SSL_PROTO_TLS1_2
-ssl_serialize_session_save_load:1023:"data_files/server5.crt"
+ssl_serialize_session_save_load:1023:"data_files/server5.crt":0:MBEDTLS_SSL_VERSION_TLS1_2
+
+TLS 1.3: CLI: Session serialization, save-load: no ticket
+depends_on:MBEDTLS_SSL_PROTO_TLS1_3
+ssl_serialize_session_save_load:0:"":MBEDTLS_SSL_IS_CLIENT:MBEDTLS_SSL_VERSION_TLS1_3
+
+TLS 1.3: CLI: Session serialization, save-load: small ticket
+depends_on:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_CLI_C:MBEDTLS_SSL_PROTO_TLS1_3
+ssl_serialize_session_save_load:42:"":MBEDTLS_SSL_IS_CLIENT:MBEDTLS_SSL_VERSION_TLS1_3
+
+TLS 1.3: CLI: Session serialization, save-load: large ticket
+depends_on:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_CLI_C:MBEDTLS_SSL_PROTO_TLS1_3
+ssl_serialize_session_save_load:1023:"":MBEDTLS_SSL_IS_CLIENT:MBEDTLS_SSL_VERSION_TLS1_3
+
+TLS 1.3: SRV: Session serialization, save-load: large ticket
+depends_on:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_SRV_C:MBEDTLS_SSL_PROTO_TLS1_3
+ssl_serialize_session_save_load:1023:"":MBEDTLS_SSL_IS_SERVER:MBEDTLS_SSL_VERSION_TLS1_3
 
 Session serialization, load-save: no ticket, no cert
 depends_on:MBEDTLS_SSL_PROTO_TLS1_2
-ssl_serialize_session_load_save:0:""
+ssl_serialize_session_load_save:0:"":0:MBEDTLS_SSL_VERSION_TLS1_2
 
 Session serialization, load-save: small ticket, no cert
 depends_on:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_CLI_C:MBEDTLS_SSL_PROTO_TLS1_2
-ssl_serialize_session_load_save:42:""
+ssl_serialize_session_load_save:42:"":0:MBEDTLS_SSL_VERSION_TLS1_2
 
 Session serialization, load-save: large ticket, no cert
 depends_on:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_CLI_C:MBEDTLS_SSL_PROTO_TLS1_2
-ssl_serialize_session_load_save:1023:""
+ssl_serialize_session_load_save:1023:"":0:MBEDTLS_SSL_VERSION_TLS1_2
 
 Session serialization, load-save: no ticket, cert
 depends_on:MBEDTLS_X509_USE_C:MBEDTLS_PEM_PARSE_C:MBEDTLS_ECDSA_C:MBEDTLS_ECP_DP_SECP256R1_ENABLED:MBEDTLS_SHA256_C:MBEDTLS_FS_IO:MBEDTLS_SSL_PROTO_TLS1_2
-ssl_serialize_session_load_save:0:"data_files/server5.crt"
+ssl_serialize_session_load_save:0:"data_files/server5.crt":0:MBEDTLS_SSL_VERSION_TLS1_2
 
 Session serialization, load-save: small ticket, cert
 depends_on:MBEDTLS_SSL_PROTO_TLS1_2:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_CLI_C:MBEDTLS_X509_USE_C:MBEDTLS_PEM_PARSE_C:MBEDTLS_ECDSA_C:MBEDTLS_ECP_DP_SECP256R1_ENABLED:MBEDTLS_SHA256_C:MBEDTLS_FS_IO
-ssl_serialize_session_load_save:42:"data_files/server5.crt"
+ssl_serialize_session_load_save:42:"data_files/server5.crt":0:MBEDTLS_SSL_VERSION_TLS1_2
 
 Session serialization, load-save: large ticket, cert
 depends_on:MBEDTLS_SSL_PROTO_TLS1_2:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_CLI_C:MBEDTLS_X509_USE_C:MBEDTLS_PEM_PARSE_C:MBEDTLS_ECDSA_C:MBEDTLS_ECP_DP_SECP256R1_ENABLED:MBEDTLS_SHA256_C:MBEDTLS_FS_IO
-ssl_serialize_session_load_save:1023:"data_files/server5.crt"
+ssl_serialize_session_load_save:1023:"data_files/server5.crt":0:MBEDTLS_SSL_VERSION_TLS1_2
+
+TLS 1.3: CLI: Session serialization, load-save: no ticket
+depends_on:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_CLI_C:MBEDTLS_SSL_PROTO_TLS1_3
+ssl_serialize_session_load_save:0:"":MBEDTLS_SSL_IS_CLIENT:MBEDTLS_SSL_VERSION_TLS1_3
+
+TLS 1.3: CLI: Session serialization, load-save: small ticket
+depends_on:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_CLI_C:MBEDTLS_SSL_PROTO_TLS1_3
+ssl_serialize_session_load_save:42:"":MBEDTLS_SSL_IS_CLIENT:MBEDTLS_SSL_VERSION_TLS1_3
+
+TLS 1.3: CLI: Session serialization, load-save: large ticket
+depends_on:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_CLI_C:MBEDTLS_SSL_PROTO_TLS1_3
+ssl_serialize_session_load_save:1023:"":MBEDTLS_SSL_IS_CLIENT:MBEDTLS_SSL_VERSION_TLS1_3
+
+TLS 1.3: SRV: Session serialization, load-save
+depends_on:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_SRV_C:MBEDTLS_SSL_PROTO_TLS1_3
+ssl_serialize_session_load_save:0:"":MBEDTLS_SSL_IS_SERVER:MBEDTLS_SSL_VERSION_TLS1_3
 
 Session serialization, save buffer size: no ticket, no cert
 depends_on:MBEDTLS_SSL_PROTO_TLS1_2
-ssl_serialize_session_save_buf_size:0:""
+ssl_serialize_session_save_buf_size:0:"":0:MBEDTLS_SSL_VERSION_TLS1_2
 
 Session serialization, save buffer size: small ticket, no cert
 depends_on:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_CLI_C:MBEDTLS_SSL_PROTO_TLS1_2
-ssl_serialize_session_save_buf_size:42:""
+ssl_serialize_session_save_buf_size:42:"":0:MBEDTLS_SSL_VERSION_TLS1_2
 
 Session serialization, save buffer size: large ticket, no cert
 depends_on:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_CLI_C:MBEDTLS_SSL_PROTO_TLS1_2
-ssl_serialize_session_save_buf_size:1023:""
+ssl_serialize_session_save_buf_size:1023:"":0:MBEDTLS_SSL_VERSION_TLS1_2
 
 Session serialization, save buffer size: no ticket, cert
 depends_on:MBEDTLS_X509_USE_C:MBEDTLS_PEM_PARSE_C:MBEDTLS_ECDSA_C:MBEDTLS_ECP_DP_SECP256R1_ENABLED:MBEDTLS_SHA256_C:MBEDTLS_FS_IO:MBEDTLS_SSL_PROTO_TLS1_2
-ssl_serialize_session_save_buf_size:0:"data_files/server5.crt"
+ssl_serialize_session_save_buf_size:0:"data_files/server5.crt":0:MBEDTLS_SSL_VERSION_TLS1_2
 
 Session serialization, save buffer size: small ticket, cert
 depends_on:MBEDTLS_SSL_PROTO_TLS1_2:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_CLI_C:MBEDTLS_X509_USE_C:MBEDTLS_PEM_PARSE_C:MBEDTLS_ECDSA_C:MBEDTLS_ECP_DP_SECP256R1_ENABLED:MBEDTLS_SHA256_C:MBEDTLS_FS_IO
-ssl_serialize_session_save_buf_size:42:"data_files/server5.crt"
+ssl_serialize_session_save_buf_size:42:"data_files/server5.crt":0:MBEDTLS_SSL_VERSION_TLS1_2
 
 Session serialization, save buffer size: large ticket, cert
 depends_on:MBEDTLS_SSL_PROTO_TLS1_2:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_CLI_C:MBEDTLS_X509_USE_C:MBEDTLS_PEM_PARSE_C:MBEDTLS_ECDSA_C:MBEDTLS_ECP_DP_SECP256R1_ENABLED:MBEDTLS_SHA256_C:MBEDTLS_FS_IO
-ssl_serialize_session_save_buf_size:1023:"data_files/server5.crt"
+ssl_serialize_session_save_buf_size:1023:"data_files/server5.crt":0:MBEDTLS_SSL_VERSION_TLS1_2
+
+TLS 1.3: CLI: Session serialization, save buffer size: no ticket
+depends_on:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_CLI_C:MBEDTLS_SSL_PROTO_TLS1_3
+ssl_serialize_session_save_buf_size:0:"":MBEDTLS_SSL_IS_CLIENT:MBEDTLS_SSL_VERSION_TLS1_3
+
+TLS 1.3: CLI: Session serialization, save buffer size: small ticket
+depends_on:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_CLI_C:MBEDTLS_SSL_PROTO_TLS1_3
+ssl_serialize_session_save_buf_size:42:"":MBEDTLS_SSL_IS_CLIENT:MBEDTLS_SSL_VERSION_TLS1_3
+
+TLS 1.3: CLI: Session serialization, save buffer size: large ticket
+depends_on:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_CLI_C:MBEDTLS_SSL_PROTO_TLS1_3
+ssl_serialize_session_save_buf_size:1023:"":MBEDTLS_SSL_IS_CLIENT:MBEDTLS_SSL_VERSION_TLS1_3
+
+TLS 1.3: SRV: Session serialization, save buffer size
+depends_on:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_SRV_C:MBEDTLS_SSL_PROTO_TLS1_3
+ssl_serialize_session_save_buf_size:0:"":MBEDTLS_SSL_IS_SERVER:MBEDTLS_SSL_VERSION_TLS1_3
 
 Session serialization, load buffer size: no ticket, no cert
 depends_on:MBEDTLS_SSL_PROTO_TLS1_2
-ssl_serialize_session_load_buf_size:0:""
+ssl_serialize_session_load_buf_size:0:"":0:MBEDTLS_SSL_VERSION_TLS1_2
 
 Session serialization, load buffer size: small ticket, no cert
 depends_on:MBEDTLS_SSL_PROTO_TLS1_2:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_CLI_C
-ssl_serialize_session_load_buf_size:42:""
+ssl_serialize_session_load_buf_size:42:"":0:MBEDTLS_SSL_VERSION_TLS1_2
 
 Session serialization, load buffer size: large ticket, no cert
 depends_on:MBEDTLS_SSL_PROTO_TLS1_2:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_CLI_C
-ssl_serialize_session_load_buf_size:1023:""
+ssl_serialize_session_load_buf_size:1023:"":0:MBEDTLS_SSL_VERSION_TLS1_2
 
 Session serialization, load buffer size: no ticket, cert
 depends_on:MBEDTLS_SSL_PROTO_TLS1_2:MBEDTLS_X509_USE_C:MBEDTLS_PEM_PARSE_C:MBEDTLS_ECDSA_C:MBEDTLS_ECP_DP_SECP256R1_ENABLED:MBEDTLS_SHA256_C:MBEDTLS_FS_IO
-ssl_serialize_session_load_buf_size:0:"data_files/server5.crt"
+ssl_serialize_session_load_buf_size:0:"data_files/server5.crt":0:MBEDTLS_SSL_VERSION_TLS1_2
 
 Session serialization, load buffer size: small ticket, cert
 depends_on:MBEDTLS_SSL_PROTO_TLS1_2:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_CLI_C:MBEDTLS_X509_USE_C:MBEDTLS_PEM_PARSE_C:MBEDTLS_ECDSA_C:MBEDTLS_ECP_DP_SECP256R1_ENABLED:MBEDTLS_SHA256_C:MBEDTLS_FS_IO
-ssl_serialize_session_load_buf_size:42:"data_files/server5.crt"
+ssl_serialize_session_load_buf_size:42:"data_files/server5.crt":0:MBEDTLS_SSL_VERSION_TLS1_2
 
 Session serialization, load buffer size: large ticket, cert
 depends_on:MBEDTLS_SSL_PROTO_TLS1_2:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_CLI_C:MBEDTLS_X509_USE_C:MBEDTLS_PEM_PARSE_C:MBEDTLS_ECDSA_C:MBEDTLS_ECP_DP_SECP256R1_ENABLED:MBEDTLS_SHA256_C:MBEDTLS_FS_IO
-ssl_serialize_session_load_buf_size:1023:"data_files/server5.crt"
+ssl_serialize_session_load_buf_size:1023:"data_files/server5.crt":0:MBEDTLS_SSL_VERSION_TLS1_2
+
+TLS 1.3: CLI: Session serialization, load buffer size: no ticket
+depends_on:MBEDTLS_SSL_PROTO_TLS1_3:MBEDTLS_SSL_CLI_C
+ssl_serialize_session_load_buf_size:0:"":MBEDTLS_SSL_IS_CLIENT:MBEDTLS_SSL_VERSION_TLS1_3
+
+TLS 1.3: CLI: Session serialization, load buffer size: small ticket
+depends_on:MBEDTLS_SSL_PROTO_TLS1_3:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_CLI_C
+ssl_serialize_session_load_buf_size:42:"":MBEDTLS_SSL_IS_CLIENT:MBEDTLS_SSL_VERSION_TLS1_3
+
+TLS 1.3: CLI: Session serialization, load buffer size: large ticket
+depends_on:MBEDTLS_SSL_PROTO_TLS1_3:MBEDTLS_SSL_SESSION_TICKETS:MBEDTLS_SSL_CLI_C
+ssl_serialize_session_load_buf_size:1023:"":MBEDTLS_SSL_IS_CLIENT:MBEDTLS_SSL_VERSION_TLS1_3
+
+TLS 1.3: SRV: Session serialization, load buffer size
+depends_on:MBEDTLS_SSL_PROTO_TLS1_3:MBEDTLS_SSL_SRV_C
+ssl_serialize_session_load_buf_size:0:"":MBEDTLS_SSL_IS_SERVER:MBEDTLS_SSL_VERSION_TLS1_3
 
 Constant-flow HMAC: MD5
 depends_on:MBEDTLS_MD5_C
diff --git a/tests/suites/test_suite_ssl.function b/tests/suites/test_suite_ssl.function
index 9a031b6..1ff8aab 100644
--- a/tests/suites/test_suite_ssl.function
+++ b/tests/suites/test_suite_ssl.function
@@ -1724,7 +1724,7 @@
  * Populate a session structure for serialization tests.
  * Choose dummy values, mostly non-0 to distinguish from the init default.
  */
-static int ssl_populate_session_tls12( mbedtls_ssl_session *session,
+static int ssl_tls12_populate_session( mbedtls_ssl_session *session,
                                        int ticket_len,
                                        const char *crt_file )
 {
@@ -1805,6 +1805,52 @@
     return( 0 );
 }
 
+#if defined(MBEDTLS_SSL_PROTO_TLS1_3)
+static int ssl_tls13_populate_session( mbedtls_ssl_session *session,
+                                       int ticket_len,
+                                       int endpoint_type )
+{
+    ((void) ticket_len);
+    session->tls_version = MBEDTLS_SSL_VERSION_TLS1_3;
+    session->endpoint = endpoint_type == MBEDTLS_SSL_IS_CLIENT ?
+                            MBEDTLS_SSL_IS_CLIENT : MBEDTLS_SSL_IS_SERVER;
+    session->ciphersuite = 0xabcd;
+    session->ticket_age_add = 0x87654321;
+    session->ticket_flags = 0x7;
+
+    session->resumption_key_len = 32;
+    memset( session->resumption_key, 0x99, sizeof( session->resumption_key ) );
+
+#if defined(MBEDTLS_HAVE_TIME)
+    if( session->endpoint == MBEDTLS_SSL_IS_SERVER )
+    {
+        session->start = mbedtls_time( NULL ) - 42;
+    }
+#endif
+
+#if defined(MBEDTLS_SSL_CLI_C)
+    if( session->endpoint == MBEDTLS_SSL_IS_CLIENT )
+    {
+#if defined(MBEDTLS_HAVE_TIME)
+        session->ticket_received = mbedtls_time( NULL ) - 40;
+#endif
+        session->ticket_lifetime = 0xfedcba98;
+
+        session->ticket_len = ticket_len;
+        if( ticket_len != 0 )
+        {
+            session->ticket = mbedtls_calloc( 1, ticket_len );
+            if( session->ticket == NULL )
+                return( -1 );
+            memset( session->ticket, 33, ticket_len );
+        }
+    }
+#endif /* MBEDTLS_SSL_CLI_C */
+
+    return( 0 );
+}
+#endif /* MBEDTLS_SSL_PROTO_TLS1_3 */
+
 /*
  * Perform data exchanging between \p ssl_1 and \p ssl_2 and check if the
  * message was sent in the correct number of fragments.
@@ -4624,7 +4670,8 @@
 /* END_CASE */
 
 /* BEGIN_CASE */
-void ssl_serialize_session_save_load( int ticket_len, char *crt_file )
+void ssl_serialize_session_save_load( int ticket_len, char *crt_file,
+                                      int endpoint_type, int tls_version )
 {
     mbedtls_ssl_session original, restored;
     unsigned char *buf = NULL;
@@ -4638,7 +4685,20 @@
     mbedtls_ssl_session_init( &restored );
 
     /* Prepare a dummy session to work on */
-    TEST_ASSERT( ssl_populate_session_tls12( &original, ticket_len, crt_file ) == 0 );
+    ((void) endpoint_type);
+    ((void) tls_version);
+#if defined(MBEDTLS_SSL_PROTO_TLS1_3)
+    if( tls_version == MBEDTLS_SSL_VERSION_TLS1_3 )
+    {
+        TEST_ASSERT( ssl_tls13_populate_session(
+                         &original, 0, endpoint_type ) == 0 );
+    }
+    else
+#endif
+    {
+        TEST_ASSERT( ssl_tls12_populate_session(
+                         &original, ticket_len, crt_file ) == 0 );
+    }
 
     /* Serialize it */
     TEST_ASSERT( mbedtls_ssl_session_save( &original, NULL, 0, &len )
@@ -4658,61 +4718,109 @@
 #endif
     TEST_ASSERT( original.tls_version == restored.tls_version );
     TEST_ASSERT( original.ciphersuite == restored.ciphersuite );
-    TEST_ASSERT( original.compression == restored.compression );
-    TEST_ASSERT( original.id_len == restored.id_len );
-    TEST_ASSERT( memcmp( original.id,
-                         restored.id, sizeof( original.id ) ) == 0 );
-    TEST_ASSERT( memcmp( original.master,
-                         restored.master, sizeof( original.master ) ) == 0 );
+#if defined(MBEDTLS_SSL_PROTO_TLS1_2)
+    if( tls_version == MBEDTLS_SSL_VERSION_TLS1_2 )
+    {
+        TEST_ASSERT( original.compression == restored.compression );
+        TEST_ASSERT( original.id_len == restored.id_len );
+        TEST_ASSERT( memcmp( original.id,
+                            restored.id, sizeof( original.id ) ) == 0 );
+        TEST_ASSERT( memcmp( original.master,
+                            restored.master, sizeof( original.master ) ) == 0 );
 
 #if defined(MBEDTLS_X509_CRT_PARSE_C)
 #if defined(MBEDTLS_SSL_KEEP_PEER_CERTIFICATE)
-    TEST_ASSERT( ( original.peer_cert == NULL ) ==
-                 ( restored.peer_cert == NULL ) );
-    if( original.peer_cert != NULL )
-    {
-        TEST_ASSERT( original.peer_cert->raw.len ==
-                     restored.peer_cert->raw.len );
-        TEST_ASSERT( memcmp( original.peer_cert->raw.p,
-                             restored.peer_cert->raw.p,
-                             original.peer_cert->raw.len ) == 0 );
-    }
+        TEST_ASSERT( ( original.peer_cert == NULL ) ==
+                     ( restored.peer_cert == NULL ) );
+        if( original.peer_cert != NULL )
+        {
+            TEST_ASSERT( original.peer_cert->raw.len ==
+                        restored.peer_cert->raw.len );
+            TEST_ASSERT( memcmp( original.peer_cert->raw.p,
+                                restored.peer_cert->raw.p,
+                                original.peer_cert->raw.len ) == 0 );
+        }
 #else /* MBEDTLS_SSL_KEEP_PEER_CERTIFICATE */
-    TEST_ASSERT( original.peer_cert_digest_type ==
-                 restored.peer_cert_digest_type );
-    TEST_ASSERT( original.peer_cert_digest_len ==
-                 restored.peer_cert_digest_len );
-    TEST_ASSERT( ( original.peer_cert_digest == NULL ) ==
-                 ( restored.peer_cert_digest == NULL ) );
-    if( original.peer_cert_digest != NULL )
-    {
-        TEST_ASSERT( memcmp( original.peer_cert_digest,
-                             restored.peer_cert_digest,
-                             original.peer_cert_digest_len ) == 0 );
-    }
+        TEST_ASSERT( original.peer_cert_digest_type ==
+                    restored.peer_cert_digest_type );
+        TEST_ASSERT( original.peer_cert_digest_len ==
+                    restored.peer_cert_digest_len );
+        TEST_ASSERT( ( original.peer_cert_digest == NULL ) ==
+                    ( restored.peer_cert_digest == NULL ) );
+        if( original.peer_cert_digest != NULL )
+        {
+            TEST_ASSERT( memcmp( original.peer_cert_digest,
+                                restored.peer_cert_digest,
+                                original.peer_cert_digest_len ) == 0 );
+        }
 #endif /* MBEDTLS_SSL_KEEP_PEER_CERTIFICATE */
 #endif /* MBEDTLS_X509_CRT_PARSE_C */
-    TEST_ASSERT( original.verify_result == restored.verify_result );
-
-#if defined(MBEDTLS_SSL_SESSION_TICKETS) && defined(MBEDTLS_SSL_CLI_C)
-    TEST_ASSERT( original.ticket_len == restored.ticket_len );
-    if( original.ticket_len != 0 )
-    {
-        TEST_ASSERT( original.ticket != NULL );
-        TEST_ASSERT( restored.ticket != NULL );
-        TEST_ASSERT( memcmp( original.ticket,
-                             restored.ticket, original.ticket_len ) == 0 );
-    }
-    TEST_ASSERT( original.ticket_lifetime == restored.ticket_lifetime );
-#endif
+        TEST_ASSERT( original.verify_result == restored.verify_result );
 
 #if defined(MBEDTLS_SSL_MAX_FRAGMENT_LENGTH)
-    TEST_ASSERT( original.mfl_code == restored.mfl_code );
+        TEST_ASSERT( original.mfl_code == restored.mfl_code );
 #endif
 
 #if defined(MBEDTLS_SSL_ENCRYPT_THEN_MAC)
-    TEST_ASSERT( original.encrypt_then_mac == restored.encrypt_then_mac );
+        TEST_ASSERT( original.encrypt_then_mac == restored.encrypt_then_mac );
 #endif
+#if defined(MBEDTLS_SSL_SESSION_TICKETS) && defined(MBEDTLS_SSL_CLI_C)
+        TEST_ASSERT( original.ticket_len == restored.ticket_len );
+        if( original.ticket_len != 0 )
+        {
+            TEST_ASSERT( original.ticket != NULL );
+            TEST_ASSERT( restored.ticket != NULL );
+            TEST_ASSERT( memcmp( original.ticket,
+                                 restored.ticket, original.ticket_len ) == 0 );
+        }
+        TEST_ASSERT( original.ticket_lifetime == restored.ticket_lifetime );
+#endif
+    }
+#endif /* MBEDTLS_SSL_PROTO_TLS1_2 */
+
+#if defined(MBEDTLS_SSL_PROTO_TLS1_3)
+    if( tls_version == MBEDTLS_SSL_VERSION_TLS1_3 )
+    {
+        TEST_ASSERT( original.endpoint == restored.endpoint );
+        TEST_ASSERT( original.ciphersuite == restored.ciphersuite );
+        TEST_ASSERT( original.ticket_age_add == restored.ticket_age_add );
+        TEST_ASSERT( original.ticket_flags == restored.ticket_flags );
+        TEST_ASSERT( original.resumption_key_len == restored.resumption_key_len );
+        if( original.resumption_key_len != 0 )
+        {
+            TEST_ASSERT( original.resumption_key != NULL );
+            TEST_ASSERT( restored.resumption_key != NULL );
+            TEST_ASSERT( memcmp( original.resumption_key,
+                                 restored.resumption_key,
+                                 original.resumption_key_len ) == 0 );
+        }
+#if defined(MBEDTLS_HAVE_TIME) && defined(MBEDTLS_SSL_SRV_C)
+        if( endpoint_type == MBEDTLS_SSL_IS_CLIENT)
+        {
+            TEST_ASSERT( original.start == restored.start );
+        }
+#endif
+#if defined(MBEDTLS_SSL_SESSION_TICKETS) && defined(MBEDTLS_SSL_CLI_C)
+        if( endpoint_type == MBEDTLS_SSL_IS_CLIENT)
+        {
+#if defined(MBEDTLS_HAVE_TIME)
+            TEST_ASSERT( original.ticket_received == restored.ticket_received );
+#endif
+            TEST_ASSERT( original.ticket_lifetime == restored.ticket_lifetime );
+            TEST_ASSERT( original.ticket_len == restored.ticket_len );
+            if( original.ticket_len != 0 )
+            {
+                TEST_ASSERT( original.ticket != NULL );
+                TEST_ASSERT( restored.ticket != NULL );
+                TEST_ASSERT( memcmp( original.ticket,
+                                     restored.ticket,
+                                     original.ticket_len ) == 0 );
+            }
+
+        }
+#endif
+    }
+#endif /* MBEDTLS_SSL_PROTO_TLS1_3 */
 
 exit:
     mbedtls_ssl_session_free( &original );
@@ -4722,7 +4830,8 @@
 /* END_CASE */
 
 /* BEGIN_CASE */
-void ssl_serialize_session_load_save( int ticket_len, char *crt_file )
+void ssl_serialize_session_load_save( int ticket_len, char *crt_file,
+                                      int endpoint_type, int tls_version )
 {
     mbedtls_ssl_session session;
     unsigned char *buf1 = NULL, *buf2 = NULL;
@@ -4735,7 +4844,20 @@
     mbedtls_ssl_session_init( &session );
 
     /* Prepare a dummy session to work on */
-    TEST_ASSERT( ssl_populate_session_tls12( &session, ticket_len, crt_file ) == 0 );
+    ((void) endpoint_type);
+    ((void) tls_version);
+#if defined(MBEDTLS_SSL_PROTO_TLS1_3)
+    if(tls_version == MBEDTLS_SSL_VERSION_TLS1_3)
+    {
+        TEST_ASSERT( ssl_tls13_populate_session(
+                         &session, 0, endpoint_type ) == 0 );
+    }
+    else
+#endif
+    {
+        TEST_ASSERT( ssl_tls12_populate_session(
+                         &session, ticket_len, crt_file ) == 0 );
+    }
 
     /* Get desired buffer size for serializing */
     TEST_ASSERT( mbedtls_ssl_session_save( &session, NULL, 0, &len0 )
@@ -4772,7 +4894,8 @@
 /* END_CASE */
 
 /* BEGIN_CASE */
-void ssl_serialize_session_save_buf_size( int ticket_len, char *crt_file )
+void ssl_serialize_session_save_buf_size( int ticket_len, char *crt_file,
+                                          int endpoint_type, int tls_version )
 {
     mbedtls_ssl_session session;
     unsigned char *buf = NULL;
@@ -4785,7 +4908,20 @@
     mbedtls_ssl_session_init( &session );
 
     /* Prepare dummy session and get serialized size */
-    TEST_ASSERT( ssl_populate_session_tls12( &session, ticket_len, crt_file ) == 0 );
+    ((void) endpoint_type);
+    ((void) tls_version);
+#if defined(MBEDTLS_SSL_PROTO_TLS1_3)
+    if(tls_version == MBEDTLS_SSL_VERSION_TLS1_3)
+    {
+        TEST_ASSERT( ssl_tls13_populate_session(
+                         &session, 0, endpoint_type ) == 0 );
+    }
+    else
+#endif
+    {
+        TEST_ASSERT( ssl_tls12_populate_session(
+                         &session, ticket_len, crt_file ) == 0 );
+    }
     TEST_ASSERT( mbedtls_ssl_session_save( &session, NULL, 0, &good_len )
                  == MBEDTLS_ERR_SSL_BUFFER_TOO_SMALL );
 
@@ -4808,7 +4944,8 @@
 /* END_CASE */
 
 /* BEGIN_CASE */
-void ssl_serialize_session_load_buf_size( int ticket_len, char *crt_file )
+void ssl_serialize_session_load_buf_size( int ticket_len, char *crt_file,
+                                          int endpoint_type, int tls_version )
 {
     mbedtls_ssl_session session;
     unsigned char *good_buf = NULL, *bad_buf = NULL;
@@ -4821,7 +4958,20 @@
     mbedtls_ssl_session_init( &session );
 
     /* Prepare serialized session data */
-    TEST_ASSERT( ssl_populate_session_tls12( &session, ticket_len, crt_file ) == 0 );
+    ((void) endpoint_type);
+    ((void) tls_version);
+#if defined(MBEDTLS_SSL_PROTO_TLS1_3)
+    if(tls_version == MBEDTLS_SSL_VERSION_TLS1_3)
+    {
+        TEST_ASSERT( ssl_tls13_populate_session(
+                         &session, 0, endpoint_type ) == 0 );
+    }
+    else
+#endif
+    {
+        TEST_ASSERT( ssl_tls12_populate_session(
+                         &session, ticket_len, crt_file ) == 0 );
+    }
     TEST_ASSERT( mbedtls_ssl_session_save( &session, NULL, 0, &good_len )
                  == MBEDTLS_ERR_SSL_BUFFER_TOO_SMALL );
     TEST_ASSERT( ( good_buf = mbedtls_calloc( 1, good_len ) ) != NULL );
@@ -4853,7 +5003,9 @@
 void ssl_session_serialize_version_check( int corrupt_major,
                                           int corrupt_minor,
                                           int corrupt_patch,
-                                          int corrupt_config )
+                                          int corrupt_config,
+                                          int endpoint_type,
+                                          int tls_version )
 {
     unsigned char serialized_session[ 2048 ];
     size_t serialized_session_len;
@@ -4866,7 +5018,18 @@
                                       corrupt_config == 1 };
 
     mbedtls_ssl_session_init( &session );
-    TEST_ASSERT( ssl_populate_session_tls12( &session, 0, NULL ) == 0 );
+    ((void) endpoint_type);
+    ((void) tls_version);
+#if defined(MBEDTLS_SSL_PROTO_TLS1_3)
+    if(tls_version == MBEDTLS_SSL_VERSION_TLS1_3)
+    {
+        TEST_ASSERT( ssl_tls13_populate_session(
+                         &session, 0, endpoint_type ) == 0 );
+    }
+    else
+#endif
+        TEST_ASSERT( ssl_tls12_populate_session( &session, 0, NULL ) == 0 );
+
 
     /* Infer length of serialized session. */
     TEST_ASSERT( mbedtls_ssl_session_save( &session,