1 /*
2  * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License").
5  * You may not use this file except in compliance with the License.
6  * A copy of the License is located at
7  *
8  *  http://aws.amazon.com/apache2.0
9  *
10  * or in the "license" file accompanying this file. This file is distributed
11  * on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either
12  * express or implied. See the License for the specific language governing
13  * permissions and limitations under the License.
14  */
15 #include <math.h>
16 #include <sys/param.h>
17 
18 #include <s2n.h>
19 
20 #include "error/s2n_errno.h"
21 #include "stuffer/s2n_stuffer.h"
22 #include "utils/s2n_safety.h"
23 #include "utils/s2n_blob.h"
24 #include "utils/s2n_random.h"
25 #include "utils/s2n_set.h"
26 
27 #include "tls/s2n_cipher_suites.h"
28 #include "tls/s2n_connection.h"
29 #include "tls/s2n_resume.h"
30 #include "tls/s2n_crypto.h"
31 #include "tls/s2n_tls.h"
32 
s2n_allowed_to_cache_connection(struct s2n_connection * conn)33 int s2n_allowed_to_cache_connection(struct s2n_connection *conn)
34 {
35     /* We're unable to cache connections with a Client Cert since we currently don't serialize the Client Cert,
36      * which means that callers won't have access to the Client's Cert if the connection is resumed. */
37     if (s2n_connection_is_client_auth_enabled(conn)) {
38         return 0;
39     }
40 
41     struct s2n_config *config = conn->config;
42 
43     POSIX_ENSURE_REF(config);
44     return config->use_session_cache;
45 }
46 
s2n_tls12_serialize_resumption_state(struct s2n_connection * conn,struct s2n_stuffer * to)47 static int s2n_tls12_serialize_resumption_state(struct s2n_connection *conn, struct s2n_stuffer *to)
48 {
49     POSIX_ENSURE_REF(conn);
50     POSIX_ENSURE_REF(to);
51 
52     uint64_t now;
53 
54     S2N_ERROR_IF(s2n_stuffer_space_remaining(to) < S2N_TLS12_STATE_SIZE_IN_BYTES, S2N_ERR_STUFFER_IS_FULL);
55 
56     /* Get the time */
57     POSIX_GUARD(conn->config->wall_clock(conn->config->sys_clock_ctx, &now));
58 
59     /* Write the entry */
60     POSIX_GUARD(s2n_stuffer_write_uint8(to, S2N_TLS12_SERIALIZED_FORMAT_VERSION));
61     POSIX_GUARD(s2n_stuffer_write_uint8(to, conn->actual_protocol_version));
62     POSIX_GUARD(s2n_stuffer_write_bytes(to, conn->secure.cipher_suite->iana_value, S2N_TLS_CIPHER_SUITE_LEN));
63     POSIX_GUARD(s2n_stuffer_write_uint64(to, now));
64     POSIX_GUARD(s2n_stuffer_write_bytes(to, conn->secrets.master_secret, S2N_TLS_SECRET_LEN));
65     POSIX_GUARD(s2n_stuffer_write_uint8(to, conn->ems_negotiated));
66 
67     return S2N_SUCCESS;
68 }
69 
s2n_tls13_serialize_keying_material_expiration(struct s2n_connection * conn,uint64_t now,struct s2n_stuffer * out)70 static S2N_RESULT s2n_tls13_serialize_keying_material_expiration(struct s2n_connection *conn,
71         uint64_t now, struct s2n_stuffer *out)
72 {
73     RESULT_ENSURE_REF(conn);
74     RESULT_ENSURE_REF(out);
75 
76     if (conn->mode != S2N_SERVER) {
77         return S2N_RESULT_OK;
78     }
79 
80     uint64_t expiration_timestamp = now + (conn->server_keying_material_lifetime * (uint64_t) ONE_SEC_IN_NANOS);
81 
82     struct s2n_psk *chosen_psk = conn->psk_params.chosen_psk;
83     if (chosen_psk && chosen_psk->type == S2N_PSK_TYPE_RESUMPTION) {
84         expiration_timestamp = MIN(chosen_psk->keying_material_expiration, expiration_timestamp);
85     }
86 
87     RESULT_GUARD_POSIX(s2n_stuffer_write_uint64(out, expiration_timestamp));
88     return S2N_RESULT_OK;
89 }
90 
s2n_tls13_serialize_resumption_state(struct s2n_connection * conn,struct s2n_stuffer * out)91 static S2N_RESULT s2n_tls13_serialize_resumption_state(struct s2n_connection *conn, struct s2n_stuffer *out)
92 {
93     RESULT_ENSURE_REF(conn);
94     RESULT_ENSURE_REF(out);
95 
96     uint64_t current_time = 0;
97     struct s2n_ticket_fields *ticket_fields = &conn->tls13_ticket_fields;
98 
99     /* Get the time */
100     RESULT_GUARD_POSIX(conn->config->wall_clock(conn->config->sys_clock_ctx, &current_time));
101 
102     RESULT_GUARD_POSIX(s2n_stuffer_write_uint8(out, S2N_TLS13_SERIALIZED_FORMAT_VERSION));
103     RESULT_GUARD_POSIX(s2n_stuffer_write_uint8(out, conn->actual_protocol_version));
104     RESULT_GUARD_POSIX(s2n_stuffer_write_bytes(out, conn->secure.cipher_suite->iana_value, S2N_TLS_CIPHER_SUITE_LEN));
105     RESULT_GUARD_POSIX(s2n_stuffer_write_uint64(out, current_time));
106     RESULT_GUARD_POSIX(s2n_stuffer_write_uint32(out, ticket_fields->ticket_age_add));
107     RESULT_ENSURE_LTE(ticket_fields->session_secret.size, UINT8_MAX);
108     RESULT_GUARD_POSIX(s2n_stuffer_write_uint8(out, ticket_fields->session_secret.size));
109     RESULT_GUARD_POSIX(s2n_stuffer_write_bytes(out, ticket_fields->session_secret.data, ticket_fields->session_secret.size));
110     RESULT_GUARD(s2n_tls13_serialize_keying_material_expiration(conn, current_time, out));
111 
112     uint32_t server_max_early_data = 0;
113     RESULT_GUARD(s2n_early_data_get_server_max_size(conn, &server_max_early_data));
114     RESULT_GUARD_POSIX(s2n_stuffer_write_uint32(out, server_max_early_data));
115     if (server_max_early_data > 0) {
116         uint8_t application_protocol_len = strlen(conn->application_protocol);
117         RESULT_GUARD_POSIX(s2n_stuffer_write_uint8(out, application_protocol_len));
118         RESULT_GUARD_POSIX(s2n_stuffer_write_bytes(out, (uint8_t *) conn->application_protocol, application_protocol_len));
119         RESULT_GUARD_POSIX(s2n_stuffer_write_uint16(out, conn->server_early_data_context.size));
120         RESULT_GUARD_POSIX(s2n_stuffer_write(out, &conn->server_early_data_context));
121     }
122 
123     return S2N_RESULT_OK;
124 }
125 
s2n_serialize_resumption_state(struct s2n_connection * conn,struct s2n_stuffer * out)126 static S2N_RESULT s2n_serialize_resumption_state(struct s2n_connection *conn, struct s2n_stuffer *out)
127 {
128     if(conn->actual_protocol_version < S2N_TLS13) {
129         RESULT_GUARD_POSIX(s2n_tls12_serialize_resumption_state(conn, out));
130     } else {
131         RESULT_GUARD(s2n_tls13_serialize_resumption_state(conn, out));
132     }
133     return S2N_RESULT_OK;
134 }
135 
s2n_tls12_deserialize_resumption_state(struct s2n_connection * conn,struct s2n_stuffer * from)136 static int s2n_tls12_deserialize_resumption_state(struct s2n_connection *conn, struct s2n_stuffer *from)
137 {
138     uint8_t protocol_version = 0;
139     uint8_t cipher_suite[S2N_TLS_CIPHER_SUITE_LEN] = { 0 };
140 
141     S2N_ERROR_IF(s2n_stuffer_data_available(from) < S2N_TLS12_STATE_SIZE_IN_BYTES - sizeof(uint8_t), S2N_ERR_STUFFER_OUT_OF_DATA);
142 
143     POSIX_GUARD(s2n_stuffer_read_uint8(from, &protocol_version));
144     S2N_ERROR_IF(protocol_version != conn->actual_protocol_version, S2N_ERR_INVALID_SERIALIZED_SESSION_STATE);
145 
146     POSIX_GUARD(s2n_stuffer_read_bytes(from, cipher_suite, S2N_TLS_CIPHER_SUITE_LEN));
147     S2N_ERROR_IF(memcmp(conn->secure.cipher_suite->iana_value, cipher_suite, S2N_TLS_CIPHER_SUITE_LEN), S2N_ERR_INVALID_SERIALIZED_SESSION_STATE);
148 
149     uint64_t now;
150     POSIX_GUARD(conn->config->wall_clock(conn->config->sys_clock_ctx, &now));
151 
152     uint64_t then;
153     POSIX_GUARD(s2n_stuffer_read_uint64(from, &then));
154     S2N_ERROR_IF(then > now, S2N_ERR_INVALID_SERIALIZED_SESSION_STATE);
155     S2N_ERROR_IF(now - then > conn->config->session_state_lifetime_in_nanos, S2N_ERR_INVALID_SERIALIZED_SESSION_STATE);
156 
157     POSIX_GUARD(s2n_stuffer_read_bytes(from, conn->secrets.master_secret, S2N_TLS_SECRET_LEN));
158 
159     if (s2n_stuffer_data_available(from)) {
160         uint8_t ems_negotiated = 0;
161         POSIX_GUARD(s2n_stuffer_read_uint8(from, &ems_negotiated));
162 
163         /**
164          *= https://tools.ietf.org/rfc/rfc7627#section-5.3
165          *# If the original session did not use the "extended_master_secret"
166          *# extension but the new ClientHello contains the extension, then the
167          *# server MUST NOT perform the abbreviated handshake.  Instead, it
168          *# SHOULD continue with a full handshake (as described in
169          *# Section 5.2) to negotiate a new session.
170          *#
171          *# If the original session used the "extended_master_secret"
172          *# extension but the new ClientHello does not contain it, the server
173          *# MUST abort the abbreviated handshake.
174          **/
175         if (conn->ems_negotiated != ems_negotiated) {
176             /* The session ticket needs to have the same EMS state as the current session. If it doesn't
177              * have the same state, the current session takes the state of the session ticket and errors.
178              * If the deserialization process errors, we will use this state in a few extra checks
179              * to determine if we can fallback to a full handshake.
180              */
181             conn->ems_negotiated = ems_negotiated;
182             POSIX_BAIL(S2N_ERR_INVALID_SERIALIZED_SESSION_STATE);
183         }
184     }
185 
186     return S2N_SUCCESS;
187 }
188 
s2n_client_serialize_resumption_state(struct s2n_connection * conn,struct s2n_stuffer * to)189 static int s2n_client_serialize_resumption_state(struct s2n_connection *conn, struct s2n_stuffer *to)
190 {
191     /* Serialize session ticket */
192    if (conn->config->use_tickets && conn->client_ticket.size > 0) {
193        POSIX_GUARD(s2n_stuffer_write_uint8(to, S2N_STATE_WITH_SESSION_TICKET));
194        POSIX_GUARD(s2n_stuffer_write_uint16(to, conn->client_ticket.size));
195        POSIX_GUARD(s2n_stuffer_write(to, &conn->client_ticket));
196    } else {
197        /* Serialize session id */
198        POSIX_ENSURE_LT(conn->actual_protocol_version, S2N_TLS13);
199        POSIX_GUARD(s2n_stuffer_write_uint8(to, S2N_STATE_WITH_SESSION_ID));
200        POSIX_GUARD(s2n_stuffer_write_uint8(to, conn->session_id_len));
201        POSIX_GUARD(s2n_stuffer_write_bytes(to, conn->session_id, conn->session_id_len));
202    }
203 
204     /* Serialize session state */
205     POSIX_GUARD_RESULT(s2n_serialize_resumption_state(conn, to));
206 
207     return 0;
208 }
209 
s2n_tls12_client_deserialize_session_state(struct s2n_connection * conn,struct s2n_stuffer * from)210 static S2N_RESULT s2n_tls12_client_deserialize_session_state(struct s2n_connection *conn, struct s2n_stuffer *from)
211 {
212     RESULT_ENSURE_REF(conn);
213     RESULT_ENSURE_REF(from);
214 
215     RESULT_GUARD_POSIX(s2n_stuffer_read_uint8(from, &conn->actual_protocol_version));
216 
217     uint8_t *cipher_suite_wire = s2n_stuffer_raw_read(from, S2N_TLS_CIPHER_SUITE_LEN);
218     RESULT_ENSURE_REF(cipher_suite_wire);
219     RESULT_GUARD_POSIX(s2n_set_cipher_as_client(conn, cipher_suite_wire));
220 
221     uint64_t then = 0;
222     RESULT_GUARD_POSIX(s2n_stuffer_read_uint64(from, &then));
223 
224     RESULT_GUARD_POSIX(s2n_stuffer_read_bytes(from, conn->secrets.master_secret, S2N_TLS_SECRET_LEN));
225 
226     if (s2n_stuffer_data_available(from)) {
227         uint8_t ems_negotiated = 0;
228         RESULT_GUARD_POSIX(s2n_stuffer_read_uint8(from, &ems_negotiated));
229         conn->ems_negotiated = ems_negotiated;
230     }
231     return S2N_RESULT_OK;
232 }
233 
s2n_validate_ticket_age(uint64_t current_time,uint64_t ticket_issue_time)234 static S2N_RESULT s2n_validate_ticket_age(uint64_t current_time, uint64_t ticket_issue_time)
235 {
236     RESULT_ENSURE(current_time >= ticket_issue_time, S2N_ERR_INVALID_SESSION_TICKET);
237     uint64_t ticket_age_in_nanos = current_time - ticket_issue_time;
238     uint64_t ticket_age_in_sec = ticket_age_in_nanos / ONE_SEC_IN_NANOS;
239     RESULT_ENSURE(ticket_age_in_sec <= ONE_WEEK_IN_SEC, S2N_ERR_INVALID_SESSION_TICKET);
240     return S2N_RESULT_OK;
241 }
242 
s2n_tls13_deserialize_session_state(struct s2n_connection * conn,struct s2n_blob * psk_identity,struct s2n_stuffer * from)243 static S2N_RESULT s2n_tls13_deserialize_session_state(struct s2n_connection *conn, struct s2n_blob *psk_identity, struct s2n_stuffer *from)
244 {
245     RESULT_ENSURE_REF(conn);
246     RESULT_ENSURE_REF(psk_identity);
247     RESULT_ENSURE_REF(from);
248 
249     DEFER_CLEANUP(struct s2n_psk psk = { 0 }, s2n_psk_wipe);
250     RESULT_GUARD(s2n_psk_init(&psk, S2N_PSK_TYPE_RESUMPTION));
251     RESULT_GUARD_POSIX(s2n_psk_set_identity(&psk, psk_identity->data, psk_identity->size));
252 
253     uint8_t protocol_version = 0;
254     RESULT_GUARD_POSIX(s2n_stuffer_read_uint8(from, &protocol_version));
255     RESULT_ENSURE_GTE(protocol_version, S2N_TLS13);
256 
257     uint8_t iana_id[S2N_TLS_CIPHER_SUITE_LEN] = { 0 };
258     RESULT_GUARD_POSIX(s2n_stuffer_read_bytes(from, iana_id, S2N_TLS_CIPHER_SUITE_LEN));
259     struct s2n_cipher_suite *cipher_suite = NULL;
260     RESULT_GUARD(s2n_cipher_suite_from_iana(iana_id, &cipher_suite));
261     RESULT_ENSURE_REF(cipher_suite);
262     psk.hmac_alg = cipher_suite->prf_alg;
263 
264     RESULT_GUARD_POSIX(s2n_stuffer_read_uint64(from, &psk.ticket_issue_time));
265 
266     /**
267      *= https://tools.ietf.org/rfc/rfc8446#section-4.6.1
268      *# Clients MUST NOT cache
269      *# tickets for longer than 7 days, regardless of the ticket_lifetime,
270      *# and MAY delete tickets earlier based on local policy.
271      */
272     uint64_t current_time = 0;
273     RESULT_GUARD_POSIX(conn->config->wall_clock(conn->config->sys_clock_ctx, &current_time));
274     RESULT_GUARD(s2n_validate_ticket_age(current_time, psk.ticket_issue_time));
275 
276     RESULT_GUARD_POSIX(s2n_stuffer_read_uint32(from, &psk.ticket_age_add));
277 
278     uint8_t secret_len = 0;
279     RESULT_GUARD_POSIX(s2n_stuffer_read_uint8(from, &secret_len));
280     RESULT_ENSURE_LTE(secret_len, S2N_TLS_SECRET_LEN);
281     uint8_t *secret_data = s2n_stuffer_raw_read(from, secret_len);
282     RESULT_ENSURE_REF(secret_data);
283     RESULT_GUARD_POSIX(s2n_psk_set_secret(&psk, secret_data, secret_len));
284 
285     if (conn->mode == S2N_SERVER) {
286         RESULT_GUARD_POSIX(s2n_stuffer_read_uint64(from, &psk.keying_material_expiration));
287         RESULT_ENSURE(psk.keying_material_expiration > current_time, S2N_ERR_KEYING_MATERIAL_EXPIRED);
288     }
289 
290     uint32_t max_early_data_size = 0;
291     RESULT_GUARD_POSIX(s2n_stuffer_read_uint32(from, &max_early_data_size));
292     if (max_early_data_size > 0) {
293         RESULT_GUARD_POSIX(s2n_psk_configure_early_data(&psk, max_early_data_size,
294                 iana_id[0], iana_id[1]));
295 
296         uint8_t app_proto_size = 0;
297         RESULT_GUARD_POSIX(s2n_stuffer_read_uint8(from, &app_proto_size));
298         uint8_t *app_proto_data = s2n_stuffer_raw_read(from, app_proto_size);
299         RESULT_ENSURE_REF(app_proto_data);
300         RESULT_GUARD_POSIX(s2n_psk_set_application_protocol(&psk, app_proto_data, app_proto_size));
301 
302         uint16_t early_data_context_size = 0;
303         RESULT_GUARD_POSIX(s2n_stuffer_read_uint16(from, &early_data_context_size));
304         uint8_t *early_data_context_data = s2n_stuffer_raw_read(from, early_data_context_size);
305         RESULT_ENSURE_REF(early_data_context_data);
306         RESULT_GUARD_POSIX(s2n_psk_set_early_data_context(&psk, early_data_context_data, early_data_context_size));
307     }
308 
309     /* Make sure that this connection is configured for resumption PSKs, not external PSKs */
310     RESULT_GUARD(s2n_connection_set_psk_type(conn, S2N_PSK_TYPE_RESUMPTION));
311     /* Remove all previously-set PSKs. To keep the session ticket API behavior consistent
312      * across protocol versions, we currently only support setting a single resumption PSK. */
313     RESULT_GUARD(s2n_psk_parameters_wipe(&conn->psk_params));
314     RESULT_GUARD_POSIX(s2n_connection_append_psk(conn, &psk));
315 
316     return S2N_RESULT_OK;
317 }
318 
s2n_deserialize_resumption_state(struct s2n_connection * conn,struct s2n_blob * psk_identity,struct s2n_stuffer * from)319 static S2N_RESULT s2n_deserialize_resumption_state(struct s2n_connection *conn, struct s2n_blob *psk_identity, struct s2n_stuffer *from)
320 {
321     RESULT_ENSURE_REF(conn);
322     RESULT_ENSURE_REF(from);
323 
324     uint8_t format = 0;
325     RESULT_GUARD_POSIX(s2n_stuffer_read_uint8(from, &format));
326 
327     if (format == S2N_TLS12_SERIALIZED_FORMAT_VERSION) {
328         if (conn->mode == S2N_SERVER) {
329             RESULT_GUARD_POSIX(s2n_tls12_deserialize_resumption_state(conn, from));
330         } else {
331             RESULT_GUARD(s2n_tls12_client_deserialize_session_state(conn, from));
332         }
333     } else if (format == S2N_TLS13_SERIALIZED_FORMAT_VERSION) {
334         RESULT_GUARD(s2n_tls13_deserialize_session_state(conn, psk_identity, from));
335         if (conn->mode == S2N_CLIENT) {
336             /* Free the client_ticket after setting a psk on the connection.
337              * This prevents s2n_connection_get_session from returning a TLS1.3
338              * ticket before a ticket has been received from the server. */
339             RESULT_GUARD_POSIX(s2n_free(&conn->client_ticket));
340         }
341     } else {
342         RESULT_BAIL(S2N_ERR_INVALID_SERIALIZED_SESSION_STATE);
343     }
344     return S2N_RESULT_OK;
345 }
346 
s2n_client_deserialize_with_session_id(struct s2n_connection * conn,struct s2n_stuffer * from)347 static int s2n_client_deserialize_with_session_id(struct s2n_connection *conn, struct s2n_stuffer *from)
348 {
349     uint8_t session_id_len;
350     POSIX_GUARD(s2n_stuffer_read_uint8(from, &session_id_len));
351 
352     if (session_id_len == 0 || session_id_len > S2N_TLS_SESSION_ID_MAX_LEN
353         || session_id_len > s2n_stuffer_data_available(from)) {
354         POSIX_BAIL(S2N_ERR_INVALID_SERIALIZED_SESSION_STATE);
355     }
356 
357     conn->session_id_len = session_id_len;
358     POSIX_GUARD(s2n_stuffer_read_bytes(from, conn->session_id, session_id_len));
359 
360     POSIX_GUARD_RESULT(s2n_deserialize_resumption_state(conn, NULL, from));
361 
362     return 0;
363 }
364 
s2n_client_deserialize_with_session_ticket(struct s2n_connection * conn,struct s2n_stuffer * from)365 static int s2n_client_deserialize_with_session_ticket(struct s2n_connection *conn, struct s2n_stuffer *from)
366 {
367     uint16_t session_ticket_len;
368     POSIX_GUARD(s2n_stuffer_read_uint16(from, &session_ticket_len));
369 
370     if (session_ticket_len == 0 || session_ticket_len > s2n_stuffer_data_available(from)) {
371         POSIX_BAIL(S2N_ERR_INVALID_SERIALIZED_SESSION_STATE);
372     }
373 
374     POSIX_GUARD(s2n_realloc(&conn->client_ticket, session_ticket_len));
375     POSIX_GUARD(s2n_stuffer_read(from, &conn->client_ticket));
376 
377     POSIX_GUARD_RESULT(s2n_deserialize_resumption_state(conn, &conn->client_ticket, from));
378 
379     return 0;
380 }
381 
s2n_client_deserialize_resumption_state(struct s2n_connection * conn,struct s2n_stuffer * from)382 static int s2n_client_deserialize_resumption_state(struct s2n_connection *conn, struct s2n_stuffer *from)
383 {
384     uint8_t format;
385     POSIX_GUARD(s2n_stuffer_read_uint8(from, &format));
386 
387     switch (format) {
388     case S2N_STATE_WITH_SESSION_ID:
389         POSIX_GUARD(s2n_client_deserialize_with_session_id(conn, from));
390         break;
391     case S2N_STATE_WITH_SESSION_TICKET:
392         POSIX_GUARD(s2n_client_deserialize_with_session_ticket(conn, from));
393         break;
394     default:
395         POSIX_BAIL(S2N_ERR_INVALID_SERIALIZED_SESSION_STATE);
396     }
397 
398     return 0;
399 }
400 
s2n_resume_from_cache(struct s2n_connection * conn)401 int s2n_resume_from_cache(struct s2n_connection *conn)
402 {
403     S2N_ERROR_IF(conn->session_id_len == 0, S2N_ERR_SESSION_ID_TOO_SHORT);
404     S2N_ERROR_IF(conn->session_id_len > S2N_TLS_SESSION_ID_MAX_LEN, S2N_ERR_SESSION_ID_TOO_LONG);
405 
406     uint8_t data[S2N_TLS12_TICKET_SIZE_IN_BYTES] = { 0 };
407     struct s2n_blob entry = {0};
408     POSIX_GUARD(s2n_blob_init(&entry, data, S2N_TLS12_TICKET_SIZE_IN_BYTES));
409     uint64_t size = entry.size;
410     int result = conn->config->cache_retrieve(conn, conn->config->cache_retrieve_data, conn->session_id, conn->session_id_len, entry.data, &size);
411     if (result == S2N_CALLBACK_BLOCKED) {
412         POSIX_BAIL(S2N_ERR_ASYNC_BLOCKED);
413     }
414     POSIX_GUARD(result);
415 
416     S2N_ERROR_IF(size != entry.size, S2N_ERR_SIZE_MISMATCH);
417 
418     struct s2n_stuffer from = {0};
419     POSIX_GUARD(s2n_stuffer_init(&from, &entry));
420     POSIX_GUARD(s2n_stuffer_write(&from, &entry));
421     POSIX_GUARD(s2n_decrypt_session_cache(conn, &from));
422 
423     return 0;
424 }
425 
s2n_store_to_cache(struct s2n_connection * conn)426 S2N_RESULT s2n_store_to_cache(struct s2n_connection *conn)
427 {
428     uint8_t data[S2N_TLS12_TICKET_SIZE_IN_BYTES] = { 0 };
429     struct s2n_blob entry = {0};
430     RESULT_GUARD_POSIX(s2n_blob_init(&entry, data, S2N_TLS12_TICKET_SIZE_IN_BYTES));
431     struct s2n_stuffer to = {0};
432 
433     /* session_id_len should always be >0 since either the Client provided a SessionId or the Server generated a new
434      * one for the Client */
435     RESULT_ENSURE(conn->session_id_len > 0, S2N_ERR_SESSION_ID_TOO_SHORT);
436     RESULT_ENSURE(conn->session_id_len <= S2N_TLS_SESSION_ID_MAX_LEN, S2N_ERR_SESSION_ID_TOO_LONG);
437 
438     RESULT_GUARD_POSIX(s2n_stuffer_init(&to, &entry));
439     RESULT_GUARD_POSIX(s2n_encrypt_session_cache(conn, &to));
440 
441     /* Store to the cache */
442     conn->config->cache_store(conn, conn->config->cache_store_data, S2N_TLS_SESSION_CACHE_TTL, conn->session_id, conn->session_id_len, entry.data, entry.size);
443 
444     return S2N_RESULT_OK;
445 }
446 
s2n_connection_set_session(struct s2n_connection * conn,const uint8_t * session,size_t length)447 int s2n_connection_set_session(struct s2n_connection *conn, const uint8_t *session, size_t length)
448 {
449     POSIX_ENSURE_REF(conn);
450     POSIX_ENSURE_REF(session);
451 
452     DEFER_CLEANUP(struct s2n_blob session_data = {0}, s2n_free);
453     POSIX_GUARD(s2n_alloc(&session_data, length));
454     memcpy(session_data.data, session, length);
455 
456     struct s2n_stuffer from = {0};
457     POSIX_GUARD(s2n_stuffer_init(&from, &session_data));
458     POSIX_GUARD(s2n_stuffer_write(&from, &session_data));
459     POSIX_GUARD(s2n_client_deserialize_resumption_state(conn, &from));
460     return 0;
461 }
462 
s2n_connection_get_session(struct s2n_connection * conn,uint8_t * session,size_t max_length)463 int s2n_connection_get_session(struct s2n_connection *conn, uint8_t *session, size_t max_length)
464 {
465     POSIX_ENSURE_REF(conn);
466     POSIX_ENSURE_REF(session);
467 
468     int len = s2n_connection_get_session_length(conn);
469 
470     if (len == 0) {
471         return 0;
472     }
473 
474     S2N_ERROR_IF(len > max_length, S2N_ERR_SERIALIZED_SESSION_STATE_TOO_LONG);
475 
476     struct s2n_blob serialized_data = {0};
477     POSIX_GUARD(s2n_blob_init(&serialized_data, session, len));
478     POSIX_GUARD(s2n_blob_zero(&serialized_data));
479 
480     struct s2n_stuffer to = {0};
481     POSIX_GUARD(s2n_stuffer_init(&to, &serialized_data));
482     POSIX_GUARD(s2n_client_serialize_resumption_state(conn, &to));
483 
484     return len;
485 }
486 
s2n_connection_get_session_ticket_lifetime_hint(struct s2n_connection * conn)487 int s2n_connection_get_session_ticket_lifetime_hint(struct s2n_connection *conn)
488 {
489     POSIX_ENSURE_REF(conn);
490     S2N_ERROR_IF(!(conn->config->use_tickets && conn->client_ticket.size > 0), S2N_ERR_SESSION_TICKET_NOT_SUPPORTED);
491 
492     /* Session resumption using session ticket */
493     return conn->ticket_lifetime_hint;
494 }
495 
s2n_connection_get_session_state_size(struct s2n_connection * conn,size_t * state_size)496 S2N_RESULT s2n_connection_get_session_state_size(struct s2n_connection *conn, size_t *state_size)
497 {
498     RESULT_ENSURE_REF(conn);
499     RESULT_ENSURE_REF(state_size);
500 
501     if (conn->actual_protocol_version < S2N_TLS13) {
502         *state_size = S2N_TLS12_STATE_SIZE_IN_BYTES;
503         return S2N_RESULT_OK;
504     }
505 
506     *state_size = S2N_TLS13_FIXED_STATE_SIZE;
507 
508     uint8_t secret_size = 0;
509     RESULT_ENSURE_REF(conn->secure.cipher_suite);
510     RESULT_GUARD_POSIX(s2n_hmac_digest_size(conn->secure.cipher_suite->prf_alg, &secret_size));
511     *state_size += secret_size;
512 
513     uint32_t server_max_early_data = 0;
514     RESULT_GUARD(s2n_early_data_get_server_max_size(conn, &server_max_early_data));
515     if (server_max_early_data > 0) {
516         *state_size += S2N_TLS13_FIXED_EARLY_DATA_STATE_SIZE
517                 + strlen(conn->application_protocol)
518                 + conn->server_early_data_context.size;
519     }
520 
521     return S2N_RESULT_OK;
522 }
523 
s2n_connection_get_session_length_impl(struct s2n_connection * conn,size_t * length)524 static S2N_RESULT s2n_connection_get_session_length_impl(struct s2n_connection *conn, size_t *length)
525 {
526     RESULT_ENSURE_REF(conn);
527     RESULT_ENSURE_REF(conn->config);
528     RESULT_ENSURE_REF(length);
529     *length = 0;
530 
531     if (conn->config->use_tickets && conn->client_ticket.size > 0) {
532         size_t session_state_size = 0;
533         RESULT_GUARD(s2n_connection_get_session_state_size(conn, &session_state_size));
534         *length = S2N_STATE_FORMAT_LEN + S2N_SESSION_TICKET_SIZE_LEN + conn->client_ticket.size + session_state_size;
535     } else if (conn->session_id_len > 0 && conn->actual_protocol_version < S2N_TLS13) {
536         *length = S2N_STATE_FORMAT_LEN + sizeof(conn->session_id_len) + conn->session_id_len + S2N_TLS12_STATE_SIZE_IN_BYTES;
537     }
538     return S2N_RESULT_OK;
539 }
540 
s2n_connection_get_session_length(struct s2n_connection * conn)541 int s2n_connection_get_session_length(struct s2n_connection *conn)
542 {
543     size_t length = 0;
544     if (s2n_result_is_ok(s2n_connection_get_session_length_impl(conn, &length))) {
545         return length;
546     }
547     return 0;
548 }
549 
s2n_connection_is_session_resumed(struct s2n_connection * conn)550 int s2n_connection_is_session_resumed(struct s2n_connection *conn)
551 {
552     return conn && IS_RESUMPTION_HANDSHAKE(conn)
553         && (conn->actual_protocol_version < S2N_TLS13 || conn->psk_params.type == S2N_PSK_TYPE_RESUMPTION);
554 }
555 
s2n_connection_is_ocsp_stapled(struct s2n_connection * conn)556 int s2n_connection_is_ocsp_stapled(struct s2n_connection *conn)
557 {
558     POSIX_ENSURE_REF(conn);
559 
560     if (conn->actual_protocol_version >= S2N_TLS13) {
561         return (s2n_server_can_send_ocsp(conn) || s2n_server_sent_ocsp(conn));
562     } else {
563         return IS_OCSP_STAPLED(conn);
564     }
565 }
566 
s2n_config_is_encrypt_decrypt_key_available(struct s2n_config * config)567 int s2n_config_is_encrypt_decrypt_key_available(struct s2n_config *config)
568 {
569     uint64_t now;
570     struct s2n_ticket_key *ticket_key = NULL;
571     POSIX_GUARD(config->wall_clock(config->sys_clock_ctx, &now));
572     POSIX_ENSURE_REF(config->ticket_keys);
573 
574     uint32_t ticket_keys_len = 0;
575     POSIX_GUARD_RESULT(s2n_set_len(config->ticket_keys, &ticket_keys_len));
576 
577     for (uint32_t i = ticket_keys_len; i > 0; i--) {
578         uint32_t idx = i - 1;
579         POSIX_GUARD_RESULT(s2n_set_get(config->ticket_keys, idx, (void **)&ticket_key));
580         uint64_t key_intro_time = ticket_key->intro_timestamp;
581 
582         if (key_intro_time < now
583                 && now < key_intro_time + config->encrypt_decrypt_key_lifetime_in_nanos) {
584             return 1;
585         }
586     }
587 
588     return 0;
589 }
590 
591 /* This function is used in s2n_get_ticket_encrypt_decrypt_key to compute the weight
592  * of the keys and to choose a single key from all of the encrypt-decrypt keys.
593  * Higher the weight of the key, higher the probability of being picked.
594  */
s2n_compute_weight_of_encrypt_decrypt_keys(struct s2n_config * config,uint8_t * encrypt_decrypt_keys_index,uint8_t num_encrypt_decrypt_keys,uint64_t now)595 int s2n_compute_weight_of_encrypt_decrypt_keys(struct s2n_config *config,
596                                                uint8_t *encrypt_decrypt_keys_index,
597                                                uint8_t num_encrypt_decrypt_keys,
598                                                uint64_t now)
599 {
600     double total_weight = 0;
601     struct s2n_ticket_key_weight ticket_keys_weight[S2N_MAX_TICKET_KEYS];
602     struct s2n_ticket_key *ticket_key = NULL;
603 
604     /* Compute weight of encrypt-decrypt keys */
605     for (int i = 0; i < num_encrypt_decrypt_keys; i++) {
606         POSIX_GUARD_RESULT(s2n_set_get(config->ticket_keys, encrypt_decrypt_keys_index[i], (void **)&ticket_key));
607 
608         uint64_t key_intro_time = ticket_key->intro_timestamp;
609         uint64_t key_encryption_peak_time = key_intro_time + (config->encrypt_decrypt_key_lifetime_in_nanos / 2);
610 
611         /* The % of encryption using this key is linearly increasing */
612         if (now < key_encryption_peak_time) {
613             ticket_keys_weight[i].key_weight = now - key_intro_time;
614         } else {
615             /* The % of encryption using this key is linearly decreasing */
616             ticket_keys_weight[i].key_weight = (config->encrypt_decrypt_key_lifetime_in_nanos / 2) - (now - key_encryption_peak_time);
617         }
618 
619         ticket_keys_weight[i].key_index = encrypt_decrypt_keys_index[i];
620         total_weight += ticket_keys_weight[i].key_weight;
621     }
622 
623     /* Pick a random number in [0, 1). Using 53 bits (IEEE 754 double-precision floats). */
624     uint64_t random_int = 0;
625     POSIX_GUARD_RESULT(s2n_public_random(pow(2, 53), &random_int));
626     double random = (double)random_int / (double)pow(2, 53);
627 
628     /* Compute cumulative weight of encrypt-decrypt keys */
629     for (int i = 0; i < num_encrypt_decrypt_keys; i++) {
630         ticket_keys_weight[i].key_weight = ticket_keys_weight[i].key_weight / total_weight;
631 
632         if (i > 0) {
633             ticket_keys_weight[i].key_weight += ticket_keys_weight[i - 1].key_weight;
634         }
635 
636         if (ticket_keys_weight[i].key_weight > random) {
637             return ticket_keys_weight[i].key_index;
638         }
639     }
640 
641     POSIX_BAIL(S2N_ERR_ENCRYPT_DECRYPT_KEY_SELECTION_FAILED);
642 }
643 
644 /* This function is used in s2n_encrypt_session_ticket in order for s2n to
645  * choose a key in encrypt-decrypt state from all of the keys added to config
646  */
s2n_get_ticket_encrypt_decrypt_key(struct s2n_config * config)647 struct s2n_ticket_key *s2n_get_ticket_encrypt_decrypt_key(struct s2n_config *config)
648 {
649     uint8_t num_encrypt_decrypt_keys = 0;
650     uint8_t encrypt_decrypt_keys_index[S2N_MAX_TICKET_KEYS] = { 0 };
651     struct s2n_ticket_key *ticket_key = NULL;
652 
653     uint64_t now;
654     PTR_GUARD_POSIX(config->wall_clock(config->sys_clock_ctx, &now));
655     PTR_ENSURE_REF(config->ticket_keys);
656 
657     uint32_t ticket_keys_len = 0;
658     PTR_GUARD_RESULT(s2n_set_len(config->ticket_keys, &ticket_keys_len));
659 
660     for (uint32_t i = ticket_keys_len; i > 0; i--) {
661         uint32_t idx = i - 1;
662         PTR_GUARD_RESULT(s2n_set_get(config->ticket_keys, idx, (void **)&ticket_key));
663         uint64_t key_intro_time = ticket_key->intro_timestamp;
664 
665         if (key_intro_time < now
666                 && now < key_intro_time + config->encrypt_decrypt_key_lifetime_in_nanos) {
667             encrypt_decrypt_keys_index[num_encrypt_decrypt_keys] = idx;
668             num_encrypt_decrypt_keys++;
669         }
670     }
671 
672     if (num_encrypt_decrypt_keys == 0) {
673         PTR_BAIL(S2N_ERR_NO_TICKET_ENCRYPT_DECRYPT_KEY);
674     }
675 
676     if (num_encrypt_decrypt_keys == 1) {
677         PTR_GUARD_RESULT(s2n_set_get(config->ticket_keys, encrypt_decrypt_keys_index[0], (void **)&ticket_key));
678         return ticket_key;
679     }
680 
681     int8_t idx;
682     PTR_GUARD_POSIX(idx = s2n_compute_weight_of_encrypt_decrypt_keys(config, encrypt_decrypt_keys_index, num_encrypt_decrypt_keys, now));
683 
684     PTR_GUARD_RESULT(s2n_set_get(config->ticket_keys, idx, (void **)&ticket_key));
685     return ticket_key;
686 }
687 
688 /* This function is used in s2n_decrypt_session_ticket in order for s2n to
689  * find the matching key that was used for encryption.
690  */
s2n_find_ticket_key(struct s2n_config * config,const uint8_t * name)691 struct s2n_ticket_key *s2n_find_ticket_key(struct s2n_config *config, const uint8_t *name)
692 {
693     uint64_t now;
694     struct s2n_ticket_key *ticket_key = NULL;
695     PTR_GUARD_POSIX(config->wall_clock(config->sys_clock_ctx, &now));
696     PTR_ENSURE_REF(config->ticket_keys);
697 
698     uint32_t ticket_keys_len = 0;
699     PTR_GUARD_RESULT(s2n_set_len(config->ticket_keys, &ticket_keys_len));
700 
701     for (uint32_t i = 0; i < ticket_keys_len; i++) {
702         PTR_GUARD_RESULT(s2n_set_get(config->ticket_keys, i, (void **)&ticket_key));
703 
704         if (memcmp(ticket_key->key_name, name, S2N_TICKET_KEY_NAME_LEN) == 0) {
705 
706             /* Check to see if the key has expired */
707             if (now >= ticket_key->intro_timestamp +
708                                 config->encrypt_decrypt_key_lifetime_in_nanos + config->decrypt_key_lifetime_in_nanos) {
709                 s2n_config_wipe_expired_ticket_crypto_keys(config, i);
710 
711                 return NULL;
712             }
713 
714             return ticket_key;
715         }
716     }
717 
718     return NULL;
719 }
720 
s2n_encrypt_session_ticket(struct s2n_connection * conn,struct s2n_stuffer * to)721 int s2n_encrypt_session_ticket(struct s2n_connection *conn, struct s2n_stuffer *to)
722 {
723     struct s2n_ticket_key *key;
724     struct s2n_session_key aes_ticket_key = {0};
725     struct s2n_blob aes_key_blob = {0};
726 
727     uint8_t iv_data[S2N_TLS_GCM_IV_LEN] = { 0 };
728     struct s2n_blob iv = {0};
729     POSIX_GUARD(s2n_blob_init(&iv, iv_data, sizeof(iv_data)));
730 
731     uint8_t aad_data[S2N_TICKET_AAD_LEN] = { 0 };
732     struct s2n_blob aad_blob = {0};
733     POSIX_GUARD(s2n_blob_init(&aad_blob, aad_data, sizeof(aad_data)));
734     struct s2n_stuffer aad = {0};
735 
736     key = s2n_get_ticket_encrypt_decrypt_key(conn->config);
737 
738     /* No keys loaded by the user or the keys are either in decrypt-only or expired state */
739     S2N_ERROR_IF(!key, S2N_ERR_NO_TICKET_ENCRYPT_DECRYPT_KEY);
740 
741     POSIX_GUARD(s2n_stuffer_write_bytes(to, key->key_name, S2N_TICKET_KEY_NAME_LEN));
742 
743     POSIX_GUARD_RESULT(s2n_get_public_random_data(&iv));
744     POSIX_GUARD(s2n_stuffer_write(to, &iv));
745 
746     POSIX_GUARD(s2n_blob_init(&aes_key_blob, key->aes_key, S2N_AES256_KEY_LEN));
747     POSIX_GUARD(s2n_session_key_alloc(&aes_ticket_key));
748     POSIX_GUARD(s2n_aes256_gcm.init(&aes_ticket_key));
749     POSIX_GUARD(s2n_aes256_gcm.set_encryption_key(&aes_ticket_key, &aes_key_blob));
750 
751     POSIX_GUARD(s2n_stuffer_init(&aad, &aad_blob));
752     POSIX_GUARD(s2n_stuffer_write_bytes(&aad, key->implicit_aad, S2N_TICKET_AAD_IMPLICIT_LEN));
753     POSIX_GUARD(s2n_stuffer_write_bytes(&aad, key->key_name, S2N_TICKET_KEY_NAME_LEN));
754 
755     uint32_t plaintext_header_size = s2n_stuffer_data_available(to);
756     POSIX_GUARD_RESULT(s2n_serialize_resumption_state(conn, to));
757     POSIX_GUARD(s2n_stuffer_skip_write(to, S2N_TLS_GCM_TAG_LEN));
758 
759     struct s2n_blob state_blob = { 0 };
760     struct s2n_stuffer copy_for_encryption = *to;
761     POSIX_GUARD(s2n_stuffer_skip_read(&copy_for_encryption, plaintext_header_size));
762     uint32_t state_blob_size = s2n_stuffer_data_available(&copy_for_encryption);
763     uint8_t *state_blob_data = s2n_stuffer_raw_read(&copy_for_encryption, state_blob_size);
764     POSIX_ENSURE_REF(state_blob_data);
765     POSIX_GUARD(s2n_blob_init(&state_blob, state_blob_data, state_blob_size));
766 
767     POSIX_GUARD(s2n_aes256_gcm.io.aead.encrypt(&aes_ticket_key, &iv, &aad_blob, &state_blob, &state_blob));
768 
769     POSIX_GUARD(s2n_aes256_gcm.destroy_key(&aes_ticket_key));
770     POSIX_GUARD(s2n_session_key_free(&aes_ticket_key));
771 
772     return 0;
773 }
774 
s2n_decrypt_session_ticket(struct s2n_connection * conn,struct s2n_stuffer * from)775 int s2n_decrypt_session_ticket(struct s2n_connection *conn, struct s2n_stuffer *from)
776 {
777     struct s2n_ticket_key *key;
778     DEFER_CLEANUP(struct s2n_session_key aes_ticket_key = {0}, s2n_session_key_free);
779     struct s2n_blob aes_key_blob = {0};
780 
781     uint8_t key_name[S2N_TICKET_KEY_NAME_LEN];
782 
783     uint8_t iv_data[S2N_TLS_GCM_IV_LEN] = { 0 };
784     struct s2n_blob iv = { 0 };
785     POSIX_GUARD(s2n_blob_init(&iv, iv_data, sizeof(iv_data)));
786 
787     uint8_t aad_data[S2N_TICKET_AAD_LEN] = { 0 };
788     struct s2n_blob aad_blob = {0};
789     POSIX_GUARD(s2n_blob_init(&aad_blob, aad_data, sizeof(aad_data)));
790     struct s2n_stuffer aad = {0};
791 
792     POSIX_GUARD(s2n_stuffer_read_bytes(from, key_name, S2N_TICKET_KEY_NAME_LEN));
793 
794     key = s2n_find_ticket_key(conn->config, key_name);
795 
796     /* Key has expired; do full handshake with New Session Ticket (NST) */
797     S2N_ERROR_IF(!key, S2N_ERR_KEY_USED_IN_SESSION_TICKET_NOT_FOUND);
798 
799     POSIX_GUARD(s2n_stuffer_read(from, &iv));
800 
801     s2n_blob_init(&aes_key_blob, key->aes_key, S2N_AES256_KEY_LEN);
802     POSIX_GUARD(s2n_session_key_alloc(&aes_ticket_key));
803     POSIX_GUARD(s2n_aes256_gcm.init(&aes_ticket_key));
804     POSIX_GUARD(s2n_aes256_gcm.set_decryption_key(&aes_ticket_key, &aes_key_blob));
805 
806     POSIX_GUARD(s2n_stuffer_init(&aad, &aad_blob));
807     POSIX_GUARD(s2n_stuffer_write_bytes(&aad, key->implicit_aad, S2N_TICKET_AAD_IMPLICIT_LEN));
808     POSIX_GUARD(s2n_stuffer_write_bytes(&aad, key->key_name, S2N_TICKET_KEY_NAME_LEN));
809 
810     struct s2n_blob en_blob = { 0 };
811     uint32_t en_blob_size = s2n_stuffer_data_available(from);
812     uint8_t *en_blob_data = s2n_stuffer_raw_read(from, en_blob_size);
813     POSIX_ENSURE_REF(en_blob_data);
814     POSIX_GUARD(s2n_blob_init(&en_blob, en_blob_data, en_blob_size));
815     POSIX_GUARD(s2n_aes256_gcm.io.aead.decrypt(&aes_ticket_key, &iv, &aad_blob, &en_blob, &en_blob));
816 
817     struct s2n_blob state_blob = { 0 };
818     uint32_t state_blob_size = en_blob_size - S2N_TLS_GCM_TAG_LEN;
819     POSIX_GUARD(s2n_blob_init(&state_blob, en_blob.data, state_blob_size));
820     struct s2n_stuffer state_stuffer = { 0 };
821     POSIX_GUARD(s2n_stuffer_init(&state_stuffer, &state_blob));
822     POSIX_GUARD(s2n_stuffer_skip_write(&state_stuffer, state_blob_size));
823     POSIX_GUARD_RESULT(s2n_deserialize_resumption_state(conn, &from->blob, &state_stuffer));
824 
825     uint64_t now;
826     POSIX_GUARD(conn->config->wall_clock(conn->config->sys_clock_ctx, &now));
827 
828     /* If the key is in decrypt-only state, then a new key is assigned
829      * for the ticket.
830      */
831     if (now >= key->intro_timestamp + conn->config->encrypt_decrypt_key_lifetime_in_nanos) {
832         /* Check if a key in encrypt-decrypt state is available */
833         if (s2n_config_is_encrypt_decrypt_key_available(conn->config) == 1) {
834             conn->session_ticket_status = S2N_NEW_TICKET;
835             POSIX_GUARD_RESULT(s2n_handshake_type_set_tls12_flag(conn, WITH_SESSION_TICKET));
836             return S2N_SUCCESS;
837         }
838     }
839     return S2N_SUCCESS;
840 }
841 
s2n_encrypt_session_cache(struct s2n_connection * conn,struct s2n_stuffer * to)842 int s2n_encrypt_session_cache(struct s2n_connection *conn, struct s2n_stuffer *to)
843 {
844     return s2n_encrypt_session_ticket(conn, to);
845 }
846 
s2n_decrypt_session_cache(struct s2n_connection * conn,struct s2n_stuffer * from)847 int s2n_decrypt_session_cache(struct s2n_connection *conn, struct s2n_stuffer *from)
848 {
849     struct s2n_ticket_key *key;
850     struct s2n_session_key aes_ticket_key = {0};
851     struct s2n_blob aes_key_blob = {0};
852 
853     uint8_t key_name[S2N_TICKET_KEY_NAME_LEN] = {0};
854 
855     uint8_t iv_data[S2N_TLS_GCM_IV_LEN] = { 0 };
856     struct s2n_blob iv = {0};
857     POSIX_GUARD(s2n_blob_init(&iv, iv_data, sizeof(iv_data)));
858 
859     uint8_t aad_data[S2N_TICKET_AAD_LEN] = { 0 };
860     struct s2n_blob aad_blob = {0};
861     POSIX_GUARD(s2n_blob_init(&aad_blob, aad_data, sizeof(aad_data)));
862     struct s2n_stuffer aad = {0};
863 
864     uint8_t s_data[S2N_TLS12_STATE_SIZE_IN_BYTES] = { 0 };
865     struct s2n_blob state_blob = {0};
866     POSIX_GUARD(s2n_blob_init(&state_blob, s_data, sizeof(s_data)));
867     struct s2n_stuffer state = {0};
868 
869     uint8_t en_data[S2N_TLS12_STATE_SIZE_IN_BYTES + S2N_TLS_GCM_TAG_LEN] = {0};
870     struct s2n_blob en_blob = {0};
871     POSIX_GUARD(s2n_blob_init(&en_blob, en_data, sizeof(en_data)));
872 
873     POSIX_GUARD(s2n_stuffer_read_bytes(from, key_name, S2N_TICKET_KEY_NAME_LEN));
874 
875     key = s2n_find_ticket_key(conn->config, key_name);
876 
877     /* Key has expired; do full handshake with New Session Ticket (NST) */
878     S2N_ERROR_IF(!key, S2N_ERR_KEY_USED_IN_SESSION_TICKET_NOT_FOUND);
879 
880     POSIX_GUARD(s2n_stuffer_read(from, &iv));
881 
882     s2n_blob_init(&aes_key_blob, key->aes_key, S2N_AES256_KEY_LEN);
883     POSIX_GUARD(s2n_session_key_alloc(&aes_ticket_key));
884     POSIX_GUARD(s2n_aes256_gcm.init(&aes_ticket_key));
885     POSIX_GUARD(s2n_aes256_gcm.set_decryption_key(&aes_ticket_key, &aes_key_blob));
886 
887     POSIX_GUARD(s2n_stuffer_init(&aad, &aad_blob));
888     POSIX_GUARD(s2n_stuffer_write_bytes(&aad, key->implicit_aad, S2N_TICKET_AAD_IMPLICIT_LEN));
889     POSIX_GUARD(s2n_stuffer_write_bytes(&aad, key->key_name, S2N_TICKET_KEY_NAME_LEN));
890 
891     POSIX_GUARD(s2n_stuffer_read(from, &en_blob));
892 
893     POSIX_GUARD(s2n_aes256_gcm.io.aead.decrypt(&aes_ticket_key, &iv, &aad_blob, &en_blob, &en_blob));
894 
895     POSIX_GUARD(s2n_stuffer_init(&state, &state_blob));
896     POSIX_GUARD(s2n_stuffer_write_bytes(&state, en_data, S2N_TLS12_STATE_SIZE_IN_BYTES));
897 
898     POSIX_GUARD_RESULT(s2n_deserialize_resumption_state(conn, NULL, &state));
899 
900     POSIX_GUARD(s2n_aes256_gcm.destroy_key(&aes_ticket_key));
901     POSIX_GUARD(s2n_session_key_free(&aes_ticket_key));
902 
903     return 0;
904 }
905 
906 /* This function is used to remove all or just one expired key from server config */
s2n_config_wipe_expired_ticket_crypto_keys(struct s2n_config * config,int8_t expired_key_index)907 int s2n_config_wipe_expired_ticket_crypto_keys(struct s2n_config *config, int8_t expired_key_index)
908 {
909     int num_of_expired_keys = 0;
910     int expired_keys_index[S2N_MAX_TICKET_KEYS];
911     struct s2n_ticket_key *ticket_key = NULL;
912 
913     if (expired_key_index != -1) {
914         expired_keys_index[num_of_expired_keys] = expired_key_index;
915         num_of_expired_keys++;
916 
917         goto end;
918     }
919 
920     uint64_t now;
921     POSIX_GUARD(config->wall_clock(config->sys_clock_ctx, &now));
922     POSIX_ENSURE_REF(config->ticket_keys);
923 
924     uint32_t ticket_keys_len = 0;
925     POSIX_GUARD_RESULT(s2n_set_len(config->ticket_keys, &ticket_keys_len));
926 
927     for (uint32_t i = 0; i < ticket_keys_len; i++) {
928         POSIX_GUARD_RESULT(s2n_set_get(config->ticket_keys, i, (void **)&ticket_key));
929         if (now >= ticket_key->intro_timestamp +
930                    config->encrypt_decrypt_key_lifetime_in_nanos + config->decrypt_key_lifetime_in_nanos) {
931             expired_keys_index[num_of_expired_keys] = i;
932             num_of_expired_keys++;
933         }
934     }
935 
936 end:
937     for (int j = 0; j < num_of_expired_keys; j++) {
938         POSIX_GUARD_RESULT(s2n_set_remove(config->ticket_keys, expired_keys_index[j] - j));
939     }
940 
941     return 0;
942 }
943 
944 
s2n_config_store_ticket_key(struct s2n_config * config,struct s2n_ticket_key * key)945 int s2n_config_store_ticket_key(struct s2n_config *config, struct s2n_ticket_key *key)
946 {
947     /* Keys are stored from oldest to newest */
948     POSIX_GUARD_RESULT(s2n_set_add(config->ticket_keys, key));
949     return S2N_SUCCESS;
950 }
951 
s2n_config_set_initial_ticket_count(struct s2n_config * config,uint8_t num)952 int s2n_config_set_initial_ticket_count(struct s2n_config *config, uint8_t num)
953 {
954     POSIX_ENSURE_REF(config);
955 
956     config->initial_tickets_to_send = num;
957     POSIX_GUARD(s2n_config_set_session_tickets_onoff(config, true));
958 
959     return S2N_SUCCESS;
960 }
961 
s2n_connection_add_new_tickets_to_send(struct s2n_connection * conn,uint8_t num)962 int s2n_connection_add_new_tickets_to_send(struct s2n_connection *conn, uint8_t num)
963 {
964     POSIX_ENSURE_REF(conn);
965     POSIX_GUARD_RESULT(s2n_psk_validate_keying_material(conn));
966 
967     uint32_t out = conn->tickets_to_send + num;
968     POSIX_ENSURE(out <= UINT16_MAX, S2N_ERR_INTEGER_OVERFLOW);
969     conn->tickets_to_send = out;
970 
971     return S2N_SUCCESS;
972 }
973 
s2n_connection_get_tickets_sent(struct s2n_connection * conn,uint16_t * num)974 int s2n_connection_get_tickets_sent(struct s2n_connection *conn, uint16_t *num)
975 {
976     POSIX_ENSURE_REF(conn);
977     POSIX_ENSURE_REF(num);
978     POSIX_ENSURE(conn->mode == S2N_SERVER, S2N_ERR_CLIENT_MODE);
979     *num = conn->tickets_sent;
980     return S2N_SUCCESS;
981 }
982 
s2n_connection_set_server_keying_material_lifetime(struct s2n_connection * conn,uint32_t lifetime_in_secs)983 int s2n_connection_set_server_keying_material_lifetime(struct s2n_connection *conn, uint32_t lifetime_in_secs)
984 {
985     POSIX_ENSURE_REF(conn);
986     conn->server_keying_material_lifetime = lifetime_in_secs;
987     return S2N_SUCCESS;
988 }
989 
s2n_config_set_session_ticket_cb(struct s2n_config * config,s2n_session_ticket_fn callback,void * ctx)990 int s2n_config_set_session_ticket_cb(struct s2n_config *config, s2n_session_ticket_fn callback, void *ctx)
991 {
992     POSIX_ENSURE_MUT(config);
993 
994     config->session_ticket_cb = callback;
995     config->session_ticket_ctx = ctx;
996     return S2N_SUCCESS;
997 }
998 
s2n_session_ticket_get_data_len(struct s2n_session_ticket * ticket,size_t * data_len)999 int s2n_session_ticket_get_data_len(struct s2n_session_ticket *ticket, size_t *data_len)
1000 {
1001     POSIX_ENSURE_REF(ticket);
1002     POSIX_ENSURE_MUT(data_len);
1003 
1004     *data_len = ticket->ticket_data.size;
1005     return S2N_SUCCESS;
1006 }
1007 
s2n_session_ticket_get_data(struct s2n_session_ticket * ticket,size_t max_data_len,uint8_t * data)1008 int s2n_session_ticket_get_data(struct s2n_session_ticket *ticket, size_t max_data_len, uint8_t *data)
1009 {
1010     POSIX_ENSURE_REF(ticket);
1011     POSIX_ENSURE_MUT(data);
1012 
1013     POSIX_ENSURE(ticket->ticket_data.size <= max_data_len, S2N_ERR_SERIALIZED_SESSION_STATE_TOO_LONG);
1014     POSIX_CHECKED_MEMCPY(data, ticket->ticket_data.data, ticket->ticket_data.size);
1015 
1016     return S2N_SUCCESS;
1017 }
1018 
s2n_session_ticket_get_lifetime(struct s2n_session_ticket * ticket,uint32_t * session_lifetime)1019 int s2n_session_ticket_get_lifetime(struct s2n_session_ticket *ticket, uint32_t *session_lifetime)
1020 {
1021     POSIX_ENSURE_REF(ticket);
1022     POSIX_ENSURE_REF(session_lifetime);
1023 
1024     *session_lifetime = ticket->session_lifetime;
1025 
1026     return S2N_SUCCESS;
1027 }
1028