tls.c
Go to the documentation of this file.
1 /**
2  * @file tls.c
3  * @brief TLS (Transport Layer Security)
4  *
5  * @section License
6  *
7  * SPDX-License-Identifier: GPL-2.0-or-later
8  *
9  * Copyright (C) 2010-2025 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  * @section Description
28  *
29  * The TLS protocol provides communications security over the Internet. The
30  * protocol allows client/server applications to communicate in a way that
31  * is designed to prevent eavesdropping, tampering, or message forgery
32  *
33  * @author Oryx Embedded SARL (www.oryx-embedded.com)
34  * @version 2.5.4
35  **/
36 
37 //Switch to the appropriate trace level
38 #define TRACE_LEVEL TLS_TRACE_LEVEL
39 
40 //Dependencies
41 #include "tls.h"
42 #include "tls_cipher_suites.h"
43 #include "tls_handshake.h"
44 #include "tls_common.h"
45 #include "tls_certificate.h"
46 #include "tls_key_material.h"
47 #include "tls_transcript_hash.h"
48 #include "tls_record.h"
49 #include "tls_misc.h"
50 #include "tls13_client_misc.h"
51 #include "tls13_key_material.h"
52 #include "tls13_ticket.h"
53 #include "dtls_record.h"
54 #include "pkix/pem_import.h"
55 #include "pkix/x509_cert_parse.h"
56 #include "debug.h"
57 
58 //Check TLS library configuration
59 #if (TLS_SUPPORT == ENABLED)
60 
61 
62 /**
63  * @brief TLS context initialization
64  * @return Handle referencing the fully initialized TLS context
65  **/
66 
68 {
69  TlsContext *context;
70 
71  //Allocate a memory buffer to hold the TLS context
72  context = tlsAllocMem(sizeof(TlsContext));
73 
74  //Successful memory allocation?
75  if(context != NULL)
76  {
77  //Clear TLS context
78  osMemset(context, 0, sizeof(TlsContext));
79 
80  //Default state
81  context->state = TLS_STATE_INIT;
82  //Default transport protocol
83  context->transportProtocol = TLS_TRANSPORT_PROTOCOL_STREAM;
84  //Default operation mode
85  context->entity = TLS_CONNECTION_END_CLIENT;
86  //Default client authentication mode
87  context->clientAuthMode = TLS_CLIENT_AUTH_NONE;
88 
89  //Minimum and maximum versions accepted by the implementation
90  context->versionMin = TLS_MIN_VERSION;
91  context->versionMax = TLS_MAX_VERSION;
92 
93  //Default record layer version number
94  context->version = TLS_MIN_VERSION;
95  context->encryptionEngine.version = TLS_MIN_VERSION;
96 
97 #if (TLS_MAX_VERSION >= TLS_VERSION_1_3 && TLS_MIN_VERSION <= TLS_VERSION_1_3)
98  //A TLS 1.3 client may pregenerate key shares
99  context->cipherSuiteTypes = TLS_CIPHER_SUITE_TYPE_TLS13 |
101 
102  //Select default named group
104  {
105  context->preferredGroup = TLS_GROUP_X25519;
106  }
107  else if(tls13IsGroupSupported(context, TLS_GROUP_SECP256R1))
108  {
109  context->preferredGroup = TLS_GROUP_SECP256R1;
110  }
111  else
112  {
113  context->preferredGroup = TLS_GROUP_NONE;
114  }
115 #endif
116 
117 #if (DTLS_SUPPORT == ENABLED)
118  //Default PMTU
119  context->pmtu = DTLS_DEFAULT_PMTU;
120  //Default timeout
121  context->timeout = INFINITE_DELAY;
122 #endif
123 
124 #if (DTLS_SUPPORT == ENABLED && DTLS_REPLAY_DETECTION_SUPPORT == ENABLED)
125  //Anti-replay mechanism is enabled by default
126  context->replayDetectionEnabled = TRUE;
127 #endif
128 
129 #if (TLS_QUIC_SUPPORT == ENABLED)
130  //Select initial encryption level
131  context->encryptionEngine.level = TLS_ENCRYPTION_LEVEL_INITIAL;
132  context->decryptionEngine.level = TLS_ENCRYPTION_LEVEL_INITIAL;
133 #endif
134 
135 #if (TLS_DH_SUPPORT == ENABLED)
136  //Initialize Diffie-Hellman context
137  dhInit(&context->dhContext);
138 #endif
139 
140 #if (TLS_ECDH_SUPPORT == ENABLED || TLS_HYBRID_SUPPORT == ENABLED)
141  //Initialize ECDH context
142  ecdhInit(&context->ecdhContext);
143 #endif
144 
145 #if (TLS_MLKEM_SUPPORT == ENABLED || TLS_HYBRID_SUPPORT == ENABLED)
146  //Initialize KEM context
147  kemInit(&context->kemContext, NULL);
148 #endif
149 
150 #if (TLS_RSA_SUPPORT == ENABLED)
151  //Initialize peer's RSA public key
152  rsaInitPublicKey(&context->peerRsaPublicKey);
153 #endif
154 
155 #if (TLS_DSA_SIGN_SUPPORT == ENABLED)
156  //Initialize peer's DSA public key
157  dsaInitPublicKey(&context->peerDsaPublicKey);
158 #endif
159 
160 #if (TLS_ECDSA_SIGN_SUPPORT == ENABLED || TLS_SM2_SIGN_SUPPORT == ENABLED)
161  //Initialize peer's EC public key
162  ecInitPublicKey(&context->peerEcPublicKey);
163 #endif
164 
165 #if (TLS_ED25519_SIGN_SUPPORT == ENABLED || TLS_ED448_SIGN_SUPPORT == ENABLED)
166  //Initialize peer's EdDSA public key
167  eddsaInitPublicKey(&context->peerEddsaPublicKey);
168 #endif
169 
170  //Maximum number of plaintext data the TX and RX buffers can hold
171  context->txBufferMaxLen = TLS_MAX_RECORD_LENGTH;
172  context->rxBufferMaxLen = TLS_MAX_RECORD_LENGTH;
173 
174 #if (TLS_MAX_FRAG_LEN_SUPPORT == ENABLED)
175  //Maximum fragment length
176  context->maxFragLen = TLS_MAX_RECORD_LENGTH;
177 #endif
178 #if (TLS_RECORD_SIZE_LIMIT_SUPPORT == ENABLED)
179  //Maximum record size the peer is willing to receive
180  context->recordSizeLimit = TLS_MAX_RECORD_LENGTH;
181 #endif
182 
183 #if (DTLS_SUPPORT == ENABLED)
184  //Calculate the required size for the TX buffer
185  context->txBufferSize = context->txBufferMaxLen + sizeof(DtlsRecord) +
187 
188  //Calculate the required size for the RX buffer
189  context->rxBufferSize = context->rxBufferMaxLen + sizeof(DtlsRecord) +
191 #else
192  //Calculate the required size for the TX buffer
193  context->txBufferSize = context->txBufferMaxLen + sizeof(TlsRecord) +
195 
196  //Calculate the required size for the RX buffer
197  context->rxBufferSize = context->rxBufferMaxLen + sizeof(TlsRecord) +
199 #endif
200  }
201 
202  //Return a pointer to the freshly created TLS context
203  return context;
204 }
205 
206 
207 /**
208  * @brief Retrieve current TLS state
209  * @param[in] context Pointer to the TLS context
210  * @return Current TLS state
211  **/
212 
214 {
215  TlsState state;
216 
217  //Valid TLS context?
218  if(context != NULL)
219  {
220  state = context->state;
221  }
222  else
223  {
224  state = TLS_STATE_INIT;
225  }
226 
227  //Return current state
228  return state;
229 }
230 
231 
232 /**
233  * @brief Register TLS state change callback
234  * @param[in] context Pointer to the TLS context
235  * @param[in] stateChangeCallback TLS state change callback
236  * @return Error code
237  **/
238 
240  TlsStateChangeCallback stateChangeCallback)
241 {
242  //Check parameters
243  if(context == NULL || stateChangeCallback == NULL)
245 
246  //Save TLS state change callback
247  context->stateChangeCallback = stateChangeCallback;
248 
249  //Successful processing
250  return NO_ERROR;
251 }
252 
253 
254 /**
255  * @brief Set socket send and receive callbacks
256  * @param[in] context Pointer to the TLS context
257  * @param[in] socketSendCallback Send callback function
258  * @param[in] socketReceiveCallback Receive callback function
259  * @param[in] handle Socket handle
260  * @return Error code
261  **/
262 
264  TlsSocketSendCallback socketSendCallback,
265  TlsSocketReceiveCallback socketReceiveCallback, TlsSocketHandle handle)
266 {
267  //Invalid TLS context?
268  if(context == NULL)
270 
271  //Check parameters
272  if(socketSendCallback == NULL || socketReceiveCallback == NULL)
274 
275  //Save send and receive callback functions
276  context->socketSendCallback = socketSendCallback;
277  context->socketReceiveCallback = socketReceiveCallback;
278 
279  //This socket handle will be directly passed to the callback functions
280  context->socketHandle = handle;
281 
282  //Successful processing
283  return NO_ERROR;
284 }
285 
286 
287 /**
288  * @brief Set minimum and maximum versions permitted
289  * @param[in] context Pointer to the TLS context
290  * @param[in] versionMin Minimum version accepted by the TLS implementation
291  * @param[in] versionMax Maximum version accepted by the TLS implementation
292  * @return Error code
293  **/
294 
295 error_t tlsSetVersion(TlsContext *context, uint16_t versionMin,
296  uint16_t versionMax)
297 {
298  //Invalid TLS context?
299  if(context == NULL)
301 
302  //Check parameters
303  if(versionMin < TLS_VERSION_1_0 || versionMin > TLS_MAX_VERSION)
305 
306  if(versionMax > TLS_VERSION_1_3 || versionMax < TLS_MIN_VERSION)
308 
309  if(versionMin > versionMax)
311 
312  //Minimum version accepted by the implementation
313  context->versionMin = MAX(versionMin, TLS_MIN_VERSION);
314  //Maximum version accepted by the implementation
315  context->versionMax = MIN(versionMax, TLS_MAX_VERSION);
316 
317  //Default record layer version number
318  context->version = context->versionMin;
319  context->encryptionEngine.version = context->versionMin;
320 
321  //Successful processing
322  return NO_ERROR;
323 }
324 
325 
326 /**
327  * @brief Set the transport protocol to be used
328  * @param[in] context Pointer to the TLS context
329  * @param[in] transportProtocol Transport protocol to be used
330  * @return Error code
331  **/
332 
334  TlsTransportProtocol transportProtocol)
335 {
336  //Invalid TLS context?
337  if(context == NULL)
339 
340  //Check parameters
341  if(transportProtocol != TLS_TRANSPORT_PROTOCOL_STREAM &&
342  transportProtocol != TLS_TRANSPORT_PROTOCOL_DATAGRAM &&
343  transportProtocol != TLS_TRANSPORT_PROTOCOL_QUIC &&
344  transportProtocol != TLS_TRANSPORT_PROTOCOL_EAP)
345  {
347  }
348 
349  //Set transport protocol
350  context->transportProtocol = transportProtocol;
351 
352  //Successful processing
353  return NO_ERROR;
354 }
355 
356 
357 /**
358  * @brief Set operation mode (client or server)
359  * @param[in] context Pointer to the TLS context
360  * @param[in] entity Specifies whether this entity is considered a client or a server
361  * @return Error code
362  **/
363 
365 {
366  //Invalid TLS context?
367  if(context == NULL)
369 
370  //Check parameters
371  if(entity != TLS_CONNECTION_END_CLIENT && entity != TLS_CONNECTION_END_SERVER)
373 
374  //Check whether TLS operates as a client or a server
375  context->entity = entity;
376 
377  //Successful processing
378  return NO_ERROR;
379 }
380 
381 
382 /**
383  * @brief Set the pseudo-random number generator to be used
384  * @param[in] context Pointer to the TLS context
385  * @param[in] prngAlgo PRNG algorithm
386  * @param[in] prngContext Pointer to the PRNG context
387  * @return Error code
388  **/
389 
390 error_t tlsSetPrng(TlsContext *context, const PrngAlgo *prngAlgo,
391  void *prngContext)
392 {
393  //Invalid TLS context?
394  if(context == NULL)
396 
397  //Check parameters
398  if(prngAlgo == NULL || prngContext == NULL)
400 
401  //PRNG algorithm that will be used to generate random numbers
402  context->prngAlgo = prngAlgo;
403  //PRNG context
404  context->prngContext = prngContext;
405 
406  //Successful processing
407  return NO_ERROR;
408 }
409 
410 
411 /**
412  * @brief Set the server name
413  * @param[in] context Pointer to the TLS context
414  * @param[in] serverName Fully qualified domain name of the server
415  * @return Error code
416  **/
417 
418 error_t tlsSetServerName(TlsContext *context, const char_t *serverName)
419 {
420  size_t i;
421  size_t length;
422 
423  //Check parameters
424  if(context == NULL || serverName == NULL)
426 
427  //Retrieve the length of the server name
428  length = osStrlen(serverName);
429 
430  //Check whether the server name has already been configured
431  if(context->serverName != NULL)
432  {
433  //Release memory
434  tlsFreeMem(context->serverName);
435  context->serverName = NULL;
436  }
437 
438  //Valid server name?
439  if(length > 0)
440  {
441  //Allocate a memory block to hold the hostname
442  context->serverName = tlsAllocMem(length + 1);
443  //Failed to allocate memory?
444  if(context->serverName == NULL)
445  return ERROR_OUT_OF_MEMORY;
446 
447  //Convert the hostname into lowercase
448  for(i = 0; i < length; i++)
449  {
450  context->serverName[i] = osTolower(serverName[i]);
451  }
452 
453  //Properly terminate the string with a NULL character
454  context->serverName[length] = '\0';
455  }
456 
457  //Successful processing
458  return NO_ERROR;
459 }
460 
461 
462 /**
463  * @brief Get the server name
464  * @param[in] context Pointer to the TLS context
465  * @return Fully qualified domain name of the server
466  **/
467 
469 {
470  static const char_t defaultServerName[] = "";
471 
472  //Valid protocol name?
473  if(context != NULL && context->serverName != NULL)
474  {
475  //Return the fully qualified domain name of the server
476  return context->serverName;
477  }
478  else
479  {
480  //Return an empty string
481  return defaultServerName;
482  }
483 }
484 
485 
486 /**
487  * @brief Set session cache
488  * @param[in] context Pointer to the TLS context
489  * @param[in] cache Session cache that will be used to save/resume TLS sessions
490  * @return Error code
491  **/
492 
494 {
495  //Check parameters
496  if(context == NULL)
498 
499  //The cache will be used to save/resume TLS sessions
500  context->cache = cache;
501 
502  //Successful processing
503  return NO_ERROR;
504 }
505 
506 
507 /**
508  * @brief Set client authentication mode (for servers only)
509  * @param[in] context Pointer to the TLS context
510  * @param[in] mode Client authentication mode
511  * @return Error code
512  **/
513 
515 {
516  //Invalid TLS context?
517  if(context == NULL)
519 
520  //Save client authentication mode
521  context->clientAuthMode = mode;
522 
523  //Successful processing
524  return NO_ERROR;
525 }
526 
527 
528 /**
529  * @brief Set TLS buffer size
530  * @param[in] context Pointer to the TLS context
531  * @param[in] txBufferSize TX buffer size
532  * @param[in] rxBufferSize RX buffer size
533  * @return Error code
534  **/
535 
536 error_t tlsSetBufferSize(TlsContext *context, size_t txBufferSize,
537  size_t rxBufferSize)
538 {
539  //Invalid TLS context?
540  if(context == NULL)
542 
543  //Check parameters
544  if(txBufferSize < TLS_MIN_RECORD_LENGTH ||
545  rxBufferSize < TLS_MIN_RECORD_LENGTH)
546  {
548  }
549 
550  //Maximum number of plaintext data the TX and RX buffers can hold
551  context->txBufferMaxLen = txBufferSize;
552  context->rxBufferMaxLen = rxBufferSize;
553 
554 #if (DTLS_SUPPORT == ENABLED)
555  //Calculate the required size for the TX buffer
556  context->txBufferSize = txBufferSize + sizeof(DtlsRecord) +
558 
559  //Calculate the required size for the RX buffer
560  context->rxBufferSize = rxBufferSize + sizeof(DtlsRecord) +
562 #else
563  //Calculate the required size for the TX buffer
564  context->txBufferSize = txBufferSize + sizeof(TlsRecord) +
566 
567  //Calculate the required size for the RX buffer
568  context->rxBufferSize = rxBufferSize + sizeof(TlsRecord) +
570 #endif
571 
572  //Successful processing
573  return NO_ERROR;
574 }
575 
576 
577 /**
578  * @brief Set maximum fragment length
579  * @param[in] context Pointer to the TLS context
580  * @param[in] maxFragLen Maximum fragment length
581  * @return Error code
582  **/
583 
584 error_t tlsSetMaxFragmentLength(TlsContext *context, size_t maxFragLen)
585 {
586 #if (TLS_MAX_FRAG_LEN_SUPPORT == ENABLED)
587  //Invalid TLS context?
588  if(context == NULL)
590 
591  //Make sure the specified value is acceptable (ref to RFC 6066, section 4)
592  if(maxFragLen != 512 && maxFragLen != 1024 &&
593  maxFragLen != 2048 && maxFragLen != 4096 &&
594  maxFragLen != 16384)
595  {
597  }
598 
599  //Set maximum fragment length
600  context->maxFragLen = maxFragLen;
601 
602  //Successful processing
603  return NO_ERROR;
604 #else
605  //Not implemented
606  return ERROR_NOT_IMPLEMENTED;
607 #endif
608 }
609 
610 
611 /**
612  * @brief Specify the list of allowed cipher suites
613  * @param[in] context Pointer to the TLS context
614  * @param[in] cipherSuites List of allowed cipher suites (most preferred
615  * first). This parameter is taken as reference
616  * @param[in] length Number of cipher suites in the list
617  * @return Error code
618  **/
619 
620 error_t tlsSetCipherSuites(TlsContext *context, const uint16_t *cipherSuites,
621  uint_t length)
622 {
623  //Invalid TLS context?
624  if(context == NULL)
626 
627  //Check parameters
628  if(cipherSuites == NULL && length != 0)
630 
631  //Restrict the cipher suites that can be used
632  context->cipherSuites = cipherSuites;
633  context->numCipherSuites = length;
634 
635  //Successful processing
636  return NO_ERROR;
637 }
638 
639 
640 /**
641  * @brief Specify the list of allowed ECDHE and FFDHE groups
642  * @param[in] context Pointer to the TLS context
643  * @param[in] groups List of named groups (most preferred first). This
644  * parameter is taken as reference
645  * @param[in] length Number of named groups in the list
646  * @return Error code
647  **/
648 
649 error_t tlsSetSupportedGroups(TlsContext *context, const uint16_t *groups,
650  uint_t length)
651 {
652  //Invalid TLS context?
653  if(context == NULL)
655 
656  //Check parameters
657  if(groups == NULL && length != 0)
659 
660  //Restrict the named groups that can be used
661  context->supportedGroups = groups;
662  context->numSupportedGroups = length;
663 
664  //Successful processing
665  return NO_ERROR;
666 }
667 
668 
669 /**
670  * @brief Specify the preferred ECDHE or FFDHE group
671  * @param[in] context Pointer to the TLS context
672  * @param[in] group Preferred ECDHE or FFDHE named group
673  * @return Error code
674  **/
675 
676 error_t tlsSetPreferredGroup(TlsContext *context, uint16_t group)
677 {
678 #if (TLS_MAX_VERSION >= TLS_VERSION_1_3 && TLS_MIN_VERSION <= TLS_VERSION_1_3)
679  //Invalid TLS context?
680  if(context == NULL)
682 
683  //Save the preferred named group
684  context->preferredGroup = group;
685 
686  //Successful processing
687  return NO_ERROR;
688 #else
689  //Not implemented
690  return ERROR_NOT_IMPLEMENTED;
691 #endif
692 }
693 
694 
695 /**
696  * @brief Specify the list of allowed signature algorithms
697  * @param[in] context Pointer to the TLS context
698  * @param[in] signAlgos List of signature algorithms (most preferred first). This
699  * parameter is taken as reference
700  * @param[in] length Number of signature algorithms in the list
701  * @return Error code
702  **/
703 
705  const uint16_t *signAlgos, uint_t length)
706 {
707 #if (TLS_MAX_VERSION >= TLS_VERSION_1_2 && TLS_MIN_VERSION <= TLS_VERSION_1_3)
708  //Invalid TLS context?
709  if(context == NULL)
711 
712  //Check parameters
713  if(signAlgos == NULL && length != 0)
715 
716  //Restrict the signature algorithms that can be used
717  context->supportedSignAlgos = signAlgos;
718  context->numSupportedSignAlgos = length;
719 
720  //Successful processing
721  return NO_ERROR;
722 #else
723  //Not implemented
724  return ERROR_NOT_IMPLEMENTED;
725 #endif
726 }
727 
728 
729 /**
730  * @brief Import Diffie-Hellman parameters
731  * @param[in] context Pointer to the TLS context
732  * @param[in] params PEM structure that holds Diffie-Hellman parameters. This
733  * parameter is taken as reference
734  * @param[in] length Total length of the DER structure
735  * @return Error code
736  **/
737 
738 error_t tlsSetDhParameters(TlsContext *context, const char_t *params,
739  size_t length)
740 {
741 #if (TLS_DH_SUPPORT == ENABLED)
742  //Invalid TLS context?
743  if(context == NULL)
745 
746  //Check parameters
747  if(params == NULL && length != 0)
749 
750  //Decode the PEM structure that holds Diffie-Hellman parameters
751  return pemImportDhParameters(&context->dhContext.params, params, length);
752 #else
753  //Diffie-Hellman is not implemented
754  return ERROR_NOT_IMPLEMENTED;
755 #endif
756 }
757 
758 
759 /**
760  * @brief Register ECDH key agreement callback function
761  * @param[in] context Pointer to the TLS context
762  * @param[in] ecdhCallback ECDH callback function
763  * @return Error code
764  **/
765 
767 {
768 #if (TLS_ECC_CALLBACK_SUPPORT == ENABLED)
769  //Check parameters
770  if(context == NULL || ecdhCallback == NULL)
772 
773  //Save ECDH key agreement callback function
774  context->ecdhCallback = ecdhCallback;
775 
776  //Successful processing
777  return NO_ERROR;
778 #else
779  //PSK key exchange is not implemented
780  return ERROR_NOT_IMPLEMENTED;
781 #endif
782 }
783 
784 
785 /**
786  * @brief Register ECDSA signature generation callback function
787  * @param[in] context Pointer to the TLS context
788  * @param[in] ecdsaSignCallback ECDSA signature generation callback function
789  * @return Error code
790  **/
791 
793  TlsEcdsaSignCallback ecdsaSignCallback)
794 {
795 #if (TLS_ECC_CALLBACK_SUPPORT == ENABLED)
796  //Check parameters
797  if(context == NULL || ecdsaSignCallback == NULL)
799 
800  //Save ECDSA signature generation callback function
801  context->ecdsaSignCallback = ecdsaSignCallback;
802 
803  //Successful processing
804  return NO_ERROR;
805 #else
806  //PSK key exchange is not implemented
807  return ERROR_NOT_IMPLEMENTED;
808 #endif
809 }
810 
811 
812 /**
813  * @brief Register ECDSA signature verification callback function
814  * @param[in] context Pointer to the TLS context
815  * @param[in] ecdsaVerifyCallback ECDSA signature verification callback function
816  * @return Error code
817  **/
818 
820  TlsEcdsaVerifyCallback ecdsaVerifyCallback)
821 {
822 #if (TLS_ECC_CALLBACK_SUPPORT == ENABLED)
823  //Check parameters
824  if(context == NULL || ecdsaVerifyCallback == NULL)
826 
827  //Save ECDSA signature verification callback function
828  context->ecdsaVerifyCallback = ecdsaVerifyCallback;
829 
830  //Successful processing
831  return NO_ERROR;
832 #else
833  //PSK key exchange is not implemented
834  return ERROR_NOT_IMPLEMENTED;
835 #endif
836 }
837 
838 
839 /**
840  * @brief Register key logging callback function (for debugging purpose only)
841  * @param[in] context Pointer to the TLS context
842  * @param[in] keyLogCallback Key logging callback function
843  * @return Error code
844  **/
845 
847  TlsKeyLogCallback keyLogCallback)
848 {
849 #if (TLS_KEY_LOG_SUPPORT == ENABLED)
850  //Check parameters
851  if(context == NULL || keyLogCallback == NULL)
853 
854  //Save key logging callback function
855  context->keyLogCallback = keyLogCallback;
856 
857  //Successful processing
858  return NO_ERROR;
859 #else
860  //Key logging is not implemented
861  return ERROR_NOT_IMPLEMENTED;
862 #endif
863 }
864 
865 
866 /**
867  * @brief Allow unknown ALPN protocols
868  * @param[in] context Pointer to the TLS context
869  * @param[in] allowed Specifies whether unknown ALPN protocols are allowed
870  * @return Error code
871  **/
872 
874 {
875 #if (TLS_ALPN_SUPPORT == ENABLED)
876  //Invalid TLS context?
877  if(context == NULL)
879 
880  //Allow or disallow unknown ALPN protocols
881  context->unknownProtocolsAllowed = allowed;
882 
883  //Successful processing
884  return NO_ERROR;
885 #else
886  //ALPN is not implemented
887  return ERROR_NOT_IMPLEMENTED;
888 #endif
889 }
890 
891 
892 /**
893  * @brief Set the list of supported ALPN protocols
894  * @param[in] context Pointer to the TLS context
895  * @param[in] protocolList Comma-delimited list of supported protocols
896  * @return Error code
897  **/
898 
899 error_t tlsSetAlpnProtocolList(TlsContext *context, const char_t *protocolList)
900 {
901 #if (TLS_ALPN_SUPPORT == ENABLED)
902  size_t length;
903 
904  //Check parameters
905  if(context == NULL || protocolList == NULL)
907 
908  //Retrieve the length of the list
909  length = osStrlen(protocolList);
910 
911  //Check whether the list of supported protocols has already been configured
912  if(context->protocolList != NULL)
913  {
914  //Release memory
915  tlsFreeMem(context->protocolList);
916  context->protocolList = NULL;
917  }
918 
919  //Check whether the list of protocols is valid
920  if(length > 0)
921  {
922  //Allocate a memory block to hold the list
923  context->protocolList = tlsAllocMem(length + 1);
924  //Failed to allocate memory?
925  if(context->protocolList == NULL)
926  return ERROR_OUT_OF_MEMORY;
927 
928  //Save the list of supported protocols
929  osStrcpy(context->protocolList, protocolList);
930  }
931 
932  //Successful processing
933  return NO_ERROR;
934 #else
935  //ALPN is not implemented
936  return ERROR_NOT_IMPLEMENTED;
937 #endif
938 }
939 
940 
941 /**
942  * @brief Register ALPN callback function
943  * @param[in] context Pointer to the TLS context
944  * @param[in] alpnCallback ALPN callback function
945  * @return Error code
946  **/
947 
949 {
950 #if (TLS_ALPN_SUPPORT == ENABLED)
951  //Check parameters
952  if(context == NULL || alpnCallback == NULL)
954 
955  //Save ALPN callback function
956  context->alpnCallback = alpnCallback;
957 
958  //Successful processing
959  return NO_ERROR;
960 #else
961  //ALPN is not implemented
962  return ERROR_NOT_IMPLEMENTED;
963 #endif
964 }
965 
966 
967 /**
968  * @brief Get the name of the selected ALPN protocol
969  * @param[in] context Pointer to the TLS context
970  * @return Pointer to the protocol name
971  **/
972 
974 {
975  static const char_t defaultProtocolName[] = "";
976 
977 #if (TLS_ALPN_SUPPORT == ENABLED)
978  //Valid protocol name?
979  if(context != NULL && context->selectedProtocol != NULL)
980  {
981  //Return the name of the selected protocol
982  return context->selectedProtocol;
983  }
984  else
985 #endif
986  {
987  //Return an empty string
988  return defaultProtocolName;
989  }
990 }
991 
992 
993 /**
994  * @brief Set the pre-shared key to be used
995  * @param[in] context Pointer to the TLS context
996  * @param[in] psk Pointer to the pre-shared key
997  * @param[in] length Length of the pre-shared key, in bytes
998  * @return Error code
999  **/
1000 
1001 error_t tlsSetPsk(TlsContext *context, const uint8_t *psk, size_t length)
1002 {
1003 #if (TLS_PSK_SUPPORT == ENABLED)
1004  //Invalid TLS context?
1005  if(context == NULL)
1006  return ERROR_INVALID_PARAMETER;
1007 
1008  //Check parameters
1009  if(psk == NULL && length != 0)
1010  return ERROR_INVALID_PARAMETER;
1011 
1012  //Check whether the pre-shared key has already been configured
1013  if(context->psk != NULL)
1014  {
1015  //Release memory
1016  osMemset(context->psk, 0, context->pskLen);
1017  tlsFreeMem(context->psk);
1018  context->psk = NULL;
1019  context->pskLen = 0;
1020  }
1021 
1022  //Valid PSK?
1023  if(length > 0)
1024  {
1025  //Allocate a memory block to hold the pre-shared key
1026  context->psk = tlsAllocMem(length);
1027  //Failed to allocate memory?
1028  if(context->psk == NULL)
1029  return ERROR_OUT_OF_MEMORY;
1030 
1031  //Save the pre-shared key
1032  osMemcpy(context->psk, psk, length);
1033  //Save the length of the key
1034  context->pskLen = length;
1035  }
1036 
1037 #if (TLS_MAX_VERSION >= TLS_VERSION_1_3 && TLS_MIN_VERSION <= TLS_VERSION_1_3)
1038  //For externally established PSKs, the hash algorithm must be set when the
1039  //PSK is established, or default to SHA-256 if no such algorithm is defined
1040  context->pskHashAlgo = TLS_HASH_ALGO_SHA256;
1041 
1042  //The cipher suite must be provisioned along with the key
1043  context->pskCipherSuite = 0;
1044 #endif
1045 
1046  //Successful processing
1047  return NO_ERROR;
1048 #else
1049  //PSK key exchange is not implemented
1050  return ERROR_NOT_IMPLEMENTED;
1051 #endif
1052 }
1053 
1054 
1055 /**
1056  * @brief Set the PSK identity to be used by the client
1057  * @param[in] context Pointer to the TLS context
1058  * @param[in] pskIdentity NULL-terminated string that contains the PSK identity
1059  * @return Error code
1060  **/
1061 
1062 error_t tlsSetPskIdentity(TlsContext *context, const char_t *pskIdentity)
1063 {
1064 #if (TLS_PSK_SUPPORT == ENABLED)
1065  size_t length;
1066 
1067  //Check parameters
1068  if(context == NULL || pskIdentity == NULL)
1069  return ERROR_INVALID_PARAMETER;
1070 
1071  //Retrieve the length of the PSK identity
1072  length = osStrlen(pskIdentity);
1073 
1074  //Check whether the PSK identity has already been configured
1075  if(context->pskIdentity != NULL)
1076  {
1077  //Release memory
1078  tlsFreeMem(context->pskIdentity);
1079  context->pskIdentity = NULL;
1080  }
1081 
1082  //Valid PSK identity?
1083  if(length > 0)
1084  {
1085  //Allocate a memory block to hold the PSK identity
1086  context->pskIdentity = tlsAllocMem(length + 1);
1087  //Failed to allocate memory?
1088  if(context->pskIdentity == NULL)
1089  return ERROR_OUT_OF_MEMORY;
1090 
1091  //Save the PSK identity
1092  osStrcpy(context->pskIdentity, pskIdentity);
1093  }
1094 
1095  //Successful processing
1096  return NO_ERROR;
1097 #else
1098  //PSK key exchange is not implemented
1099  return ERROR_NOT_IMPLEMENTED;
1100 #endif
1101 }
1102 
1103 
1104 /**
1105  * @brief Set the PSK identity hint to be used by the server
1106  * @param[in] context Pointer to the TLS context
1107  * @param[in] pskIdentityHint NULL-terminated string that contains the PSK identity hint
1108  * @return Error code
1109  **/
1110 
1111 error_t tlsSetPskIdentityHint(TlsContext *context, const char_t *pskIdentityHint)
1112 {
1113 #if (TLS_PSK_SUPPORT == ENABLED)
1114  size_t length;
1115 
1116  //Check parameters
1117  if(context == NULL || pskIdentityHint == NULL)
1118  return ERROR_INVALID_PARAMETER;
1119 
1120  //Retrieve the length of the PSK identity hint
1121  length = osStrlen(pskIdentityHint);
1122 
1123  //Check whether the PSK identity hint has already been configured
1124  if(context->pskIdentityHint != NULL)
1125  {
1126  //Release memory
1127  tlsFreeMem(context->pskIdentityHint);
1128  context->pskIdentityHint = NULL;
1129  }
1130 
1131  //Valid PSK identity hint?
1132  if(length > 0)
1133  {
1134  //Allocate a memory block to hold the PSK identity hint
1135  context->pskIdentityHint = tlsAllocMem(length + 1);
1136  //Failed to allocate memory?
1137  if(context->pskIdentityHint == NULL)
1138  return ERROR_OUT_OF_MEMORY;
1139 
1140  //Save the PSK identity hint
1141  osStrcpy(context->pskIdentityHint, pskIdentityHint);
1142  }
1143 
1144  //Successful processing
1145  return NO_ERROR;
1146 #else
1147  //PSK key exchange is not implemented
1148  return ERROR_NOT_IMPLEMENTED;
1149 #endif
1150 }
1151 
1152 
1153 /**
1154  * @brief Register PSK callback function
1155  * @param[in] context Pointer to the TLS context
1156  * @param[in] pskCallback PSK callback function
1157  * @return Error code
1158  **/
1159 
1161 {
1162 #if (TLS_PSK_SUPPORT == ENABLED)
1163  //Check parameters
1164  if(context == NULL || pskCallback == NULL)
1165  return ERROR_INVALID_PARAMETER;
1166 
1167  //Save PSK callback function
1168  context->pskCallback = pskCallback;
1169 
1170  //Successful processing
1171  return NO_ERROR;
1172 #else
1173  //PSK key exchange is not implemented
1174  return ERROR_NOT_IMPLEMENTED;
1175 #endif
1176 }
1177 
1178 
1179 /**
1180  * @brief Register the raw public key verification callback function
1181  * @param[in] context Pointer to the TLS context
1182  * @param[in] rpkVerifyCallback RPK verification callback function
1183  * @return Error code
1184  **/
1185 
1187  TlsRpkVerifyCallback rpkVerifyCallback)
1188 {
1189 #if (TLS_RAW_PUBLIC_KEY_SUPPORT == ENABLED)
1190  //Check parameters
1191  if(context == NULL || rpkVerifyCallback == NULL)
1192  return ERROR_INVALID_PARAMETER;
1193 
1194  //Save raw public key verification callback function
1195  context->rpkVerifyCallback = rpkVerifyCallback;
1196 
1197  //Successful processing
1198  return NO_ERROR;
1199 #else
1200  //Raw public keys are not implemented
1201  return ERROR_NOT_IMPLEMENTED;
1202 #endif
1203 }
1204 
1205 
1206 /**
1207  * @brief Import a trusted CA list
1208  * @param[in] context Pointer to the TLS context
1209  * @param[in] trustedCaList List of trusted CA (PEM format)
1210  * @param[in] length Total length of the list
1211  * @return Error code
1212  **/
1213 
1214 error_t tlsSetTrustedCaList(TlsContext *context, const char_t *trustedCaList,
1215  size_t length)
1216 {
1217  //Invalid TLS context?
1218  if(context == NULL)
1219  return ERROR_INVALID_PARAMETER;
1220 
1221  //Check parameters
1222  if(trustedCaList == NULL && length != 0)
1223  return ERROR_INVALID_PARAMETER;
1224 
1225  //Save the list of trusted CA
1226  context->trustedCaList = trustedCaList;
1227  context->trustedCaListLen = length;
1228 
1229  //Successful processing
1230  return NO_ERROR;
1231 }
1232 
1233 
1234 /**
1235  * @brief Load entity's certificate
1236  * @param[in] context Pointer to the TLS context
1237  * @param[in] index Zero-based index identifying a slot
1238  * @param[in] certChain Certificate chain (PEM format). This parameter is
1239  * taken as reference
1240  * @param[in] certChainLen Length of the certificate chain
1241  * @param[in] privateKey Private key (PEM format). This parameter is taken
1242  * as reference
1243  * @param[in] privateKeyLen Length of the private key
1244  * @param[in] password NULL-terminated string containing the password. This
1245  * parameter is required if the private key is encrypted
1246  * @return Error code
1247  **/
1248 
1250  const char_t *certChain, size_t certChainLen, const char_t *privateKey,
1251  size_t privateKeyLen, const char_t *password)
1252 {
1253  error_t error;
1254  uint8_t *derCert;
1255  size_t derCertLen;
1256  X509CertInfo *certInfo;
1257  TlsCertDesc *cert;
1258  TlsCertificateType certType;
1259  TlsNamedGroup namedCurve;
1260  TlsSignatureScheme certSignScheme;
1261 
1262  //Make sure the TLS context is valid
1263  if(context == NULL)
1264  return ERROR_INVALID_PARAMETER;
1265 
1266  //The implementation limits the number of certificates that can be loaded
1267  if(index >= TLS_MAX_CERTIFICATES)
1268  return ERROR_INVALID_PARAMETER;
1269 
1270  //Check whether the certificate chain is valid
1271  if(certChain == NULL || certChainLen == 0)
1272  return ERROR_INVALID_PARAMETER;
1273 
1274  //The private key is optional
1275  if(privateKey == NULL && privateKeyLen != 0)
1276  return ERROR_INVALID_PARAMETER;
1277 
1278  //The password if required only for encrypted private keys
1279  if(password != NULL && osStrlen(password) > TLS_MAX_PASSWORD_LEN)
1280  return ERROR_INVALID_PASSWORD;
1281 
1282  //The first pass calculates the length of the DER-encoded certificate
1283  error = pemImportCertificate(certChain, certChainLen, NULL, &derCertLen,
1284  NULL);
1285 
1286  //Check status code
1287  if(!error)
1288  {
1289  //Allocate a memory buffer to hold the DER-encoded certificate
1290  derCert = tlsAllocMem(derCertLen);
1291 
1292  //Successful memory allocation?
1293  if(derCert != NULL)
1294  {
1295  //The second pass decodes the PEM certificate
1296  error = pemImportCertificate(certChain, certChainLen, derCert,
1297  &derCertLen, NULL);
1298 
1299  //Check status code
1300  if(!error)
1301  {
1302  //Allocate a memory buffer to store X.509 certificate info
1303  certInfo = tlsAllocMem(sizeof(X509CertInfo));
1304 
1305  //Successful memory allocation?
1306  if(certInfo != NULL)
1307  {
1309 
1310  //Additional certificate parsing options
1312  options.ignoreUnknownExtensions = TRUE;
1313 
1314  //Parse X.509 certificate
1315  error = x509ParseCertificateEx(derCert, derCertLen, certInfo,
1316  &options);
1317 
1318  //Check status code
1319  if(!error)
1320  {
1321  //Retrieve the type of the X.509 certificate
1322  error = tlsGetCertificateType(certInfo, &certType,
1323  &namedCurve);
1324  }
1325 
1326  //Check status code
1327  if(!error)
1328  {
1329  //Retrieve the signature algorithm that has been used to sign
1330  //the certificate
1331  error = tlsGetCertificateSignAlgo(certInfo, &certSignScheme);
1332  }
1333 
1334  //Release previously allocated memory
1335  tlsFreeMem(certInfo);
1336  }
1337  else
1338  {
1339  //Failed to allocate memory
1340  error = ERROR_OUT_OF_MEMORY;
1341  }
1342  }
1343 
1344  //Release previously allocated memory
1345  tlsFreeMem(derCert);
1346  }
1347  else
1348  {
1349  //Failed to allocate memory
1350  error = ERROR_OUT_OF_MEMORY;
1351  }
1352  }
1353 
1354  //Check status code
1355  if(!error)
1356  {
1357  //Point to the structure that describes the certificate
1358  cert = &context->certs[index];
1359 
1360  //Save the certificate chain and the corresponding private key
1361  cert->certChain = certChain;
1362  cert->certChainLen = certChainLen;
1363  cert->privateKey = privateKey;
1364  cert->privateKeyLen = privateKeyLen;
1365  cert->type = certType;
1366  cert->signScheme = certSignScheme;
1367  cert->namedCurve = namedCurve;
1368 
1369  //The password if required only for encrypted private keys
1370  if(password != NULL)
1371  {
1372  osStrcpy(cert->password, password);
1373  }
1374  else
1375  {
1376  osStrcpy(cert->password, "");
1377  }
1378  }
1379 
1380  //Return status code
1381  return error;
1382 }
1383 
1384 
1385 /**
1386  * @brief Register certificate verification callback function
1387  * @param[in] context Pointer to the TLS context
1388  * @param[in] certVerifyCallback Certificate verification callback function
1389  * @param[in] param An opaque pointer passed to the callback function
1390  * @return Error code
1391  **/
1392 
1394  TlsCertVerifyCallback certVerifyCallback, void *param)
1395 {
1396  //Invalid TLS context?
1397  if(context == NULL)
1398  return ERROR_INVALID_PARAMETER;
1399 
1400  //Save certificate verification callback function
1401  context->certVerifyCallback = certVerifyCallback;
1402  //This opaque pointer will be directly passed to the callback function
1403  context->certVerifyParam = param;
1404 
1405  //Successful processing
1406  return NO_ERROR;
1407 }
1408 
1409 
1410 /**
1411  * @brief Enable session ticket mechanism
1412  * @param[in] context Pointer to the TLS context
1413  * @param[in] enabled Specifies whether session tickets are allowed
1414  * @return Error code
1415  **/
1416 
1418 {
1419 #if (TLS_TICKET_SUPPORT == ENABLED)
1420  //Invalid TLS context?
1421  if(context == NULL)
1422  return ERROR_INVALID_PARAMETER;
1423 
1424  //Enable or disable session ticket mechanism
1425  context->sessionTicketEnabled = enabled;
1426 
1427  //Successful processing
1428  return NO_ERROR;
1429 #else
1430  //Session ticket mechanism is not implemented
1431  return ERROR_NOT_IMPLEMENTED;
1432 #endif
1433 }
1434 
1435 
1436 /**
1437  * @brief Enable TrustedCaKeys extension
1438  * @param[in] context Pointer to the TLS context
1439  * @param[in] enabled Specifies whether TrustedCaKeys extension is enabled
1440  * @return Error code
1441  **/
1442 
1444 {
1445 #if (TLS_TRUSTED_CA_KEYS_SUPPORT == ENABLED)
1446  //Invalid TLS context?
1447  if(context == NULL)
1448  return ERROR_INVALID_PARAMETER;
1449 
1450  //Enable or disable support for TrustedCaKeys extension
1451  context->trustedCaKeysEnabled = enabled;
1452 
1453  //Successful processing
1454  return NO_ERROR;
1455 #else
1456  //TrustedCaKeys extension is not implemented
1457  return ERROR_NOT_IMPLEMENTED;
1458 #endif
1459 }
1460 
1461 
1462 /**
1463  * @brief Enable CertificateAuthorities extension
1464  * @param[in] context Pointer to the TLS context
1465  * @param[in] enabled Specifies whether CertificateAuthorities extension is
1466  * enabled
1467  * @return Error code
1468  **/
1469 
1471 {
1472 #if (TLS_CERT_AUTHORITIES_SUPPORT == ENABLED)
1473  //Invalid TLS context?
1474  if(context == NULL)
1475  return ERROR_INVALID_PARAMETER;
1476 
1477  //Enable or disable support for CertificateAuthorities extension
1478  context->certAuthoritiesEnabled = enabled;
1479 
1480  //Successful processing
1481  return NO_ERROR;
1482 #else
1483  //CertificateAuthorities extension is not implemented
1484  return ERROR_NOT_IMPLEMENTED;
1485 #endif
1486 }
1487 
1488 
1489 /**
1490  * @brief Enable secure renegotiation
1491  * @param[in] context Pointer to the TLS context
1492  * @param[in] enabled Specifies whether secure renegotiation is allowed
1493  * @return Error code
1494  **/
1495 
1497 {
1498 #if (TLS_SECURE_RENEGOTIATION_SUPPORT == ENABLED)
1499  //Invalid TLS context?
1500  if(context == NULL)
1501  return ERROR_INVALID_PARAMETER;
1502 
1503  //Enable or disable secure renegotiation
1504  context->secureRenegoEnabled = enabled;
1505 
1506  //Successful processing
1507  return NO_ERROR;
1508 #else
1509  //Secure renegotiation is not implemented
1510  return ERROR_NOT_IMPLEMENTED;
1511 #endif
1512 }
1513 
1514 
1515 /**
1516  * @brief Perform fallback retry (for clients only)
1517  * @param[in] context Pointer to the TLS context
1518  * @param[in] enabled Specifies whether FALLBACK_SCSV is enabled
1519  * @return Error code
1520  **/
1521 
1523 {
1524 #if (TLS_FALLBACK_SCSV_SUPPORT == ENABLED)
1525  //Invalid TLS context?
1526  if(context == NULL)
1527  return ERROR_INVALID_PARAMETER;
1528 
1529  //Enable or disable support for FALLBACK_SCSV
1530  context->fallbackScsvEnabled = enabled;
1531 
1532  //Successful processing
1533  return NO_ERROR;
1534 #else
1535  //Not implemented
1536  return ERROR_NOT_IMPLEMENTED;
1537 #endif
1538 }
1539 
1540 
1541 /**
1542  * @brief Set ticket encryption/decryption callbacks
1543  * @param[in] context Pointer to the TLS context
1544  * @param[in] ticketEncryptCallback Ticket encryption callback function
1545  * @param[in] ticketDecryptCallback Ticket decryption callback function
1546  * @param[in] param An opaque pointer passed to the callback functions
1547  * @return Error code
1548  **/
1549 
1551  TlsTicketEncryptCallback ticketEncryptCallback,
1552  TlsTicketDecryptCallback ticketDecryptCallback, void *param)
1553 {
1554 #if (TLS_TICKET_SUPPORT == ENABLED)
1555  //Invalid TLS context?
1556  if(context == NULL)
1557  return ERROR_INVALID_PARAMETER;
1558 
1559  //Save ticket encryption/decryption callback functions
1560  context->ticketEncryptCallback = ticketEncryptCallback;
1561  context->ticketDecryptCallback = ticketDecryptCallback;
1562 
1563  //This opaque pointer will be directly passed to the callback functions
1564  context->ticketParam = param;
1565 
1566  //Successful processing
1567  return NO_ERROR;
1568 #else
1569  //Session ticket mechanism is not implemented
1570  return ERROR_NOT_IMPLEMENTED;
1571 #endif
1572 }
1573 
1574 
1575 /**
1576  * @brief Set PMTU value (for DTLS only)
1577  * @param[in] context Pointer to the TLS context
1578  * @param[in] pmtu PMTU value
1579  * @return Error code
1580  **/
1581 
1582 error_t tlsSetPmtu(TlsContext *context, size_t pmtu)
1583 {
1584 #if (DTLS_SUPPORT == ENABLED)
1585  //Invalid TLS context?
1586  if(context == NULL)
1587  return ERROR_INVALID_PARAMETER;
1588 
1589  //Make sure the PMTU value is acceptable
1590  if(pmtu < DTLS_MIN_PMTU)
1591  return ERROR_INVALID_PARAMETER;
1592 
1593  //Save PMTU value
1594  context->pmtu = pmtu;
1595 
1596  //Successful processing
1597  return NO_ERROR;
1598 #else
1599  //DTLS is not implemented
1600  return ERROR_NOT_IMPLEMENTED;
1601 #endif
1602 }
1603 
1604 
1605 /**
1606  * @brief Set timeout for blocking calls (for DTLS only)
1607  * @param[in] context Pointer to the TLS context
1608  * @param[in] timeout Maximum time to wait
1609  * @return Error code
1610  **/
1611 
1613 {
1614 #if (DTLS_SUPPORT == ENABLED)
1615  //Invalid TLS context?
1616  if(context == NULL)
1617  return ERROR_INVALID_PARAMETER;
1618 
1619  //Save timeout value
1620  context->timeout = timeout;
1621 
1622  //Successful processing
1623  return NO_ERROR;
1624 #else
1625  //DTLS is not implemented
1626  return ERROR_NOT_IMPLEMENTED;
1627 #endif
1628 }
1629 
1630 
1631 /**
1632  * @brief Set cookie generation/verification callbacks (for DTLS only)
1633  * @param[in] context Pointer to the TLS context
1634  * @param[in] cookieGenerateCallback Cookie generation callback function
1635  * @param[in] cookieVerifyCallback Cookie verification callback function
1636  * @param[in] param An opaque pointer passed to the callback functions
1637  * @return Error code
1638  **/
1639 
1641  DtlsCookieGenerateCallback cookieGenerateCallback,
1642  DtlsCookieVerifyCallback cookieVerifyCallback, void *param)
1643 {
1644 #if (DTLS_SUPPORT == ENABLED)
1645  //Invalid TLS context?
1646  if(context == NULL)
1647  return ERROR_INVALID_PARAMETER;
1648 
1649  //Check parameters
1650  if(cookieGenerateCallback == NULL || cookieVerifyCallback == NULL)
1651  return ERROR_INVALID_PARAMETER;
1652 
1653  //Save cookie generation/verification callback functions
1654  context->cookieGenerateCallback = cookieGenerateCallback;
1655  context->cookieVerifyCallback = cookieVerifyCallback;
1656 
1657  //This opaque pointer will be directly passed to the callback functions
1658  context->cookieParam = param;
1659 
1660  //Successful processing
1661  return NO_ERROR;
1662 #else
1663  //DTLS is not implemented
1664  return ERROR_NOT_IMPLEMENTED;
1665 #endif
1666 }
1667 
1668 
1669 /**
1670  * @brief Enable anti-replay mechanism (for DTLS only)
1671  * @param[in] context Pointer to the TLS context
1672  * @param[in] enabled Specifies whether anti-replay protection is enabled
1673  * @return Error code
1674  **/
1675 
1677 {
1678 #if (DTLS_SUPPORT == ENABLED && DTLS_REPLAY_DETECTION_SUPPORT == ENABLED)
1679  //Invalid TLS context?
1680  if(context == NULL)
1681  return ERROR_INVALID_PARAMETER;
1682 
1683  //Enable or disable anti-replay mechanism
1684  context->replayDetectionEnabled = enabled;
1685 
1686  //Successful processing
1687  return NO_ERROR;
1688 #else
1689  //Anti-replay mechanism is not implemented
1690  return ERROR_NOT_IMPLEMENTED;
1691 #endif
1692 }
1693 
1694 
1695 /**
1696  * @brief Send the maximum amount of 0-RTT data the server can accept
1697  * @param[in] context Pointer to the TLS context
1698  * @param[in] maxEarlyDataSize Maximum amount of 0-RTT data that the client
1699  * is allowed to send
1700  * @return Error code
1701  **/
1702 
1703 
1704 error_t tlsSetMaxEarlyDataSize(TlsContext *context, size_t maxEarlyDataSize)
1705 {
1706 #if (TLS_MAX_VERSION >= TLS_VERSION_1_3 && TLS_MIN_VERSION <= TLS_VERSION_1_3)
1707  //Invalid TLS context?
1708  if(context == NULL)
1709  return ERROR_INVALID_PARAMETER;
1710 
1711  //Save the maximum amount of 0-RTT data that the client is allowed to send
1712  context->maxEarlyDataSize = maxEarlyDataSize;
1713 
1714  //Successful processing
1715  return NO_ERROR;
1716 #else
1717  //Not implemented
1718  return ERROR_NOT_IMPLEMENTED;
1719 #endif
1720 }
1721 
1722 
1723 /**
1724  * @brief Send early data to the remote TLS server
1725  * @param[in] context Pointer to the TLS context
1726  * @param[in] data Pointer to a buffer containing the data to be transmitted
1727  * @param[in] length Number of bytes to be transmitted
1728  * @param[out] written Actual number of bytes written (optional parameter)
1729  * @param[in] flags Set of flags that influences the behavior of this function
1730  * @return Error code
1731  **/
1732 
1734  size_t length, size_t *written, uint_t flags)
1735 {
1736 #if (TLS_MAX_VERSION >= TLS_VERSION_1_3 && TLS_MIN_VERSION <= TLS_VERSION_1_3 && \
1737  TLS_CLIENT_SUPPORT == ENABLED && TLS13_EARLY_DATA_SUPPORT == ENABLED)
1738  size_t n;
1739  error_t error;
1740 
1741  //Invalid TLS context?
1742  if(context == NULL)
1743  return ERROR_INVALID_PARAMETER;
1744 
1745  //Check parameters
1746  if(data == NULL && length != 0)
1747  return ERROR_INVALID_PARAMETER;
1748 
1749  //Check operation mode
1750  if(context->entity != TLS_CONNECTION_END_CLIENT)
1751  return ERROR_FAILURE;
1752 
1753  //Make sure TLS 1.3 is supported by the client
1754  if(context->versionMax < TLS_VERSION_1_3)
1755  return ERROR_FAILURE;
1756 
1757  //Check transport protocol
1758  if(context->transportProtocol != TLS_TRANSPORT_PROTOCOL_STREAM)
1759  return ERROR_FAILURE;
1760 
1761  //Ensure the send/receive functions are properly registered
1762  if(context->socketSendCallback == NULL || context->socketReceiveCallback == NULL)
1763  return ERROR_NOT_CONFIGURED;
1764 
1765  //Verify that the PRNG is properly set
1766  if(context->prngAlgo == NULL || context->prngContext == NULL)
1767  return ERROR_NOT_CONFIGURED;
1768 
1769 #if (DTLS_SUPPORT == ENABLED)
1770  //Save current time
1771  context->startTime = osGetSystemTime();
1772 #endif
1773 
1774  //Send 0-RTT data
1775  error = tls13SendEarlyData(context, data, length, &n);
1776 
1777  //Total number of data that have been written
1778  if(written != NULL)
1779  {
1780  *written = n;
1781  }
1782 
1783  //Return status code
1784  return error;
1785 #else
1786  //Not implemented
1787  return ERROR_NOT_IMPLEMENTED;
1788 #endif
1789 }
1790 
1791 
1792 /**
1793  * @brief Initiate the TLS handshake
1794  * @param[in] context Pointer to the TLS context
1795  * @return Error code
1796  **/
1797 
1799 {
1800  error_t error;
1801 
1802  //Invalid TLS context?
1803  if(context == NULL)
1804  return ERROR_INVALID_PARAMETER;
1805 
1806  //Ensure the send/receive functions are properly registered
1807  if(context->socketSendCallback == NULL || context->socketReceiveCallback == NULL)
1808  return ERROR_NOT_CONFIGURED;
1809 
1810  //Verify that the PRNG is properly set
1811  if(context->prngAlgo == NULL || context->prngContext == NULL)
1812  return ERROR_NOT_CONFIGURED;
1813 
1814 #if (DTLS_SUPPORT == ENABLED)
1815  //Save current time
1816  context->startTime = osGetSystemTime();
1817 #endif
1818 
1819 #if (TLS_MAX_VERSION >= TLS_VERSION_1_3 && TLS_MIN_VERSION <= TLS_VERSION_1_3 && \
1820  TLS_CLIENT_SUPPORT == ENABLED && TLS13_EARLY_DATA_SUPPORT == ENABLED)
1821  //Any 0-RTT data sent by the client?
1822  if(context->entity == TLS_CONNECTION_END_CLIENT &&
1823  context->state == TLS_STATE_EARLY_DATA)
1824  {
1825  //Save current sequence number
1826  context->earlyDataSeqNum = context->encryptionEngine.seqNum;
1827  //Wait for a ServerHello message
1829  }
1830 #endif
1831 
1832  //Perform TLS handshake
1833  error = tlsPerformHandshake(context);
1834  //Return status code
1835  return error;
1836 }
1837 
1838 
1839 /**
1840  * @brief Check whether the server has accepted or rejected the early data
1841  * @param[in] context Pointer to the TLS context
1842  * @return TLS_EARLY_DATA_ACCEPTED if the early data was accepted, else
1843  * TLS_EARLY_DATA_REJECT if the early data was rejected
1844  **/
1845 
1847 {
1848  TlsEarlyDataStatus status;
1849 
1850  //Initialize early data status
1851  status = TLS_EARLY_DATA_REJECTED;
1852 
1853 #if (TLS_MAX_VERSION >= TLS_VERSION_1_3 && TLS_MIN_VERSION <= TLS_VERSION_1_3 && \
1854  TLS_CLIENT_SUPPORT == ENABLED && TLS13_EARLY_DATA_SUPPORT == ENABLED)
1855  //Make sure the TLS context is valid
1856  if(context != NULL)
1857  {
1858  //Client mode?
1859  if(context->entity == TLS_CONNECTION_END_CLIENT)
1860  {
1861  //Any 0-RTT data sent by the client?
1862  if(context->earlyDataEnabled)
1863  {
1864  //Check whether the server has accepted or rejected the early data
1865  if(context->earlyDataExtReceived && !context->earlyDataRejected)
1866  {
1867  status = TLS_EARLY_DATA_ACCEPTED;
1868  }
1869  }
1870  }
1871  }
1872 #endif
1873 
1874  //Return early data status
1875  return status;
1876 }
1877 
1878 
1879 /**
1880  * @brief Export keying material per RFC 5705 standard
1881  * @param[in] context Pointer to the TLS context
1882  * @param[in] label Identifying label (NULL-terminated string)
1883  * @param[in] useContextValue Specifies whether upper-layer context should
1884  * be used when exporting keying material
1885  * @param[in] contextValue Pointer to the upper-layer context
1886  * @param[in] contextValueLen Length of the upper-layer context
1887  * @param[out] output Buffer where to store the keying material
1888  * @param[in] outputLen Desired output length
1889  * @return Error code
1890  **/
1891 
1893  bool_t useContextValue, const uint8_t *contextValue,
1894  size_t contextValueLen, uint8_t *output, size_t outputLen)
1895 {
1896  error_t error;
1897  size_t n;
1898  uint8_t *seed;
1899 
1900  //Invalid TLS context?
1901  if(context == NULL)
1902  return ERROR_INVALID_PARAMETER;
1903 
1904  //Check parameters
1905  if(label == NULL || output == NULL)
1906  return ERROR_INVALID_PARAMETER;
1907 
1908  //Make sure the upper-layer context is valid
1909  if(contextValue == NULL && contextValueLen != 0)
1910  return ERROR_INVALID_PARAMETER;
1911 
1912  //Calculate the length of the seed
1913  n = 2 * TLS_RANDOM_SIZE;
1914 
1915  //Check whether a context is provided
1916  if(useContextValue)
1917  {
1918  n += contextValueLen + 2;
1919  }
1920 
1921  //Allocate a memory buffer to hold the seed
1922  seed = tlsAllocMem(n);
1923  //Failed to allocate memory?
1924  if(seed == NULL)
1925  return ERROR_OUT_OF_RESOURCES;
1926 
1927  //Concatenate client_random and server_random values
1928  osMemcpy(seed, context->clientRandom, TLS_RANDOM_SIZE);
1929  osMemcpy(seed + 32, context->serverRandom, TLS_RANDOM_SIZE);
1930 
1931  //Check whether a context is provided
1932  if(useContextValue)
1933  {
1934  //The context_value_length is encoded as an unsigned, 16-bit quantity
1935  //representing the length of the context value
1936  STORE16BE(contextValueLen, seed + 64);
1937 
1938  //Copy the context value provided by the application using the exporter
1939  osMemcpy(seed + 66, contextValue, contextValueLen);
1940  }
1941 
1942 #if (TLS_MAX_VERSION >= TLS_VERSION_1_0 && TLS_MIN_VERSION <= TLS_VERSION_1_1)
1943  //TLS 1.0 or TLS 1.1 currently selected?
1944  if(context->version == TLS_VERSION_1_0 || context->version == TLS_VERSION_1_1)
1945  {
1946  //TLS 1.0 and 1.1 use a PRF that combines MD5 and SHA-1
1947  error = tlsPrf(context->masterSecret, TLS_MASTER_SECRET_SIZE,
1948  label, seed, n, output, outputLen);
1949  }
1950  else
1951 #endif
1952 #if (TLS_MAX_VERSION >= TLS_VERSION_1_2 && TLS_MIN_VERSION <= TLS_VERSION_1_2)
1953  //TLS 1.2 currently selected?
1954  if(context->version == TLS_VERSION_1_2)
1955  {
1956  //Make sure the PRF hash algorithm is valid
1957  if(context->cipherSuite.prfHashAlgo != NULL)
1958  {
1959  //TLS 1.2 PRF uses SHA-256 or a stronger hash algorithm as the core
1960  //function in its construction
1961  error = tls12Prf(context->cipherSuite.prfHashAlgo, context->masterSecret,
1962  TLS_MASTER_SECRET_SIZE, label, seed, n, output, outputLen);
1963  }
1964  else
1965  {
1966  //Invalid PRF hash algorithm
1967  error = ERROR_FAILURE;
1968  }
1969  }
1970  else
1971 #endif
1972 #if (TLS_MAX_VERSION >= TLS_VERSION_1_3 && TLS_MIN_VERSION <= TLS_VERSION_1_3)
1973  //TLS 1.3 currently selected?
1974  if(context->version == TLS_VERSION_1_3)
1975  {
1976  const HashAlgo *hash;
1978  uint8_t digest[TLS_MAX_HKDF_DIGEST_SIZE];
1979 
1980  //The hash function used by HKDF is the cipher suite hash algorithm
1981  hash = context->cipherSuite.prfHashAlgo;
1982 
1983  //Make sure the HKDF hash algorithm is valid
1984  if(hash != NULL)
1985  {
1986  //Derive exporter master secret
1987  error = tls13DeriveSecret(context, context->exporterMasterSecret,
1988  hash->digestSize, label, "", 0, secret, hash->digestSize);
1989 
1990  //Check status code
1991  if(!error)
1992  {
1993  //Hash context_value input
1994  error = hash->compute(contextValue, contextValueLen, digest);
1995  }
1996 
1997  //Check status code
1998  if(!error)
1999  {
2000  //Export keying material
2001  error = tls13HkdfExpandLabel(context->transportProtocol, hash,
2002  secret, hash->digestSize, "exporter", digest, hash->digestSize,
2003  output, outputLen);
2004  }
2005  }
2006  else
2007  {
2008  //Invalid HKDF hash algorithm
2009  error = ERROR_FAILURE;
2010  }
2011  }
2012  else
2013 #endif
2014  //Invalid TLS version?
2015  {
2016  //Report an error
2017  error = ERROR_INVALID_VERSION;
2018  }
2019 
2020  //Release previously allocated memory
2021  tlsFreeMem(seed);
2022 
2023  //Return status code
2024  return error;
2025 }
2026 
2027 
2028 /**
2029  * @brief Export channel binding value
2030  * @param[in] context Pointer to the TLS context
2031  * @param[in] type Channel binding type
2032  * @param[out] output Buffer where to store the channel binding value
2033  * @param[out] length Length of the channel binding value, in bytes
2034  * @return Error code
2035  **/
2036 
2038  uint8_t *output, size_t *length)
2039 {
2040  error_t error;
2041 
2042  //Check parameters
2043  if(context == NULL || type == NULL || length == 0)
2044  return ERROR_INVALID_PARAMETER;
2045 
2046  //Initialize status code
2047  error = NO_ERROR;
2048 
2049  //Check channel binding type
2050  if(osStrcmp(type, "tls-unique") == 0)
2051  {
2052  //Check TLS version
2053  if(context->version <= TLS_VERSION_1_2)
2054  {
2055  //The "tls-unique" channel binding value is the first TLS Finished
2056  //message sent in the most recent TLS handshake of the TLS connection
2057  //being bound to (refer to RFC 5929, section 3.1)
2058  if(context->resume)
2059  {
2060  //For abbreviated TLS handshakes (session resumption), the first
2061  //Finished message is sent by the server
2062  if(output != NULL)
2063  {
2064  osMemcpy(output, context->serverVerifyData,
2065  context->serverVerifyDataLen);
2066  }
2067 
2068  //Length of the channel binding value
2069  *length = context->clientVerifyDataLen;
2070  }
2071  else
2072  {
2073  //For full TLS handshakes, the first Finished message is sent by
2074  //the client
2075  if(output != NULL)
2076  {
2077  osMemcpy(output, context->clientVerifyData,
2078  context->clientVerifyDataLen);
2079  }
2080 
2081  //Length of the channel binding value
2082  *length = context->clientVerifyDataLen;
2083  }
2084  }
2085  else
2086  {
2087  //Appendix C.5 of RFC 8446 notes the lack of channel bindings for
2088  //TLS 1.3 (refer to to RFC 9266, section 1)
2089  }
2090  }
2091  else if(osStrcmp(type, "tls-exporter") == 0)
2092  {
2093  //The "tls-exporter" channel binding type uses Exported Keying Material
2094  //(EKM), which is already widely exposed by TLS implementations (refer
2095  //to RFC 9266, section 2)
2096  error = tlsExportKeyingMaterial(context, "EXPORTER-Channel-Binding",
2097  TRUE, NULL, 0, output, 32);
2098 
2099  //Check status code
2100  if(!error)
2101  {
2102  //The derived value consists of 32 bytes
2103  *length = 32;
2104  }
2105  }
2106  else
2107  {
2108  //Report an error
2109  error = ERROR_INVALID_TYPE;
2110  }
2111 
2112  //Return status code
2113  return error;
2114 }
2115 
2116 
2117 /**
2118  * @brief Send application data to the remote host using TLS
2119  * @param[in] context Pointer to the TLS context
2120  * @param[in] data Pointer to a buffer containing the data to be transmitted
2121  * @param[in] length Number of bytes to be transmitted
2122  * @param[out] written Actual number of bytes written (optional parameter)
2123  * @param[in] flags Set of flags that influences the behavior of this function
2124  * @return Error code
2125  **/
2126 
2127 error_t tlsWrite(TlsContext *context, const void *data, size_t length,
2128  size_t *written, uint_t flags)
2129 {
2130  error_t error;
2131  size_t n;
2132  size_t totalLength;
2133 
2134  //Invalid TLS context?
2135  if(context == NULL)
2136  return ERROR_INVALID_PARAMETER;
2137 
2138  //Check parameters
2139  if(data == NULL && length != 0)
2140  return ERROR_INVALID_PARAMETER;
2141 
2142  //Ensure the send/receive functions are properly registered
2143  if(context->socketSendCallback == NULL || context->socketReceiveCallback == NULL)
2144  return ERROR_NOT_CONFIGURED;
2145 
2146 #if (DTLS_SUPPORT == ENABLED)
2147  //Save current time
2148  context->startTime = osGetSystemTime();
2149 #endif
2150 
2151  //Initialize status code
2152  error = NO_ERROR;
2153 
2154  //Actual number of bytes written
2155  totalLength = 0;
2156 
2157  //Send as much data as possible
2158  while(totalLength < length)
2159  {
2160  //Check current state
2161  if(context->state < TLS_STATE_APPLICATION_DATA)
2162  {
2163  //Perform TLS handshake
2164  error = tlsConnect(context);
2165  }
2166  else if(context->state == TLS_STATE_APPLICATION_DATA)
2167  {
2168 #if (DTLS_SUPPORT == ENABLED)
2169  //DTLS protocol?
2170  if(context->transportProtocol == TLS_TRANSPORT_PROTOCOL_DATAGRAM)
2171  {
2172  //Length of the payload data
2173  n = length;
2174 
2175  //Send a datagram
2176  error = dtlsWriteProtocolData(context, data, n,
2178  }
2179  else
2180 #endif
2181  //TLS protocol?
2182  {
2183  //Calculate the number of bytes to write at a time
2184  n = MIN(length - totalLength, context->txBufferMaxLen);
2185  //The record length must not exceed 16384 bytes
2187 
2188 #if (TLS_MAX_FRAG_LEN_SUPPORT == ENABLED)
2189  //Do not exceed the negotiated maximum fragment length
2190  n = MIN(n, context->maxFragLen);
2191 #endif
2192 
2193 #if (TLS_RECORD_SIZE_LIMIT_SUPPORT == ENABLED)
2194  //Maximum record size the peer is willing to receive
2195  n = MIN(n, context->recordSizeLimit);
2196 #endif
2197 
2198 #if (TLS_MAX_VERSION >= TLS_VERSION_1_0 && TLS_MIN_VERSION <= TLS_VERSION_1_0)
2199  //The 1/n-1 record splitting technique is a workaround for the
2200  //BEAST attack
2201  if(context->version <= TLS_VERSION_1_0 &&
2202  context->cipherSuite.cipherMode == CIPHER_MODE_CBC &&
2203  context->txLastRecordLen != 1 &&
2204  totalLength == 0)
2205  {
2206  n = 1;
2207  }
2208 #endif
2209  //Send application data
2210  error = tlsWriteProtocolData(context, data, n,
2212  }
2213 
2214  //Check status code
2215  if(!error)
2216  {
2217 #if (TLS_MAX_VERSION >= TLS_VERSION_1_0 && TLS_MIN_VERSION <= TLS_VERSION_1_0)
2218  //Save the length of the TLS record
2219  context->txLastRecordLen = n;
2220 #endif
2221  //Advance data pointer
2222  data = (uint8_t *) data + n;
2223  //Update byte counter
2224  totalLength += n;
2225  }
2226  else
2227  {
2228  //Send an alert message to the peer, if applicable
2229  tlsProcessError(context, error);
2230  }
2231  }
2232  else
2233  {
2234  //The connection has not yet been established
2235  error = ERROR_NOT_CONNECTED;
2236  }
2237 
2238  //Any error to report?
2239  if(error)
2240  break;
2241  }
2242 
2243  //Total number of data that have been written
2244  if(written != NULL)
2245  {
2246  *written = totalLength;
2247  }
2248 
2249  //Return status code
2250  return error;
2251 }
2252 
2253 
2254 /**
2255  * @brief Receive application data from a the remote host using TLS
2256  * @param[in] context Pointer to the TLS context
2257  * @param[out] data Buffer into which received data will be placed
2258  * @param[in] size Maximum number of bytes that can be received
2259  * @param[out] received Number of bytes that have been received
2260  * @param[in] flags Set of flags that influences the behavior of this function
2261  * @return Error code
2262  **/
2263 
2264 error_t tlsRead(TlsContext *context, void *data, size_t size, size_t *received,
2265  uint_t flags)
2266 {
2267  error_t error;
2268  size_t i;
2269  size_t n;
2270  uint8_t *p;
2271  TlsContentType contentType;
2272 
2273  //Invalid TLS context?
2274  if(context == NULL)
2275  return ERROR_INVALID_PARAMETER;
2276 
2277  //Check parameters
2278  if(data == NULL || received == NULL)
2279  return ERROR_INVALID_PARAMETER;
2280 
2281  //Ensure the send/receive functions are properly registered
2282  if(context->socketSendCallback == NULL || context->socketReceiveCallback == NULL)
2283  return ERROR_NOT_CONFIGURED;
2284 
2285 #if (DTLS_SUPPORT == ENABLED)
2286  //Save current time
2287  context->startTime = osGetSystemTime();
2288 #endif
2289 
2290  //Initialize status code
2291  error = NO_ERROR;
2292 
2293  //No data has been read yet
2294  *received = 0;
2295 
2296  //Read as much data as possible
2297  while(*received < size)
2298  {
2299  //Check current state
2300  if(context->state < TLS_STATE_APPLICATION_DATA)
2301  {
2302  //Perform TLS handshake
2303  error = tlsConnect(context);
2304  }
2305  else if(context->state == TLS_STATE_APPLICATION_DATA)
2306  {
2307 #if (DTLS_SUPPORT == ENABLED)
2308  //DTLS protocol?
2309  if(context->transportProtocol == TLS_TRANSPORT_PROTOCOL_DATAGRAM)
2310  {
2311  //Receive a datagram
2312  error = dtlsReadProtocolData(context, &p, &n, &contentType);
2313  }
2314  else
2315 #endif
2316  //TLS protocol?
2317  {
2318  //The record layer receives uninterpreted data from higher layers
2319  error = tlsReadProtocolData(context, &p, &n, &contentType);
2320  }
2321 
2322  //Check status code
2323  if(!error)
2324  {
2325  //Application data received?
2326  if(contentType == TLS_TYPE_APPLICATION_DATA)
2327  {
2328 #if (DTLS_SUPPORT == ENABLED)
2329  //DTLS protocol?
2330  if(context->transportProtocol == TLS_TRANSPORT_PROTOCOL_DATAGRAM)
2331  {
2332  //Make sure the user buffer is large enough to hold the whole
2333  //datagram
2334  if(n > size)
2335  {
2336  //Report an error
2337  error = ERROR_BUFFER_OVERFLOW;
2338  }
2339  else
2340  {
2341  //Copy data to user buffer
2342  osMemcpy(data, p, n);
2343  //Total number of data that have been read
2344  *received = n;
2345  }
2346 
2347  //If the TLS_FLAG_PEEK flag is set, the data is copied into
2348  //the buffer but is not removed from the receive queue
2349  if((flags & TLS_FLAG_PEEK) == 0)
2350  {
2351  //Flush receive buffer
2352  context->rxBufferPos = 0;
2353  context->rxBufferLen = 0;
2354  }
2355 
2356  //We are done
2357  break;
2358  }
2359  else
2360 #endif
2361  //TLS protocol?
2362  {
2363  //Limit the number of bytes to read at a time
2364  n = MIN(n, size - *received);
2365 
2366  //The TLS_FLAG_BREAK_CHAR flag causes the function to stop reading
2367  //data as soon as the specified break character is encountered
2368  if((flags & TLS_FLAG_BREAK_CHAR) != 0)
2369  {
2370  //Retrieve the break character code
2371  char_t c = LSB(flags);
2372 
2373  //Search for the specified break character
2374  for(i = 0; i < n && p[i] != c; i++)
2375  {
2376  }
2377 
2378  //Adjust the number of data to read
2379  n = MIN(n, i + 1);
2380 
2381  //Copy data to user buffer
2382  osMemcpy(data, p, n);
2383  //Total number of data that have been read
2384  *received += n;
2385 
2386  //Advance data pointer
2387  context->rxBufferPos += n;
2388  //Number of bytes still pending in the receive buffer
2389  context->rxBufferLen -= n;
2390 
2391  //Check whether a break character has been found
2392  if(n > 0 && p[n - 1] == c)
2393  break;
2394  }
2395  else
2396  {
2397  //Copy data to user buffer
2398  osMemcpy(data, p, n);
2399  //Total number of data that have been read
2400  *received += n;
2401 
2402  //Advance data pointer
2403  context->rxBufferPos += n;
2404  //Number of bytes still pending in the receive buffer
2405  context->rxBufferLen -= n;
2406 
2407  //The TLS_FLAG_WAIT_ALL flag causes the function to return
2408  //only when the requested number of bytes have been read
2409  if((flags & TLS_FLAG_WAIT_ALL) == 0)
2410  break;
2411  }
2412 
2413  //Advance data pointer
2414  data = (uint8_t *) data + n;
2415  }
2416  }
2417  //Handshake message received?
2418  else if(contentType == TLS_TYPE_HANDSHAKE)
2419  {
2420  //Advance data pointer
2421  context->rxBufferPos += n;
2422  //Number of bytes still pending in the receive buffer
2423  context->rxBufferLen -= n;
2424 
2425  //Parse handshake message
2426  error = tlsParseHandshakeMessage(context, p, n);
2427  }
2428  //Alert message received?
2429  else if(contentType == TLS_TYPE_ALERT)
2430  {
2431  //Advance data pointer
2432  context->rxBufferPos += n;
2433  //Number of bytes still pending in the receive buffer
2434  context->rxBufferLen -= n;
2435 
2436  //Parse Alert message
2437  error = tlsParseAlert(context, (TlsAlert *) p, n);
2438  }
2439  //An inappropriate message was received?
2440  else
2441  {
2442  //Report an error
2443  error = ERROR_UNEXPECTED_MESSAGE;
2444  }
2445  }
2446 
2447  //Any error to report?
2448  if(error)
2449  {
2450  //Send an alert message to the peer, if applicable
2451  tlsProcessError(context, error);
2452  }
2453  }
2454  else if(context->state == TLS_STATE_CLOSING ||
2455  context->state == TLS_STATE_CLOSED)
2456  {
2457  //Check whether a fatal alert message has been sent or received
2458  if(context->fatalAlertSent || context->fatalAlertReceived)
2459  {
2460  //Alert messages with a level of fatal result in the immediate
2461  //termination of the connection
2462  error = ERROR_FAILURE;
2463  }
2464  else
2465  {
2466  //The user must be satisfied with data already on hand
2467  if(*received > 0)
2468  {
2469  //Some data are pending in the receive buffer
2470  error = NO_ERROR;
2471  break;
2472  }
2473  else
2474  {
2475  //The receive buffer is empty
2476  error = ERROR_END_OF_STREAM;
2477  }
2478  }
2479  }
2480  else
2481  {
2482  //The connection has not yet been established
2483  error = ERROR_NOT_CONNECTED;
2484  }
2485 
2486  //Any error to report?
2487  if(error)
2488  break;
2489  }
2490 
2491  //Return status code
2492  return error;
2493 }
2494 
2495 
2496 /**
2497  * @brief Check whether some data is ready for transmission
2498  * @param[in] context Pointer to the TLS context
2499  * @return The function returns TRUE if some data is ready for transmission.
2500  * Otherwise, FALSE is returned
2501  **/
2502 
2504 {
2505  bool_t ready;
2506 
2507  //Initialize flag
2508  ready = FALSE;
2509 
2510  //Make sure the TLS context is valid
2511  if(context != NULL)
2512  {
2513  //TLS protocol?
2514  if(context->transportProtocol == TLS_TRANSPORT_PROTOCOL_STREAM ||
2515  context->transportProtocol == TLS_TRANSPORT_PROTOCOL_EAP)
2516  {
2517  //Check whether some data is pending in the transmit buffer
2518  if(context->txBufferPos < context->txBufferLen)
2519  {
2520  ready = TRUE;
2521  }
2522  }
2523  }
2524 
2525  //The function returns TRUE if some data is ready for transmission
2526  return ready;
2527 }
2528 
2529 
2530 /**
2531  * @brief Check whether some data is available in the receive buffer
2532  * @param[in] context Pointer to the TLS context
2533  * @return The function returns TRUE if some data is pending and can be read
2534  * immediately without blocking. Otherwise, FALSE is returned
2535  **/
2536 
2538 {
2539  bool_t ready;
2540 
2541  //Initialize flag
2542  ready = FALSE;
2543 
2544  //Make sure the TLS context is valid
2545  if(context != NULL)
2546  {
2547 #if (DTLS_SUPPORT == ENABLED)
2548  //DTLS protocol?
2549  if(context->transportProtocol == TLS_TRANSPORT_PROTOCOL_DATAGRAM)
2550  {
2551  //Check whether a datagram is pending in the receive buffer
2552  if(context->rxBufferLen > 0 ||
2553  context->rxRecordLen > 0 ||
2554  context->rxDatagramLen > 0)
2555  {
2556  ready = TRUE;
2557  }
2558  }
2559  else
2560 #endif
2561  //TLS protocol?
2562  {
2563  //Check whether some data is pending in the receive buffer
2564  if(context->rxBufferLen > 0)
2565  {
2566  ready = TRUE;
2567  }
2568  }
2569  }
2570 
2571  //The function returns TRUE if some data can be read immediately
2572  //without blocking
2573  return ready;
2574 }
2575 
2576 
2577 /**
2578  * @brief Gracefully close TLS session
2579  * @param[in] context Pointer to the TLS context
2580  **/
2581 
2583 {
2584  //Either party may initiate a close by sending a close_notify alert
2585  return tlsShutdownEx(context, FALSE);
2586 }
2587 
2588 
2589 /**
2590  * @brief Gracefully close TLS session
2591  * @param[in] context Pointer to the TLS context
2592  * @param[in] waitForCloseNotify Wait for the close notify alert from the peer
2593  **/
2594 
2595 error_t tlsShutdownEx(TlsContext *context, bool_t waitForCloseNotify)
2596 {
2597  error_t error;
2598  size_t n;
2599  uint8_t *p;
2600  TlsContentType contentType;
2601 
2602  //Invalid TLS context?
2603  if(context == NULL)
2604  return ERROR_INVALID_PARAMETER;
2605 
2606  //Ensure the send/receive functions are properly registered
2607  if(context->socketSendCallback == NULL || context->socketReceiveCallback == NULL)
2608  return ERROR_NOT_CONFIGURED;
2609 
2610 #if (DTLS_SUPPORT == ENABLED)
2611  //Save current time
2612  context->startTime = osGetSystemTime();
2613 #endif
2614 
2615  //Initialize status code
2616  error = NO_ERROR;
2617 
2618  //Wait for the TLS session to be closed
2619  while(context->state != TLS_STATE_CLOSED)
2620  {
2621  //Check current state
2622  if(context->state == TLS_STATE_APPLICATION_DATA)
2623  {
2624  //TLS protocol?
2625  if(context->transportProtocol == TLS_TRANSPORT_PROTOCOL_STREAM ||
2626  context->transportProtocol == TLS_TRANSPORT_PROTOCOL_EAP)
2627  {
2628  //Flush send buffer
2629  error = tlsWriteProtocolData(context, NULL, 0, TLS_TYPE_NONE);
2630  }
2631 
2632  //Check status code
2633  if(!error)
2634  {
2635  //Either party may initiate a close by sending a close_notify alert
2637  }
2638  }
2639  else if(context->state == TLS_STATE_CLOSING)
2640  {
2641  //TLS protocol?
2642  if(context->transportProtocol == TLS_TRANSPORT_PROTOCOL_STREAM ||
2643  context->transportProtocol == TLS_TRANSPORT_PROTOCOL_EAP)
2644  {
2645  //Flush send buffer
2646  error = tlsWriteProtocolData(context, NULL, 0, TLS_TYPE_NONE);
2647  }
2648 
2649  //Check status code
2650  if(!error)
2651  {
2652  //Unless some other fatal alert has been transmitted, each party
2653  //is required to send a close_notify alert before closing the
2654  //write side of the connection
2655  if(context->fatalAlertSent || context->fatalAlertReceived)
2656  {
2657  //Close the connection immediately
2658  tlsChangeState(context, TLS_STATE_CLOSED);
2659  }
2660  else if(!context->closeNotifySent)
2661  {
2662  //Notifies the recipient that the sender will not send any
2663  //more messages on this connection
2664  error = tlsSendAlert(context, TLS_ALERT_LEVEL_WARNING,
2666  }
2667  else if(!context->closeNotifyReceived && waitForCloseNotify)
2668  {
2669 #if (DTLS_SUPPORT == ENABLED)
2670  //DTLS protocol?
2671  if(context->transportProtocol == TLS_TRANSPORT_PROTOCOL_DATAGRAM)
2672  {
2673  //Wait for the responding close_notify alert
2674  error = dtlsReadProtocolData(context, &p, &n, &contentType);
2675  }
2676  else
2677 #endif
2678  //TLS protocol?
2679  {
2680  //Wait for the responding close_notify alert
2681  error = tlsReadProtocolData(context, &p, &n, &contentType);
2682  }
2683 
2684  //Check status code
2685  if(!error)
2686  {
2687  //Advance data pointer
2688  context->rxBufferPos += n;
2689  //Number of bytes still pending in the receive buffer
2690  context->rxBufferLen -= n;
2691 
2692  //Application data received?
2693  if(contentType == TLS_TYPE_APPLICATION_DATA)
2694  {
2695  //Discard application data
2696  }
2697  //Alert message received?
2698  else if(contentType == TLS_TYPE_ALERT)
2699  {
2700  //Parse Alert message
2701  error = tlsParseAlert(context, (TlsAlert *) p, n);
2702  }
2703  else if(contentType == TLS_TYPE_HANDSHAKE)
2704  {
2705  //Parse handshake message
2706  error = tlsParseHandshakeMessage(context, p, n);
2707  }
2708  //An inappropriate message was received?
2709  else
2710  {
2711  //Report an error
2712  error = ERROR_UNEXPECTED_MESSAGE;
2713  }
2714  }
2715  }
2716  else
2717  {
2718  //The connection is closed
2719  tlsChangeState(context, TLS_STATE_CLOSED);
2720  }
2721  }
2722  }
2723  else
2724  {
2725  //Report an error
2726  error = ERROR_NOT_CONNECTED;
2727  }
2728 
2729  //Any error to report?
2730  if(error)
2731  break;
2732  }
2733 
2734  //Return status code
2735  return error;
2736 }
2737 
2738 
2739 /**
2740  * @brief Release TLS context
2741  * @param[in] context Pointer to the TLS context
2742  **/
2743 
2744 void tlsFree(TlsContext *context)
2745 {
2746  //Valid TLS context?
2747  if(context != NULL)
2748  {
2749  //Release server name
2750  if(context->serverName != NULL)
2751  {
2752  tlsFreeMem(context->serverName);
2753  }
2754 
2755  //Release cookie
2756  if(context->cookie != NULL)
2757  {
2758  osMemset(context->cookie, 0, context->cookieLen);
2759  tlsFreeMem(context->cookie);
2760  }
2761 
2762  //Release send buffer
2763  if(context->txBuffer != NULL)
2764  {
2765  osMemset(context->txBuffer, 0, context->txBufferSize);
2766  tlsFreeMem(context->txBuffer);
2767  }
2768 
2769  //Release receive buffer
2770  if(context->rxBuffer != NULL)
2771  {
2772  osMemset(context->rxBuffer, 0, context->rxBufferSize);
2773  tlsFreeMem(context->rxBuffer);
2774  }
2775 
2776  //Release transcript hash context
2777  tlsFreeTranscriptHash(context);
2778 
2779  //Release session ticket
2780  if(context->ticket != NULL)
2781  {
2782  osMemset(context->ticket, 0, context->ticketLen);
2783  tlsFreeMem(context->ticket);
2784  }
2785 
2786 #if (TLS_MAX_VERSION >= TLS_VERSION_1_3 && TLS_MIN_VERSION <= TLS_VERSION_1_3)
2787  //Release the ALPN protocol associated with the ticket
2788  if(context->ticketAlpn != NULL)
2789  {
2790  tlsFreeMem(context->ticketAlpn);
2791  }
2792 #endif
2793 
2794 #if (TLS_DH_SUPPORT == ENABLED)
2795  //Release Diffie-Hellman context
2796  dhFree(&context->dhContext);
2797 #endif
2798 
2799 #if (TLS_ECDH_SUPPORT == ENABLED || TLS_HYBRID_SUPPORT == ENABLED)
2800  //Release ECDH context
2801  ecdhFree(&context->ecdhContext);
2802 #endif
2803 
2804 #if (TLS_MLKEM_SUPPORT == ENABLED || TLS_HYBRID_SUPPORT == ENABLED)
2805  //Release KEM context
2806  kemFree(&context->kemContext);
2807 #endif
2808 
2809 #if (TLS_RSA_SUPPORT == ENABLED)
2810  //Release peer's RSA public key
2811  rsaFreePublicKey(&context->peerRsaPublicKey);
2812 #endif
2813 
2814 #if (TLS_DSA_SIGN_SUPPORT == ENABLED)
2815  //Release peer's DSA public key
2816  dsaFreePublicKey(&context->peerDsaPublicKey);
2817 #endif
2818 
2819 #if (TLS_ECDSA_SIGN_SUPPORT == ENABLED || TLS_SM2_SIGN_SUPPORT == ENABLED)
2820  //Release peer's EC public key
2821  ecFreePublicKey(&context->peerEcPublicKey);
2822 #endif
2823 
2824 #if (TLS_ED25519_SIGN_SUPPORT == ENABLED || TLS_ED448_SIGN_SUPPORT == ENABLED)
2825  //Release peer's EdDSA public key
2826  eddsaFreePublicKey(&context->peerEddsaPublicKey);
2827 #endif
2828 
2829 #if (TLS_PSK_SUPPORT == ENABLED)
2830  //Release the pre-shared key
2831  if(context->psk != NULL)
2832  {
2833  osMemset(context->psk, 0, context->pskLen);
2834  tlsFreeMem(context->psk);
2835  }
2836 
2837  //Release the PSK identity
2838  if(context->pskIdentity != NULL)
2839  {
2840  tlsFreeMem(context->pskIdentity);
2841  }
2842 
2843  //Release the PSK identity hint
2844  if(context->pskIdentityHint != NULL)
2845  {
2846  tlsFreeMem(context->pskIdentityHint);
2847  }
2848 #endif
2849 
2850 #if (TLS_ALPN_SUPPORT == ENABLED)
2851  //Release the list of supported ALPN protocols
2852  if(context->protocolList != NULL)
2853  {
2854  tlsFreeMem(context->protocolList);
2855  }
2856 
2857  //Release the selected ALPN protocol
2858  if(context->selectedProtocol != NULL)
2859  {
2860  tlsFreeMem(context->selectedProtocol);
2861  }
2862 #endif
2863 
2864  //Release encryption engine
2865  tlsFreeEncryptionEngine(&context->encryptionEngine);
2866  //Release decryption engine
2867  tlsFreeEncryptionEngine(&context->decryptionEngine);
2868 
2869 #if (DTLS_SUPPORT == ENABLED)
2870  //Release previous encryption engine
2871  tlsFreeEncryptionEngine(&context->prevEncryptionEngine);
2872 #endif
2873 
2874 #if (TLS_QUIC_SUPPORT == ENABLED)
2875  //Release local QUIC transport parameters
2876  if(context->localQuicTransportParams != NULL)
2877  {
2878  tlsFreeMem(context->localQuicTransportParams);
2879  }
2880 
2881  //Release remote QUIC transport parameters
2882  if(context->remoteQuicTransportParams != NULL)
2883  {
2884  tlsFreeMem(context->remoteQuicTransportParams);
2885  }
2886 #endif
2887 
2888  //Clear the TLS context before freeing memory
2889  osMemset(context, 0, sizeof(TlsContext));
2890  tlsFreeMem(context);
2891  }
2892 }
2893 
2894 
2895 /**
2896  * @brief Initialize session state
2897  * @param[in] session Pointer to the session state
2898  * @return Error code
2899  **/
2900 
2902 {
2903  //Make sure the session state is valid
2904  if(session == NULL)
2905  return ERROR_INVALID_PARAMETER;
2906 
2907  //Erase session state
2908  osMemset(session, 0, sizeof(TlsSessionState));
2909 
2910  //Successful initialization
2911  return NO_ERROR;
2912 }
2913 
2914 
2915 /**
2916  * @brief Save TLS session
2917  * @param[in] context Pointer to the TLS context
2918  * @param[out] session Pointer to the session state
2919  * @return Error code
2920  **/
2921 
2923  TlsSessionState *session)
2924 {
2925  error_t error;
2926 
2927  //Check parameters
2928  if(context == NULL || session == NULL)
2929  return ERROR_INVALID_PARAMETER;
2930 
2931  //Release previous session state
2932  tlsFreeSessionState(session);
2933 
2934 #if (TLS_MAX_VERSION >= TLS_VERSION_1_0 && TLS_MIN_VERSION <= TLS_VERSION_1_2)
2935  //TLS 1.0, TLS 1.1 or TLS 1.2 currently selected?
2936  if(context->version >= TLS_VERSION_1_0 && context->version <= TLS_VERSION_1_2)
2937  {
2938  //Valid session?
2939  if(context->ticketLen > 0)
2940  {
2941  //Save session ticket
2942  error = tlsSaveSessionTicket(context, session);
2943  }
2944  else if(context->sessionIdLen > 0)
2945  {
2946  //Save session identifier
2947  error = tlsSaveSessionId(context, session);
2948  }
2949  else
2950  {
2951  //No valid session to save
2952  error = ERROR_INVALID_SESSION;
2953  }
2954  }
2955  else
2956 #endif
2957 #if (TLS_MAX_VERSION >= TLS_VERSION_1_3 && TLS_MIN_VERSION <= TLS_VERSION_1_3)
2958  //TLS 1.3 currently selected?
2959  if(context->version == TLS_VERSION_1_3)
2960  {
2961  //Save session ticket
2962  error = tls13SaveSessionTicket(context, session);
2963  }
2964  else
2965 #endif
2966  //Invalid TLS version?
2967  {
2968  //Do not save session state
2969  error = ERROR_INVALID_VERSION;
2970  }
2971 
2972  //Check status code
2973  if(error)
2974  {
2975  //Clean up side effects
2976  tlsFreeSessionState(session);
2977  }
2978 
2979  //Successful processing
2980  return NO_ERROR;
2981 }
2982 
2983 
2984 /**
2985  * @brief Restore TLS session
2986  * @param[in] context Pointer to the TLS context
2987  * @param[in] session Pointer to the session state to be restored
2988  * @return Error code
2989  **/
2990 
2992  const TlsSessionState *session)
2993 {
2994  //Check parameters
2995  if(context == NULL || session == NULL)
2996  return ERROR_INVALID_PARAMETER;
2997 
2998 #if (TLS_MAX_VERSION >= TLS_VERSION_1_0 && TLS_MIN_VERSION <= TLS_VERSION_1_2)
2999  //TLS 1.0, TLS 1.1 or TLS 1.2 currently selected?
3000  if(session->version >= TLS_VERSION_1_0 && session->version <= TLS_VERSION_1_2)
3001  {
3002  //Valid session?
3003  if(session->ticketLen > 0)
3004  {
3005  //Restore a TLS session using session ticket
3006  tlsRestoreSessionTicket(context, session);
3007  }
3008  else if(session->sessionIdLen > 0)
3009  {
3010  //Restore a TLS session using session ID
3011  tlsRestoreSessionId(context, session);
3012  }
3013  else
3014  {
3015  //No valid session to restore
3016  }
3017  }
3018  else
3019 #endif
3020 #if (TLS_MAX_VERSION >= TLS_VERSION_1_3 && TLS_MIN_VERSION <= TLS_VERSION_1_3)
3021  //TLS 1.3 currently selected?
3022  if(session->version == TLS_VERSION_1_3)
3023  {
3024  //Restore TLS session using session ticket
3025  tls13RestoreSessionTicket(context, session);
3026  }
3027  else
3028 #endif
3029  //Invalid TLS version?
3030  {
3031  //Do not restore session state
3032  }
3033 
3034  //Successful processing
3035  return NO_ERROR;
3036 }
3037 
3038 
3039 /**
3040  * @brief Properly dispose a session state
3041  * @param[in] session Pointer to the session state to be released
3042  **/
3043 
3045 {
3046  //Make sure the session state is valid
3047  if(session != NULL)
3048  {
3049  //Release session ticket
3050  if(session->ticket != NULL)
3051  {
3052  osMemset(session->ticket, 0, session->ticketLen);
3053  tlsFreeMem(session->ticket);
3054  }
3055 
3056 #if (TLS_MAX_VERSION >= TLS_VERSION_1_3 && TLS_MIN_VERSION <= TLS_VERSION_1_3)
3057  //Release the ALPN protocol associated with the ticket
3058  if(session->ticketAlpn != NULL)
3059  {
3060  tlsFreeMem(session->ticketAlpn);
3061  }
3062 #endif
3063 
3064 #if (TLS_SNI_SUPPORT == ENABLED)
3065  //Release server name
3066  if(session->serverName != NULL)
3067  {
3068  tlsFreeMem(session->serverName);
3069  }
3070 #endif
3071 
3072  //Erase session state
3073  osMemset(session, 0, sizeof(TlsSessionState));
3074  }
3075 }
3076 
3077 #endif
TlsContext * tlsInit(void)
TLS context initialization.
Definition: tls.c:67
error_t tlsSetSupportedGroups(TlsContext *context, const uint16_t *groups, uint_t length)
Specify the list of allowed ECDHE and FFDHE groups.
Definition: tls.c:649
#define TLS_MAX_RECORD_LENGTH
Definition: tls.h:977
#define tlsAllocMem(size)
Definition: tls.h:888
size_t ticketLen
Length of the session ticket.
Definition: tls.h:2204
TLS helper functions.
X.509 certificate parsing.
error_t tlsEnableSecureRenegotiation(TlsContext *context, bool_t enabled)
Enable secure renegotiation.
Definition: tls.c:1496
error_t tlsSetConnectionEnd(TlsContext *context, TlsConnectionEnd entity)
Set operation mode (client or server)
Definition: tls.c:364
@ TLS_TRANSPORT_PROTOCOL_QUIC
Definition: tls.h:1001
error_t tlsSetMaxEarlyDataSize(TlsContext *context, size_t maxEarlyDataSize)
Send the maximum amount of 0-RTT data the server can accept.
Definition: tls.c:1704
int bool_t
Definition: compiler_port.h:61
TLS cipher suites.
void rsaFreePublicKey(RsaPublicKey *key)
Release an RSA public key.
Definition: rsa.c:113
error_t tlsSaveSessionTicket(const TlsContext *context, TlsSessionState *session)
Save session ticket.
Definition: tls_misc.c:504
error_t tlsSetTransportProtocol(TlsContext *context, TlsTransportProtocol transportProtocol)
Set the transport protocol to be used.
Definition: tls.c:333
error_t(* TlsTicketEncryptCallback)(TlsContext *context, const uint8_t *plaintext, size_t plaintextLen, uint8_t *ciphertext, size_t *ciphertextLen, void *param)
Ticket encryption callback function.
Definition: tls.h:2085
@ TLS_ALERT_CLOSE_NOTIFY
Definition: tls.h:1128
@ CIPHER_MODE_CBC
Definition: crypto.h:1036
#define DTLS_DEFAULT_PMTU
Definition: dtls_misc.h:48
error_t tls13DeriveSecret(TlsContext *context, const uint8_t *secret, size_t secretLen, const char_t *label, const char_t *message, size_t messageLen, uint8_t *output, size_t outputLen)
Derive-Secret function.
error_t(* TlsEcdsaVerifyCallback)(TlsContext *context, const uint8_t *digest, size_t digestLen, EcdsaSignature *signature)
ECDSA signature verification callback function.
Definition: tls.h:2118
Key material generation.
error_t tlsPerformHandshake(TlsContext *context)
Perform TLS handshake.
TLS handshake.
#define TLS_MAX_PASSWORD_LEN
Definition: tls.h:787
@ ERROR_BUFFER_OVERFLOW
Definition: error.h:143
uint8_t * ticket
Session ticket.
Definition: tls.h:2203
@ ERROR_NOT_IMPLEMENTED
Definition: error.h:66
#define PrngAlgo
Definition: crypto.h:1008
error_t tlsExportChannelBinding(TlsContext *context, const char_t *type, uint8_t *output, size_t *length)
Export channel binding value.
Definition: tls.c:2037
@ TLS_EARLY_DATA_REJECTED
Definition: tls.h:1035
error_t tlsSetPskIdentityHint(TlsContext *context, const char_t *pskIdentityHint)
Set the PSK identity hint to be used by the server.
Definition: tls.c:1111
error_t tlsPrf(const uint8_t *secret, size_t secretLen, const char_t *label, const uint8_t *seed, size_t seedLen, uint8_t *output, size_t outputLen)
Pseudorandom function (TLS 1.0 and 1.1)
@ ERROR_UNEXPECTED_MESSAGE
Definition: error.h:195
TlsState
TLS FSM states.
Definition: tls.h:1537
DtlsRecord
Definition: dtls_misc.h:180
error_t tlsEnableCertAuthorities(TlsContext *context, bool_t enabled)
Enable CertificateAuthorities extension.
Definition: tls.c:1470
uint8_t p
Definition: ndp.h:300
error_t tlsSetEcdhCallback(TlsContext *context, TlsEcdhCallback ecdhCallback)
Register ECDH key agreement callback function.
Definition: tls.c:766
TlsConnectionEnd
TLS connection end.
Definition: tls.h:1011
error_t tlsSetCertificateVerifyCallback(TlsContext *context, TlsCertVerifyCallback certVerifyCallback, void *param)
Register certificate verification callback function.
Definition: tls.c:1393
#define TRUE
Definition: os_port.h:50
error_t(* DtlsCookieGenerateCallback)(TlsContext *context, const DtlsClientParameters *clientParams, uint8_t *cookie, size_t *length, void *param)
DTLS cookie generation callback function.
Definition: dtls_misc.h:240
@ TLS_ENCRYPTION_LEVEL_INITIAL
Definition: tls.h:1580
uint8_t data[]
Definition: ethernet.h:224
@ TLS_GROUP_SECP256R1
Definition: tls.h:1471
@ TLS_TYPE_HANDSHAKE
Definition: tls.h:1070
size_t digestSize
Definition: crypto.h:1130
error_t(* TlsSocketReceiveCallback)(TlsSocketHandle handle, void *data, size_t size, size_t *received, uint_t flags)
Socket receive callback function.
Definition: tls.h:2045
error_t tlsSetCache(TlsContext *context, TlsCache *cache)
Set session cache.
Definition: tls.c:493
TlsCertificateType type
End entity certificate type.
Definition: tls.h:2242
@ ERROR_OUT_OF_RESOURCES
Definition: error.h:64
TLS 1.3 session tickets.
@ TLS_TRANSPORT_PROTOCOL_DATAGRAM
Definition: tls.h:1000
void ecdhFree(EcdhContext *context)
Release ECDH context.
Definition: ecdh.c:65
error_t tlsSaveSessionId(const TlsContext *context, TlsSessionState *session)
Save session ID.
Definition: tls_misc.c:432
void kemInit(KemContext *context, const KemAlgo *kemAlgo)
Initialize KEM context.
Definition: kem.c:48
@ TLS_STATE_APPLICATION_DATA
Definition: tls.h:1568
error_t tlsEnableTrustedCaKeys(TlsContext *context, bool_t enabled)
Enable TrustedCaKeys extension.
Definition: tls.c:1443
size_t sessionIdLen
Length of the session identifier.
Definition: tls.h:2200
uint8_t type
Definition: coap_common.h:176
error_t tlsSetSupportedSignAlgos(TlsContext *context, const uint16_t *signAlgos, uint_t length)
Specify the list of allowed signature algorithms.
Definition: tls.c:704
error_t tlsSetAlpnCallback(TlsContext *context, TlsAlpnCallback alpnCallback)
Register ALPN callback function.
Definition: tls.c:948
@ ERROR_OUT_OF_MEMORY
Definition: error.h:63
error_t tlsSetEcdsaSignCallback(TlsContext *context, TlsEcdsaSignCallback ecdsaSignCallback)
Register ECDSA signature generation callback function.
Definition: tls.c:792
#define osStrcmp(s1, s2)
Definition: os_port.h:174
@ ERROR_NOT_CONFIGURED
Definition: error.h:218
uint16_t totalLength
Definition: ipv4.h:323
#define osStrlen(s)
Definition: os_port.h:168
error_t tlsEnableReplayDetection(TlsContext *context, bool_t enabled)
Enable anti-replay mechanism (for DTLS only)
Definition: tls.c:1676
Session cache.
Definition: tls.h:2224
error_t tlsShutdownEx(TlsContext *context, bool_t waitForCloseNotify)
Gracefully close TLS session.
Definition: tls.c:2595
@ ERROR_END_OF_STREAM
Definition: error.h:211
error_t tlsSetPmtu(TlsContext *context, size_t pmtu)
Set PMTU value (for DTLS only)
Definition: tls.c:1582
@ ERROR_INVALID_VERSION
Definition: error.h:118
#define TLS_RANDOM_SIZE
Definition: tls.h:981
void kemFree(KemContext *context)
Release KEM context.
Definition: kem.c:62
void tlsFreeSessionState(TlsSessionState *session)
Properly dispose a session state.
Definition: tls.c:3044
@ TLS_CIPHER_SUITE_TYPE_TLS13
error_t(* TlsSocketSendCallback)(TlsSocketHandle handle, const void *data, size_t length, size_t *written, uint_t flags)
Socket send callback function.
Definition: tls.h:2037
#define DTLS_MIN_PMTU
Definition: dtls_misc.h:55
error_t tlsRestoreSessionState(TlsContext *context, const TlsSessionState *session)
Restore TLS session.
Definition: tls.c:2991
Certificate parsing options.
Definition: x509_common.h:1336
error_t pemImportDhParameters(DhParameters *params, const char_t *input, size_t length)
Decode a PEM file containing Diffie-Hellman parameters.
Definition: pem_import.c:137
@ TLS_CIPHER_SUITE_TYPE_SM
error_t(* TlsAlpnCallback)(TlsContext *context, const char_t *selectedProtocol)
ALPN callback function.
Definition: tls.h:2053
error_t tlsSetVersion(TlsContext *context, uint16_t versionMin, uint16_t versionMax)
Set minimum and maximum versions permitted.
Definition: tls.c:295
error_t(* TlsRpkVerifyCallback)(TlsContext *context, const uint8_t *rawPublicKey, size_t rawPublicKeyLen)
Raw public key verification callback function.
Definition: tls.h:2077
error_t tlsEnableFallbackScsv(TlsContext *context, bool_t enabled)
Perform fallback retry (for clients only)
Definition: tls.c:1522
@ TLS_ALERT_LEVEL_WARNING
Definition: tls.h:1117
error_t tlsSetMaxFragmentLength(TlsContext *context, size_t maxFragLen)
Set maximum fragment length.
Definition: tls.c:584
const char_t * tlsGetServerName(TlsContext *context)
Get the server name.
Definition: tls.c:468
error_t tls13SaveSessionTicket(const TlsContext *context, TlsSessionState *session)
Save session ticket.
Definition: tls13_ticket.c:89
error_t tlsShutdown(TlsContext *context)
Gracefully close TLS session.
Definition: tls.c:2582
size_t certChainLen
Length of the certificate chain.
Definition: tls.h:2238
#define FALSE
Definition: os_port.h:46
error_t tlsSetPsk(TlsContext *context, const uint8_t *psk, size_t length)
Set the pre-shared key to be used.
Definition: tls.c:1001
error_t pemImportCertificate(const char_t *input, size_t inputLen, uint8_t *output, size_t *outputLen, size_t *consumed)
Decode a PEM file containing a certificate.
Definition: pem_import.c:55
error_t tlsSendAlert(TlsContext *context, uint8_t level, uint8_t description)
Send Alert message.
Definition: tls_common.c:524
error_t tlsParseAlert(TlsContext *context, const TlsAlert *message, size_t length)
Parse Alert message.
Definition: tls_common.c:1637
PEM file import functions.
@ ERROR_INVALID_PARAMETER
Invalid parameter.
Definition: error.h:47
@ TLS_FLAG_PEEK
Definition: tls.h:1046
#define osMemcpy(dest, src, length)
Definition: os_port.h:144
const X509Options X509_DEFAULT_OPTIONS
Definition: x509_common.c:173
error_t tls13SendEarlyData(TlsContext *context, const void *data, size_t length, size_t *written)
Send early data to the remote TLS server.
X.509 certificate.
Definition: x509_common.h:1121
#define TlsContext
Definition: tls.h:36
error_t
Error codes.
Definition: error.h:43
DTLS record protocol.
bool_t tls13IsGroupSupported(TlsContext *context, uint16_t namedGroup)
Check whether a given named group is supported.
Definition: tls13_misc.c:953
HashAlgoCompute compute
Definition: crypto.h:1133
void ecInitPublicKey(EcPublicKey *key)
Initialize an EC public key.
Definition: ec.c:52
@ TLS_CONNECTION_END_SERVER
Definition: tls.h:1013
#define TLS_MIN_RECORD_LENGTH
Definition: tls.h:975
error_t x509ParseCertificateEx(const uint8_t *data, size_t length, X509CertInfo *certInfo, const X509Options *options)
Parse a X.509 certificate.
void tlsFreeEncryptionEngine(TlsEncryptionEngine *encryptionEngine)
Release encryption engine.
Definition: tls_misc.c:928
void(* TlsStateChangeCallback)(TlsContext *context, TlsState state)
TLS state change callback.
Definition: tls.h:2030
TlsClientAuthMode
Client authentication mode.
Definition: tls.h:1022
error_t tlsSetTicketCallbacks(TlsContext *context, TlsTicketEncryptCallback ticketEncryptCallback, TlsTicketDecryptCallback ticketDecryptCallback, void *param)
Set ticket encryption/decryption callbacks.
Definition: tls.c:1550
#define TLS_VERSION_1_2
Definition: tls.h:96
@ TLS_FLAG_WAIT_ALL
Definition: tls.h:1047
@ TLS_GROUP_NONE
Definition: tls.h:1448
error_t tlsSetTimeout(TlsContext *context, systime_t timeout)
Set timeout for blocking calls (for DTLS only)
Definition: tls.c:1612
error_t(* TlsEcdhCallback)(TlsContext *context)
ECDH key agreement callback function.
Definition: tls.h:2103
@ ERROR_FAILURE
Generic error code.
Definition: error.h:45
#define TLS_MAX_VERSION
Definition: tls.h:136
TlsEarlyDataStatus tlsGetEarlyDataStatus(TlsContext *context)
Check whether the server has accepted or rejected the early data.
Definition: tls.c:1846
TlsAlert
Definition: tls.h:1991
#define STORE16BE(a, p)
Definition: cpu_endian.h:262
#define TLS_MIN_VERSION
Definition: tls.h:129
@ TLS_TYPE_APPLICATION_DATA
Definition: tls.h:1071
Helper functions for TLS 1.3 client.
@ TLS_TYPE_ALERT
Definition: tls.h:1069
#define TLS_VERSION_1_3
Definition: tls.h:97
@ TLS_STATE_EARLY_DATA
Definition: tls.h:1541
Handshake message processing (TLS client and server)
void dhFree(DhContext *context)
Release Diffie-Hellman context.
Definition: dh.c:71
TlsSignatureScheme signScheme
Signature scheme used to sign the end entity certificate.
Definition: tls.h:2243
bool_t tlsIsTxReady(TlsContext *context)
Check whether some data is ready for transmission.
Definition: tls.c:2503
error_t tlsSetPreferredGroup(TlsContext *context, uint16_t group)
Specify the preferred ECDHE or FFDHE group.
Definition: tls.c:676
TLS record protocol.
#define TLS_MAX_CERTIFICATES
Definition: tls.h:283
error_t tlsReadProtocolData(TlsContext *context, uint8_t **data, size_t *length, TlsContentType *contentType)
Read protocol data.
Definition: tls_record.c:157
@ TLS_TRANSPORT_PROTOCOL_EAP
Definition: tls.h:1002
@ TLS_STATE_SERVER_HELLO_3
Definition: tls.h:1546
@ TLS_HASH_ALGO_SHA256
Definition: tls.h:1264
error_t tlsEnableSessionTickets(TlsContext *context, bool_t enabled)
Enable session ticket mechanism.
Definition: tls.c:1417
@ ERROR_INVALID_TYPE
Definition: error.h:115
error_t dtlsWriteProtocolData(TlsContext *context, const uint8_t *data, size_t length, TlsContentType contentType)
Write protocol data.
Definition: dtls_record.c:58
error_t tlsSaveSessionState(const TlsContext *context, TlsSessionState *session)
Save TLS session.
Definition: tls.c:2922
uint8_t length
Definition: tcp.h:375
#define LSB(x)
Definition: os_port.h:55
error_t tlsRead(TlsContext *context, void *data, size_t size, size_t *received, uint_t flags)
Receive application data from a the remote host using TLS.
Definition: tls.c:2264
@ TLS_CLIENT_AUTH_NONE
Definition: tls.h:1023
#define MIN(a, b)
Definition: os_port.h:63
error_t tlsSetKeyLogCallback(TlsContext *context, TlsKeyLogCallback keyLogCallback)
Register key logging callback function (for debugging purpose only)
Definition: tls.c:846
error_t(* TlsCertVerifyCallback)(TlsContext *context, const X509CertInfo *certInfo, uint_t pathLen, void *param)
Certificate verification callback function.
Definition: tls.h:2069
error_t tls12Prf(const HashAlgo *hash, const uint8_t *secret, size_t secretLen, const char_t *label, const uint8_t *seed, size_t seedLen, uint8_t *output, size_t outputLen)
Pseudorandom function (TLS 1.2)
error_t tlsWriteEarlyData(TlsContext *context, const void *data, size_t length, size_t *written, uint_t flags)
Send early data to the remote TLS server.
Definition: tls.c:1733
TlsCertificateType
Certificate types.
Definition: tls.h:1233
error_t tlsSetServerName(TlsContext *context, const char_t *serverName)
Set the server name.
Definition: tls.c:418
#define TLS_MASTER_SECRET_SIZE
Definition: tls.h:836
size_t privateKeyLen
Length of the private key.
Definition: tls.h:2240
Certificate descriptor.
Definition: tls.h:2236
Transcript hash calculation.
uint8_t secret[TLS_MASTER_SECRET_SIZE]
Master secret.
Definition: tls.h:2002
@ TLS_FLAG_BREAK_CHAR
Definition: tls.h:1048
error_t tlsRestoreSessionId(TlsContext *context, const TlsSessionState *session)
Restore a TLS session using session ID.
Definition: tls_misc.c:558
char_t * serverName
ServerName extension.
Definition: tls.h:2214
uint32_t systime_t
System time.
error_t tlsSetRpkVerifyCallback(TlsContext *context, TlsRpkVerifyCallback rpkVerifyCallback)
Register the raw public key verification callback function.
Definition: tls.c:1186
error_t tlsSetEcdsaVerifyCallback(TlsContext *context, TlsEcdsaVerifyCallback ecdsaVerifyCallback)
Register ECDSA signature verification callback function.
Definition: tls.c:819
bool_t tlsIsRxReady(TlsContext *context)
Check whether some data is available in the receive buffer.
Definition: tls.c:2537
TlsRecord
Definition: tls.h:1860
@ TLS_TYPE_NONE
Definition: tls.h:1067
void ecdhInit(EcdhContext *context)
Initialize ECDH context.
Definition: ecdh.c:49
#define MAX(a, b)
Definition: os_port.h:67
error_t(* TlsEcdsaSignCallback)(TlsContext *context, const uint8_t *digest, size_t digestLen, EcdsaSignature *signature)
ECDSA signature generation callback function.
Definition: tls.h:2110
char char_t
Definition: compiler_port.h:55
#define TLS_VERSION_1_1
Definition: tls.h:95
TlsContentType
Content type.
Definition: tls.h:1066
@ TLS_STATE_CLOSING
Definition: tls.h:1569
@ TLS_EARLY_DATA_ACCEPTED
Definition: tls.h:1036
error_t dtlsReadProtocolData(TlsContext *context, uint8_t **data, size_t *length, TlsContentType *contentType)
Read protocol data.
Definition: dtls_record.c:131
error_t tlsSetBufferSize(TlsContext *context, size_t txBufferSize, size_t rxBufferSize)
Set TLS buffer size.
Definition: tls.c:536
TLS session state.
Definition: tls.h:2193
@ ERROR_NOT_CONNECTED
Definition: error.h:80
uint8_t n
error_t tlsParseHandshakeMessage(TlsContext *context, const uint8_t *message, size_t length)
Parse handshake message.
TlsTransportProtocol
TLS transport protocols.
Definition: tls.h:998
TlsState tlsGetState(TlsContext *context)
Retrieve current TLS state.
Definition: tls.c:213
error_t(* DtlsCookieVerifyCallback)(TlsContext *context, const DtlsClientParameters *clientParams, const uint8_t *cookie, size_t length, void *param)
DTLS cookie verification callback function.
Definition: dtls_misc.h:249
error_t tlsSetStateChangeCallback(TlsContext *context, TlsStateChangeCallback stateChangeCallback)
Register TLS state change callback.
Definition: tls.c:239
#define TLS_VERSION_1_0
Definition: tls.h:94
char_t password[TLS_MAX_PASSWORD_LEN+1]
Password used to decrypt the private key.
Definition: tls.h:2241
@ TLS_STATE_INIT
Definition: tls.h:1538
error_t tlsGetCertificateSignAlgo(const X509CertInfo *certInfo, TlsSignatureScheme *signScheme)
Retrieve the signature algorithm used to sign the certificate.
error_t tlsSetPskCallback(TlsContext *context, TlsPskCallback pskCallback)
Register PSK callback function.
Definition: tls.c:1160
error_t tlsWriteProtocolData(TlsContext *context, const uint8_t *data, size_t length, TlsContentType contentType)
Write protocol data.
Definition: tls_record.c:54
error_t tlsSetSocketCallbacks(TlsContext *context, TlsSocketSendCallback socketSendCallback, TlsSocketReceiveCallback socketReceiveCallback, TlsSocketHandle handle)
Set socket send and receive callbacks.
Definition: tls.c:263
#define TLS_MAX_HKDF_DIGEST_SIZE
Definition: tls.h:964
error_t tlsSetCipherSuites(TlsContext *context, const uint16_t *cipherSuites, uint_t length)
Specify the list of allowed cipher suites.
Definition: tls.c:620
@ TLS_CONNECTION_END_CLIENT
Definition: tls.h:1012
X.509 certificate handling.
error_t tlsWrite(TlsContext *context, const void *data, size_t length, size_t *written, uint_t flags)
Send application data to the remote host using TLS.
Definition: tls.c:2127
TLS (Transport Layer Security)
uint16_t version
TLS protocol version.
Definition: tls.h:2194
void eddsaFreePublicKey(EddsaPublicKey *key)
Release an EdDSA public key.
Definition: eddsa.c:63
#define osTolower(c)
Definition: os_port.h:270
uint8_t options[]
Definition: tcp.h:364
@ TLS_GROUP_X25519
Definition: tls.h:1477
error_t tlsSetAlpnProtocolList(TlsContext *context, const char_t *protocolList)
Set the list of supported ALPN protocols.
Definition: tls.c:899
error_t tlsLoadCertificate(TlsContext *context, uint_t index, const char_t *certChain, size_t certChainLen, const char_t *privateKey, size_t privateKeyLen, const char_t *password)
Load entity's certificate.
Definition: tls.c:1249
@ TLS_TRANSPORT_PROTOCOL_STREAM
Definition: tls.h:999
@ ERROR_INVALID_PASSWORD
Definition: error.h:281
void tlsFree(TlsContext *context)
Release TLS context.
Definition: tls.c:2744
TLS 1.3 key schedule.
const char_t * certChain
End entity certificate chain (PEM format)
Definition: tls.h:2237
Common interface for hash algorithms.
Definition: crypto.h:1124
error_t(* TlsPskCallback)(TlsContext *context, const uint8_t *pskIdentity, size_t pskIdentityLen)
Pre-shared key callback function.
Definition: tls.h:2061
error_t tlsSetClientAuthMode(TlsContext *context, TlsClientAuthMode mode)
Set client authentication mode (for servers only)
Definition: tls.c:514
const char_t * tlsGetAlpnProtocol(TlsContext *context)
Get the name of the selected ALPN protocol.
Definition: tls.c:973
error_t tlsGetCertificateType(const X509CertInfo *certInfo, TlsCertificateType *certType, TlsNamedGroup *namedCurve)
Retrieve the certificate type.
void tlsProcessError(TlsContext *context, error_t errorCode)
Translate an error code to an alert message.
Definition: tls_misc.c:74
error_t tls13HkdfExpandLabel(TlsTransportProtocol transportProtocol, const HashAlgo *hash, const uint8_t *secret, size_t secretLen, const char_t *label, const uint8_t *context, size_t contextLen, uint8_t *output, size_t outputLen)
HKDF-Expand-Label function.
uint8_t flags
Definition: tcp.h:358
error_t tlsAllowUnknownAlpnProtocols(TlsContext *context, bool_t allowed)
Allow unknown ALPN protocols.
Definition: tls.c:873
void tlsChangeState(TlsContext *context, TlsState newState)
Update TLS state.
Definition: tls_misc.c:54
TlsNamedGroup
Named groups.
Definition: tls.h:1447
error_t tlsSetCookieCallbacks(TlsContext *context, DtlsCookieGenerateCallback cookieGenerateCallback, DtlsCookieVerifyCallback cookieVerifyCallback, void *param)
Set cookie generation/verification callbacks (for DTLS only)
Definition: tls.c:1640
const char_t * privateKey
Private key (PEM format)
Definition: tls.h:2239
TlsSignatureScheme
Signature schemes.
Definition: tls.h:1294
void(* TlsKeyLogCallback)(TlsContext *context, const char_t *key)
Key logging callback function (for debugging purpose only)
Definition: tls.h:2126
error_t tlsSetPrng(TlsContext *context, const PrngAlgo *prngAlgo, void *prngContext)
Set the pseudo-random number generator to be used.
Definition: tls.c:390
unsigned int uint_t
Definition: compiler_port.h:57
#define osMemset(p, value, length)
Definition: os_port.h:138
#define tlsFreeMem(p)
Definition: tls.h:893
#define TLS_MAX_RECORD_OVERHEAD
Definition: tls.h:979
error_t tlsSetTrustedCaList(TlsContext *context, const char_t *trustedCaList, size_t length)
Import a trusted CA list.
Definition: tls.c:1214
void eddsaInitPublicKey(EddsaPublicKey *key)
Initialize an EdDSA public key.
Definition: eddsa.c:48
error_t tlsExportKeyingMaterial(TlsContext *context, const char_t *label, bool_t useContextValue, const uint8_t *contextValue, size_t contextValueLen, uint8_t *output, size_t outputLen)
Export keying material per RFC 5705 standard.
Definition: tls.c:1892
error_t tlsInitSessionState(TlsSessionState *session)
Initialize session state.
Definition: tls.c:2901
error_t(* TlsTicketDecryptCallback)(TlsContext *context, const uint8_t *ciphertext, size_t ciphertextLen, uint8_t *plaintext, size_t *plaintextLen, void *param)
Ticket decryption callback function.
Definition: tls.h:2094
#define osStrcpy(s1, s2)
Definition: os_port.h:210
void dhInit(DhContext *context)
Initialize Diffie-Hellman context.
Definition: dh.c:54
error_t tlsSetPskIdentity(TlsContext *context, const char_t *pskIdentity)
Set the PSK identity to be used by the client.
Definition: tls.c:1062
error_t tlsConnect(TlsContext *context)
Initiate the TLS handshake.
Definition: tls.c:1798
void dsaFreePublicKey(DsaPublicKey *key)
Release a DSA public key.
Definition: dsa.c:119
@ ERROR_INVALID_SESSION
Definition: error.h:287
error_t tls13RestoreSessionTicket(TlsContext *context, const TlsSessionState *session)
Restore a TLS session using session ticket.
Definition: tls13_ticket.c:187
TlsNamedGroup namedCurve
Named curve used to generate the EC public key.
Definition: tls.h:2244
void dsaInitPublicKey(DsaPublicKey *key)
Initialize a DSA public key.
Definition: dsa.c:105
error_t tlsSetDhParameters(TlsContext *context, const char_t *params, size_t length)
Import Diffie-Hellman parameters.
Definition: tls.c:738
@ NO_ERROR
Success.
Definition: error.h:44
uint8_t c
Definition: ndp.h:514
Debugging facilities.
void rsaInitPublicKey(RsaPublicKey *key)
Initialize an RSA public key.
Definition: rsa.c:100
void * TlsSocketHandle
Socket handle.
Definition: tls.h:2023
void ecFreePublicKey(EcPublicKey *key)
Release an EC public key.
Definition: ec.c:68
TlsEarlyDataStatus
Early data status.
Definition: tls.h:1034
char_t * ticketAlpn
ALPN protocol associated with the ticket.
Definition: tls.h:2210
void tlsFreeTranscriptHash(TlsContext *context)
Release transcript hash context.
#define INFINITE_DELAY
Definition: os_port.h:75
systime_t osGetSystemTime(void)
Retrieve system time.
error_t tlsRestoreSessionTicket(TlsContext *context, const TlsSessionState *session)
Restore a TLS session using session ticket.
Definition: tls_misc.c:607
@ TLS_STATE_CLOSED
Definition: tls.h:1570