tls13_server.c
Go to the documentation of this file.
1 /**
2  * @file tls13_server.c
3  * @brief Handshake message processing (TLS 1.3 server)
4  *
5  * @section License
6  *
7  * SPDX-License-Identifier: GPL-2.0-or-later
8  *
9  * Copyright (C) 2010-2024 Oryx Embedded SARL. All rights reserved.
10  *
11  * This file is part of CycloneSSL Open.
12  *
13  * This program is free software; you can redistribute it and/or
14  * modify it under the terms of the GNU General Public License
15  * as published by the Free Software Foundation; either version 2
16  * of the License, or (at your option) any later version.
17  *
18  * This program is distributed in the hope that it will be useful,
19  * but WITHOUT ANY WARRANTY; without even the implied warranty of
20  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21  * GNU General Public License for more details.
22  *
23  * You should have received a copy of the GNU General Public License
24  * along with this program; if not, write to the Free Software Foundation,
25  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
26  *
27  * @author Oryx Embedded SARL (www.oryx-embedded.com)
28  * @version 2.4.4
29  **/
30 
31 //Switch to the appropriate trace level
32 #define TRACE_LEVEL TLS_TRACE_LEVEL
33 
34 //Dependencies
35 #include "tls.h"
36 #include "tls_handshake.h"
37 #include "tls_server_extensions.h"
38 #include "tls_server_misc.h"
39 #include "tls_extensions.h"
40 #include "tls_transcript_hash.h"
41 #include "tls_ffdhe.h"
42 #include "tls_misc.h"
43 #include "tls13_server.h"
45 #include "tls13_server_misc.h"
46 #include "tls13_ticket.h"
47 #include "tls13_misc.h"
48 #include "debug.h"
49 
50 //Check TLS library configuration
51 #if (TLS_SUPPORT == ENABLED && TLS_SERVER_SUPPORT == ENABLED && \
52  TLS_MAX_VERSION >= TLS_VERSION_1_3)
53 
54 
55 /**
56  * @brief Send HelloRetryRequest message
57  *
58  * The server will send this message in response to a ClientHello message if it
59  * is able to find an acceptable set of parameters but the ClientHello does not
60  * contain sufficient information to proceed with the handshake
61  *
62  * @param[in] context Pointer to the TLS context
63  * @return Error code
64  **/
65 
67 {
68  error_t error;
69  size_t length;
71 
72  //Point to the buffer where to format the message
73  message = (Tls13HelloRetryRequest *) (context->txBuffer + context->txBufferLen);
74 
75  //When the server responds to a ClientHello with a HelloRetryRequest, the
76  //value of ClientHello1 is replaced with a special synthetic handshake
77  //message of handshake type MessageHash containing Hash(ClientHello1)
78  error = tls13DigestClientHello1(context);
79 
80  //Check status code
81  if(!error)
82  {
83  //Format HelloRetryRequest message
84  error = tls13FormatHelloRetryRequest(context, message, &length);
85  }
86 
87  //Check status code
88  if(!error)
89  {
90  //Debug message
91  TRACE_INFO("Sending HelloRetryRequest message (%" PRIuSIZE " bytes)...\r\n", length);
93 
94  //For reasons of backward compatibility with middleboxes the
95  //HelloRetryRequest message uses the same format as the ServerHello
96  error = tlsSendHandshakeMessage(context, message, length,
98  }
99 
100  //Check status code
101  if(error == NO_ERROR || error == ERROR_WOULD_BLOCK || error == ERROR_TIMEOUT)
102  {
103 #if (TLS13_MIDDLEBOX_COMPAT_SUPPORT == ENABLED)
104  //DTLS implementations do not use the "compatibility mode" and must
105  //not send ChangeCipherSpec messages (refer to RFC 9147, section 5)
106  if(context->transportProtocol == TLS_TRANSPORT_PROTOCOL_STREAM)
107  {
108  //In middlebox compatibility mode, the server sends a dummy
109  //ChangeCipherSpec record immediately after its first handshake
110  //message. This may either be after a ServerHello or a
111  //HelloRetryRequest
113  }
114  else
115 #endif
116  {
117  //Wait for the second updated ClientHello
119  }
120  }
121 
122  //Return status code
123  return error;
124 }
125 
126 
127 /**
128  * @brief Send EncryptedExtensions message
129  *
130  * The server sends the EncryptedExtensions message immediately after the
131  * ServerHello message. The EncryptedExtensions message contains extensions
132  * that can be protected
133  *
134  * @param[in] context Pointer to the TLS context
135  * @return Error code
136  **/
137 
139 {
140  error_t error;
141  size_t length;
143 
144  //Point to the buffer where to format the message
145  message = (Tls13EncryptedExtensions *) (context->txBuffer + context->txBufferLen);
146 
147  //Format EncryptedExtensions message
148  error = tls13FormatEncryptedExtensions(context, message, &length);
149 
150  //Check status code
151  if(!error)
152  {
153  //Debug message
154  TRACE_INFO("Sending EncryptedExtensions message (%" PRIuSIZE " bytes)...\r\n", length);
156 
157  //Send handshake message
158  error = tlsSendHandshakeMessage(context, message, length,
160  }
161 
162  //Check status code
163  if(error == NO_ERROR || error == ERROR_WOULD_BLOCK || error == ERROR_TIMEOUT)
164  {
165  //PSK key exchange method?
166  if(context->keyExchMethod == TLS13_KEY_EXCH_PSK ||
167  context->keyExchMethod == TLS13_KEY_EXCH_PSK_DHE ||
168  context->keyExchMethod == TLS13_KEY_EXCH_PSK_ECDHE ||
169  context->keyExchMethod == TLS13_KEY_EXCH_PSK_HYBRID)
170  {
171  //As the server is authenticating via a PSK, it does not send a
172  //Certificate or a CertificateVerify message
174  }
175  else
176  {
177  //A server can optionally request a certificate from the client
179  }
180  }
181 
182  //Return status code
183  return error;
184 }
185 
186 
187 /**
188  * @brief Send NewSessionTicket message
189  *
190  * At any time after the server has received the client Finished message, it
191  * may send a NewSessionTicket message
192  *
193  * @param[in] context Pointer to the TLS context
194  * @return Error code
195  **/
196 
198 {
199  error_t error;
200  size_t length;
202 
203  //Initialize status code
204  error = NO_ERROR;
205 
206  //Send as many NewSessionTicket messages as requested
207  if(context->newSessionTicketCount < TLS13_NEW_SESSION_TICKET_COUNT)
208  {
209  //Point to the buffer where to format the message
210  message = (Tls13NewSessionTicket *) (context->txBuffer + context->txBufferLen);
211 
212  //Format NewSessionTicket message
213  error = tls13FormatNewSessionTicket(context, message, &length);
214 
215  //Check status code
216  if(!error)
217  {
218  //Increment the number of NewSessionTicket messages that have been sent
219  context->newSessionTicketCount++;
220 
221  //Debug message
222  TRACE_INFO("Sending NewSessionTicket message (%" PRIuSIZE " bytes)...\r\n", length);
224 
225  //Send handshake message
226  error = tlsSendHandshakeMessage(context, message, length,
228  }
229  }
230  else
231  {
232  //The client and server can now exchange application-layer data
234  }
235 
236  //Return status code
237  return error;
238 }
239 
240 
241 /**
242  * @brief Format HelloRetryRequest message
243  * @param[in] context Pointer to the TLS context
244  * @param[out] message Buffer where to format the HelloRetryRequest message
245  * @param[out] length Length of the resulting HelloRetryRequest message
246  * @return Error code
247  **/
248 
251 {
252  error_t error;
253  size_t n;
254  uint8_t *p;
255  TlsExtensionList *extensionList;
256 
257  //In TLS 1.3, the client indicates its version preferences in the
258  //SupportedVersions extension and the legacy_version field must be set
259  //to 0x0303, which is the version number for TLS 1.2
260  if(context->transportProtocol == TLS_TRANSPORT_PROTOCOL_DATAGRAM)
261  {
262  message->serverVersion = HTONS(DTLS_VERSION_1_2);
263  }
264  else
265  {
266  message->serverVersion = HTONS(TLS_VERSION_1_2);
267  }
268 
269  //For backward compatibility with middleboxes the HelloRetryRequest message
270  //uses the same structure as the ServerHello, but with Random field set to
271  //a special value
273 
274  //Point to the session ID
275  p = message->sessionId;
276  //Length of the handshake message
277  *length = sizeof(Tls13HelloRetryRequest);
278 
279  //The legacy_session_id_echo echoes the contents of the client's
280  //legacy_session_id field
281  osMemcpy(message->sessionId, context->sessionId, context->sessionIdLen);
282  message->sessionIdLen = (uint8_t) context->sessionIdLen;
283 
284  //Debug message
285  TRACE_INFO("Session ID (%" PRIu8 " bytes):\r\n", message->sessionIdLen);
286  TRACE_INFO_ARRAY(" ", message->sessionId, message->sessionIdLen);
287 
288  //Advance data pointer
289  p += message->sessionIdLen;
290  //Adjust the length of the message
291  *length += message->sessionIdLen;
292 
293  //The cipher_suite field contains the cipher suite selected by the server
294  STORE16BE(context->cipherSuite.identifier, p);
295 
296  //Advance data pointer
297  p += sizeof(uint16_t);
298  //Adjust the length of the message
299  *length += sizeof(uint16_t);
300 
301  //The legacy_compression_method field must have the value 0
303 
304  //Advance data pointer
305  p += sizeof(uint8_t);
306  //Adjust the length of the message
307  *length += sizeof(uint8_t);
308 
309  //Point to the list of extensions
310  extensionList = (TlsExtensionList *) p;
311  //Total length of the extension list
312  extensionList->length = 0;
313 
314  //Point to the first extension of the list
315  p += sizeof(TlsExtensionList);
316  //Adjust the length of the message
317  *length += sizeof(TlsExtensionList);
318 
319  //The HelloRetryRequest message must contain a SupportedVersions extension
320  error = tls13FormatServerSupportedVersionsExtension(context, p, &n);
321  //Any error to report?
322  if(error)
323  return error;
324 
325  //Fix the length of the extension list
326  extensionList->length += (uint16_t) n;
327  //Point to the next field
328  p += n;
329 
330  //The KeyShare extension contains the mutually supported group the server
331  //intends to negotiate
332  error = tls13FormatSelectedGroupExtension(context, p, &n);
333  //Any error to report?
334  if(error)
335  return error;
336 
337  //Fix the length of the extension list
338  extensionList->length += (uint16_t) n;
339  //Point to the next field
340  p += n;
341 
342  //Convert the length of the extension list to network byte order
343  extensionList->length = htons(extensionList->length);
344  //Total length of the message
345  *length += htons(extensionList->length);
346 
347  //Successful processing
348  return NO_ERROR;
349 }
350 
351 
352 /**
353  * @brief Format EncryptedExtensions message
354  * @param[in] context Pointer to the TLS context
355  * @param[out] message Buffer where to format the EncryptedExtensions message
356  * @param[out] length Length of the resulting EncryptedExtensions message
357  * @return Error code
358  **/
359 
362 {
363  error_t error;
364  size_t n;
365  uint8_t *p;
366 
367  //Point to the extension of the list
368  p = message->extensions;
369  //Length of the handshake message
370  *length = sizeof(Tls13EncryptedExtensions);
371 
372  //Total length of the extension list
373  message->extensionsLen = 0;
374 
375 #if (TLS_SNI_SUPPORT == ENABLED)
376  //The server may include a SNI extension in the ServerHello
377  error = tlsFormatServerSniExtension(context, p, &n);
378  //Any error to report?
379  if(error)
380  return error;
381 
382  //Fix the length of the extension list
383  message->extensionsLen += (uint16_t) n;
384  //Point to the next field
385  p += n;
386 #endif
387 
388 #if (TLS_MAX_FRAG_LEN_SUPPORT == ENABLED)
389  //Servers that receive an ClientHello containing a MaxFragmentLength
390  //extension may accept the requested maximum fragment length by including
391  //an extension of type MaxFragmentLength in the ServerHello
392  error = tlsFormatServerMaxFragLenExtension(context, p, &n);
393  //Any error to report?
394  if(error)
395  return error;
396 
397  //Fix the length of the extension list
398  message->extensionsLen += (uint16_t) n;
399  //Point to the next field
400  p += n;
401 #endif
402 
403 #if (TLS_RECORD_SIZE_LIMIT_SUPPORT == ENABLED)
404  //The value of RecordSizeLimit is the maximum size of record in octets
405  //that the endpoint is willing to receive
406  error = tlsFormatServerRecordSizeLimitExtension(context, p, &n);
407  //Any error to report?
408  if(error)
409  return error;
410 
411  //Fix the length of the extension list
412  message->extensionsLen += (uint16_t) n;
413  //Point to the next field
414  p += n;
415 #endif
416 
417 #if (TLS_ALPN_SUPPORT == ENABLED)
418  //The ALPN extension contains the name of the selected protocol
419  error = tlsFormatServerAlpnExtension(context, p, &n);
420  //Any error to report?
421  if(error)
422  return error;
423 
424  //Fix the length of the extension list
425  message->extensionsLen += (uint16_t) n;
426  //Point to the next field
427  p += n;
428 #endif
429 
430 #if (TLS_RAW_PUBLIC_KEY_SUPPORT == ENABLED)
431  //The ClientCertType extension in the ServerHello indicates the type
432  //of certificates the client is requested to provide in a subsequent
433  //certificate payload
434  error = tlsFormatClientCertTypeExtension(context, p, &n);
435  //Any error to report?
436  if(error)
437  return error;
438 
439  //Fix the length of the extension list
440  message->extensionsLen += (uint16_t) n;
441  //Point to the next field
442  p += n;
443 
444  //With the ServerCertType extension in the ServerHello, the TLS server
445  //indicates the certificate type carried in the certificate payload
446  error = tlsFormatServerCertTypeExtension(context, p, &n);
447  //Any error to report?
448  if(error)
449  return error;
450 
451  //Fix the length of the extension list
452  message->extensionsLen += (uint16_t) n;
453  //Point to the next field
454  p += n;
455 #endif
456 
457 #if (TLS13_EARLY_DATA_SUPPORT == ENABLED)
458  //If the server intends to process the early data, then it returns its
459  //own EarlyData extension in the EncryptedExtensions message
460  error = tls13FormatServerEarlyDataExtension(context,
462  //Any error to report?
463  if(error)
464  return error;
465 
466  //Fix the length of the extension list
467  message->extensionsLen += (uint16_t) n;
468  //Point to the next field
469  p += n;
470 #endif
471 
472  //Convert the length of the extension list to network byte order
473  message->extensionsLen = htons(message->extensionsLen);
474  //Total length of the message
475  *length += htons(message->extensionsLen);
476 
477  //Successful processing
478  return NO_ERROR;
479 }
480 
481 
482 /**
483  * @brief Format NewSessionTicket message
484  * @param[in] context Pointer to the TLS context
485  * @param[out] message Buffer where to format the NewSessionTicket message
486  * @param[out] length Length of the resulting NewSessionTicket message
487  * @return Error code
488  **/
489 
492 {
493 #if (TLS_TICKET_SUPPORT == ENABLED)
494  error_t error;
495  size_t n;
496  uint8_t *p;
498  TlsExtensionList *extensionList;
499 
500  //Set the lifetime of the ticket, in seconds
501  message->ticketLifetime = HTONL(TLS_TICKET_LIFETIME / 1000);
502 
503  //The ticket_age_add field is used to obscure the age of the ticket
504  error = context->prngAlgo->read(context->prngContext,
505  (uint8_t *) &message->ticketAgeAdd, sizeof(uint32_t));
506  //Any error to report?
507  if(error)
508  return error;
509 
510  //Point to ticket nonce
511  p = message->ticketNonce;
512  //Length of the handshake message
513  *length = sizeof(Tls13NewSessionTicket);
514 
515  //The ticket nonce is a per-ticket value that is unique across all tickets
516  //issued on this connection
517  context->ticketNonce++;
518 
519  //Copy ticket nonce
520  STORE32BE(context->ticketNonce, message->ticketNonce);
521  //Set the length of the nonce
522  message->ticketNonceLen = sizeof(uint32_t);
523 
524  //Advance data pointer
525  p += message->ticketNonceLen;
526  //Adjust the length of the message
527  *length += message->ticketNonceLen;
528 
529  //Point to the value of the ticket
530  ticket = (Tls13Ticket *) p;
531 
532  //The ticket itself is an opaque label. It may be either a database lookup
533  //key or a self-encrypted and self-authenticated value
534  error = tls13GenerateTicket(context, message, ticket->data, &n);
535  //Any error to report?
536  if(error)
537  return error;
538 
539  //Fix the length of the ticket
540  ticket->length = htons(n);
541 
542  //Advance data pointer
543  p += sizeof(Tls13Ticket) + n;
544  //Adjust the length of the message
545  *length += sizeof(Tls13Ticket) + n;
546 
547  //Point to the list of extensions
548  extensionList = (TlsExtensionList *) p;
549  //Total length of the extension list
550  extensionList->length = 0;
551 
552  //Point to the first extension of the list
553  p += sizeof(TlsExtensionList);
554  //Adjust the length of the message
555  *length += sizeof(TlsExtensionList);
556 
557 #if (TLS13_EARLY_DATA_SUPPORT == ENABLED)
558  //The sole extension currently defined for NewSessionTicket is EarlyData
559  //indicating that the ticket may be used to send 0-RTT data
560  error = tls13FormatServerEarlyDataExtension(context,
562  //Any error to report?
563  if(error)
564  return error;
565 
566  //Fix the length of the extension list
567  extensionList->length += (uint16_t) n;
568  //Point to the next field
569  p += n;
570 #endif
571 
572  //Convert the length of the extension list to network byte order
573  extensionList->length = htons(extensionList->length);
574  //Total length of the message
575  *length += htons(extensionList->length);
576 
577  //Successful processing
578  return NO_ERROR;
579 #else
580  //Session ticket mechanism is not implemented
581  return ERROR_NOT_IMPLEMENTED;
582 #endif
583 }
584 
585 #endif
@ TLS13_KEY_EXCH_PSK
Definition: tls.h:1161
#define htons(value)
Definition: cpu_endian.h:413
Parsing and checking of TLS extensions.
TLS helper functions.
#define TRACE_INFO_ARRAY(p, a, n)
Definition: debug.h:96
Handshake message processing (TLS 1.3 server)
@ ERROR_WOULD_BLOCK
Definition: error.h:96
@ TLS13_KEY_EXCH_PSK_DHE
Definition: tls.h:1162
TLS handshake.
@ TLS_COMPRESSION_METHOD_NULL
Definition: tls.h:1128
error_t tls13SendEncryptedExtensions(TlsContext *context)
Send EncryptedExtensions message.
Definition: tls13_server.c:138
@ ERROR_NOT_IMPLEMENTED
Definition: error.h:66
error_t tls13SendHelloRetryRequest(TlsContext *context)
Send HelloRetryRequest message.
Definition: tls13_server.c:66
uint8_t p
Definition: ndp.h:300
uint8_t message[]
Definition: chap.h:154
@ TLS_STATE_CERTIFICATE_REQUEST
Definition: tls.h:1469
TLS 1.3 session tickets.
@ TLS_TRANSPORT_PROTOCOL_DATAGRAM
Definition: tls.h:957
@ TLS_STATE_APPLICATION_DATA
Definition: tls.h:1485
error_t tlsSendHandshakeMessage(TlsContext *context, const void *data, size_t length, TlsMessageType type)
Send handshake message.
error_t tlsFormatServerSniExtension(TlsContext *context, uint8_t *p, size_t *written)
Format SNI extension.
@ TLS13_KEY_EXCH_PSK_HYBRID
Definition: tls.h:1164
TLS 1.3 helper functions.
TlsExtensionList
Definition: tls.h:1584
error_t tlsFormatServerRecordSizeLimitExtension(TlsContext *context, uint8_t *p, size_t *written)
Format RecordSizeLimit extension.
#define osMemcpy(dest, src, length)
Definition: os_port.h:141
#define HTONL(value)
Definition: cpu_endian.h:411
#define TlsContext
Definition: tls.h:36
error_t
Error codes.
Definition: error.h:43
#define TLS_VERSION_1_2
Definition: tls.h:96
Tls13HelloRetryRequest
Definition: tls13_misc.h:297
Formatting and parsing of extensions (TLS 1.3 server)
#define STORE16BE(a, p)
Definition: cpu_endian.h:262
@ TLS_STATE_SERVER_FINISHED
Definition: tls.h:1480
error_t tlsFormatClientCertTypeExtension(TlsContext *context, uint8_t *p, size_t *written)
Format ClientCertType extension.
@ TLS_TYPE_SERVER_HELLO
Definition: tls.h:1042
@ TLS_TYPE_ENCRYPTED_EXTENSIONS
Definition: tls.h:1047
error_t tls13SendNewSessionTicket(TlsContext *context)
Send NewSessionTicket message.
Definition: tls13_server.c:197
#define TRACE_INFO(...)
Definition: debug.h:95
uint8_t length
Definition: tcp.h:368
error_t tls13FormatSelectedGroupExtension(TlsContext *context, uint8_t *p, size_t *written)
Format KeyShare extension (HelloRetryRequest message)
const uint8_t tls13HelloRetryRequestRandom[32]
Definition: tls13_misc.c:65
error_t tls13FormatServerSupportedVersionsExtension(TlsContext *context, uint8_t *p, size_t *written)
Format SupportedVersions extension.
Helper functions for TLS 1.3 server.
error_t tlsFormatServerMaxFragLenExtension(TlsContext *context, uint8_t *p, size_t *written)
Format MaxFragmentLength extension.
Transcript hash calculation.
Tls13Ticket
Definition: tls13_misc.h:349
@ ERROR_TIMEOUT
Definition: error.h:95
uint8_t ticket[]
Definition: tls.h:1844
@ TLS13_KEY_EXCH_PSK_ECDHE
Definition: tls.h:1163
@ TLS_STATE_CLIENT_HELLO_2
Definition: tls.h:1457
#define TRACE_DEBUG_ARRAY(p, a, n)
Definition: debug.h:108
#define TLS_TICKET_LIFETIME
Definition: tls.h:164
#define HTONS(value)
Definition: cpu_endian.h:410
uint8_t n
Tls13NewSessionTicket
Definition: tls13_misc.h:328
error_t tls13FormatServerEarlyDataExtension(TlsContext *context, TlsMessageType msgType, uint8_t *p, size_t *written)
Format EarlyData extension.
TLS (Transport Layer Security)
error_t tls13FormatEncryptedExtensions(TlsContext *context, Tls13EncryptedExtensions *message, size_t *length)
Format EncryptedExtensions message.
Definition: tls13_server.c:360
error_t tls13GenerateTicket(TlsContext *context, const Tls13NewSessionTicket *message, uint8_t *ticket, size_t *length)
Session ticket generation.
Definition: tls13_ticket.c:306
@ TLS_TRANSPORT_PROTOCOL_STREAM
Definition: tls.h:956
FFDHE key exchange.
Helper functions for TLS server.
@ TLS_STATE_SERVER_CHANGE_CIPHER_SPEC_2
Definition: tls.h:1479
Formatting and parsing of extensions (TLS server)
@ TLS_TYPE_NEW_SESSION_TICKET
Definition: tls.h:1044
void tlsChangeState(TlsContext *context, TlsState newState)
Update TLS state.
Definition: tls_misc.c:54
#define PRIuSIZE
error_t tlsFormatServerCertTypeExtension(TlsContext *context, uint8_t *p, size_t *written)
Format ServerCertType extension.
error_t tls13DigestClientHello1(TlsContext *context)
Hash ClientHello1 in the transcript when HelloRetryRequest is used.
Definition: tls13_misc.c:725
error_t tlsFormatServerAlpnExtension(TlsContext *context, uint8_t *p, size_t *written)
Format ALPN extension.
#define DTLS_VERSION_1_2
Definition: dtls_misc.h:36
#define STORE32BE(a, p)
Definition: cpu_endian.h:286
error_t tls13FormatNewSessionTicket(TlsContext *context, Tls13NewSessionTicket *message, size_t *length)
Format NewSessionTicket message.
Definition: tls13_server.c:490
@ NO_ERROR
Success.
Definition: error.h:44
Debugging facilities.
#define TLS13_NEW_SESSION_TICKET_COUNT
Definition: tls13_misc.h:127
error_t tls13FormatHelloRetryRequest(TlsContext *context, Tls13HelloRetryRequest *message, size_t *length)
Format HelloRetryRequest message.
Definition: tls13_server.c:249
Tls13EncryptedExtensions
Definition: tls13_misc.h:315