Respect SSL_OP_NO_TICKET in TLSv1.3
[openssl.git] / ssl / statem / extensions_srvr.c
index 7c756c03a0c95a73beadfdf859f9330ebfdb49b6..48be0444af9f2540285720ad1506db3fe362bdee 100644 (file)
@@ -1009,6 +1009,33 @@ int tls_parse_ctos_early_data(SSL *s, PACKET *pkt, unsigned int context,
     return 1;
 }
 
+static SSL_TICKET_STATUS tls_get_stateful_ticket(SSL *s, PACKET *tick,
+                                                 SSL_SESSION **sess)
+{
+    SSL_SESSION *tmpsess = NULL;
+
+    switch (PACKET_remaining(tick)) {
+        case 0:
+            return SSL_TICKET_EMPTY;
+
+        case SSL_MAX_SSL_SESSION_ID_LENGTH:
+            break;
+
+        default:
+            return SSL_TICKET_NO_DECRYPT;
+    }
+
+    tmpsess = lookup_sess_in_cache(s, PACKET_data(tick),
+                                   SSL_MAX_SSL_SESSION_ID_LENGTH);
+
+    if (tmpsess == NULL)
+        return SSL_TICKET_NO_DECRYPT;
+
+    s->ext.ticket_expected = 1;
+    *sess = tmpsess;
+    return SSL_TICKET_SUCCESS;
+}
+
 int tls_parse_ctos_psk(SSL *s, PACKET *pkt, unsigned int context, X509 *x,
                        size_t chainidx)
 {
@@ -1132,9 +1159,12 @@ int tls_parse_ctos_psk(SSL *s, PACKET *pkt, unsigned int context, X509 *x,
             uint32_t ticket_age = 0, now, agesec, agems;
             int ret;
 
-            ret = tls_decrypt_ticket(s, PACKET_data(&identity),
-                                     PACKET_remaining(&identity), NULL, 0,
-                                     &sess);
+            if ((s->options & SSL_OP_NO_TICKET) != 0)
+                ret = tls_get_stateful_ticket(s, &identity, &sess);
+            else
+                ret = tls_decrypt_ticket(s, PACKET_data(&identity),
+                                         PACKET_remaining(&identity), NULL, 0,
+                                         &sess);
 
             if (ret == SSL_TICKET_EMPTY) {
                 SSLfatal(s, SSL_AD_DECODE_ERROR, SSL_F_TLS_PARSE_CTOS_PSK,