• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * This file is part of the openHiTLS project.
3  *
4  * openHiTLS is licensed under the Mulan PSL v2.
5  * You can use this software according to the terms and conditions of the Mulan PSL v2.
6  * You may obtain a copy of Mulan PSL v2 at:
7  *
8  *     http://license.coscl.org.cn/MulanPSL2
9  *
10  * THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND,
11  * EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT,
12  * MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
13  * See the Mulan PSL v2 for more details.
14  */
15 
16 #ifndef REC_H
17 #define REC_H
18 
19 #include <stdbool.h>
20 #include <stdint.h>
21 #include "hitls_build.h"
22 #include "hitls_crypt_type.h"
23 #include "tls.h"
24 
25 #ifdef __cplusplus
26 extern "C" {
27 #endif
28 
29 #define REC_MAX_PLAIN_LENGTH 16384          /* Maximum plain length */
30 /* TLS13 Maximum MAC address padding */
31 #define REC_MAX_TLS13_ENCRYPTED_OVERHEAD  256u
32 /* TLS13 Maximum ciphertext length */
33 #define REC_MAX_TLS13_ENCRYPTED_LEN (REC_MAX_PLAIN_LENGTH + REC_MAX_TLS13_ENCRYPTED_OVERHEAD)
34 /* The length (in bytes) of the following TLSCiphertext.fragment. The length MUST NOT exceed 2^14 + 2048. */
35 #define REC_MAX_PLAIN_DECRYPTO_MAX_LENGTH (16384 + 2048)
36 
37 #define REC_MASTER_SECRET_LEN 48
38 #define REC_RANDOM_LEN  32
39 
40 #define RECORD_HEADER 0x100
41 #define RECORD_INNER_CONTENT_TYPE 0x101
42 /**
43  * record type
44  */
45 typedef enum {
46     REC_TYPE_CHANGE_CIPHER_SPEC = 20,
47     REC_TYPE_ALERT = 21,
48     REC_TYPE_HANDSHAKE = 22,
49     REC_TYPE_APP = 23,
50     REC_TYPE_UNKNOWN = 255
51 } REC_Type;
52 
53 /**
54  * SecurityParameters, used to generate keys and initialize the connect state
55  */
56 typedef struct {
57     bool isClient;                  /* Connection Endpoint */
58     bool isClientTrafficSecret;     /* TrafficSecret type */
59     HITLS_HashAlgo prfAlg;          /* prf_algorithm */
60     HITLS_MacAlgo macAlg;           /* mac algorithm */
61     HITLS_CipherAlgo cipherAlg;     /* symmetric encryption algorithm */
62     HITLS_CipherType cipherType;    /* encryption algorithm type */
63 
64     /* key length */
65     uint8_t fixedIvLength;          /* iv length. In TLS1.2 AEAD algorithm is the implicit IV length */
66     uint8_t encKeyLen;              /* Length of the symmetric key */
67     uint8_t macKeyLen;              /* MAC key length: If the AEAD algorithm is used, the MAC key length is 0 */
68 
69     uint8_t blockLength;            /* If the block length is not zero, the alignment should be handled. */
70     uint8_t recordIvLength;         /* The explicit IV needs to be sent to the peer */
71     uint8_t macLen;                 /*  MAC length. For AEAD, it is the mark length */
72 
73     uint8_t masterSecret[MAX_DIGEST_SIZE];             /* tls1.2 master key. TLS1.3 carries the TrafficSecret */
74     uint8_t clientRandom[REC_RANDOM_LEN];              /* Client random number */
75     uint8_t serverRandom[REC_RANDOM_LEN];              /* service random number */
76 } REC_SecParameters;
77 
78 /**
79  * @ingroup record
80  * @brief   Record initialization
81  *
82  * @param   ctx [IN] TLS object
83  *
84  * @retval  HITLS_SUCCESS
85  * @retval  HITLS_INTERNAL_EXCEPTION Invalid null pointer
86  * @retval  HITLS_MEMALLOC_FAIL Memory allocated failed
87  *
88  */
89 int32_t REC_Init(TLS_Ctx *ctx);
90 
91 /**
92  * @ingroup record
93  * @brief   record deinitialize
94  *
95  * @param   ctx [IN] TLS object
96  */
97 void REC_DeInit(TLS_Ctx *ctx);
98 
99 /**
100  * @ingroup record
101  * @brief   Check whether data exists in the read buffer of the reocrd
102  *
103  * @param   ctx [IN] TLS object
104  * @return  whether data exists in the read buffer
105  */
106 bool REC_ReadHasPending(const TLS_Ctx *ctx);
107 
108 /**
109  * @ingroup record
110  * @brief   Reads a message in the unit of a record. Data is read from the uio of the CTX to the data pointer
111  *
112  * @attention recordType indicates the expected record type (app or handshake)
113  *            readLen indicates the length of read data. The maximum length is REC_MAX_PLAIN_LENGTH (16384)
114  * @param   ctx [IN] TLS object
115  * @param   recordType [IN] Expected record type(app or handshake)
116  * @param   data [OUT] Read buffer
117  * @param   readLen [OUT] Length of the read data
118  * @param   num [IN] The size of read buffer, which must be greater than or equal to the maximum size of the record
119  *
120  * @retval  HITLS_SUCCESS
121  * @retval  HITLS_INTERNAL_EXCEPTION,Invalid null pointer
122  * @retval  HITLS_REC_ERR_BUFFER_NOT_ENOUGH The buffer space is insufficient
123  * @retval  HITLS_MEMCPY_FAIL Memory copy failed
124  * @retval  HITLS_REC_NORMAL_RECV_BUF_EMPTY indicates that the buffer is empty and needs to be read again
125  * @retval  HITLS_REC_ERR_IO_EXCEPTION I/O error
126  * @retval  HITLS_REC_NORMAL_RECV_UNEXPECT_MSG An unexpected message is received and needs to be processed
127  * @retval  HITLS_REC_ERR_SN_WRAPPING Sequence number wrap
128  */
129 int32_t REC_Read(TLS_Ctx *ctx, REC_Type recordType, uint8_t *data, uint32_t *readLen, uint32_t num);
130 
131 /**
132  * @ingroup record
133  * @brief   Write a record in the unit of record
134  *
135  * @attention If the value of num exceeds the maximum length of the record, return error
136  *
137  * @param   ctx [IN] TLS object
138  * @param   recordType [IN] record type
139  * @param   data [IN] Write data
140  * @param   num [IN] Attempt to write num bytes of plaintext data
141  *
142  * @retval  HITLS_SUCCESS
143  * @retval  HITLS_INTERNAL_EXCEPTION Invalid null pointer
144  * @retval  HITLS_REC_ERR_BUFFER_NOT_ENOUGH The buffer space is insufficient
145  * @retval  HITLS_MEMCPY_FAIL Memory copy failed
146  * @retval  HITLS_REC_PMTU_TOO_SMALL The PMTU is too small
147  * @retval  HITLS_REC_ERR_IO_EXCEPTION I/O error
148  * @retval  HITLS_REC_NORMAL_IO_BUSY I/O busy
149  * @retval  HITLS_REC_ERR_TOO_BIG_LENGTH The length of the plaintext data written by the upper layer exceeds the
150 * maximum length of the plaintext data that can be written by a single record
151  * @retval  HITLS_REC_ERR_NOT_SUPPORT_CIPHER The key algorithm is not supported
152  * @retval  HITLS_REC_ERR_SN_WRAPPING Sequence number wrap
153  */
154 int32_t REC_Write(TLS_Ctx *ctx, REC_Type recordType, const uint8_t *data, uint32_t num);
155 
156 /**
157  * @ingroup record
158  * @brief   Activate the expired write state. This API is invoked in the retransmission scenario
159  *
160  * @attention Reservation Interface
161  * @param   ctx [IN] TLS object
162  *
163  */
164 void REC_ActiveOutdatedWriteState(TLS_Ctx *ctx);
165 
166 /**
167  * @ingroup record
168  * @brief   Disable the expired write status. This API is invoked in the retransmission scenario
169  *
170  * @attention Reservation Interface
171  * @param   ctx [IN] TLS object
172  *
173  */
174 void REC_DeActiveOutdatedWriteState(TLS_Ctx *ctx);
175 
176 
177 /**
178  * @ingroup record
179  * @brief   Initialize the pending state
180  *
181  * @param   ctx [IN] TLS object
182  * @param   param [IN] Security parameter
183  *
184  * @retval  HITLS_SUCCESS
185  * @retval  HITLS_MEMALLOC_FAIL Memory allocated failed
186  * @retval  HITLS_INTERNAL_EXCEPTION Invalid null pointer
187  *
188  */
189 int32_t REC_InitPendingState(const TLS_Ctx *ctx, const REC_SecParameters *param);
190 
191 /**
192  * @ingroup record
193  * @brief    Activate the pending state, switch the pending state to the current state
194  *
195  * @attention ctx cannot be empty
196  * @param   ctx [IN] TLS object
197  * @param   isOut [IN] Indicates whether is the output type
198  *
199  * @retval  HITLS_SUCCESS
200  * @retval  HITLS_INTERNAL_EXCEPTION Invalid null pointer
201  *
202  */
203 int32_t REC_ActivePendingState(TLS_Ctx *ctx, bool isOut);
204 
205 /**
206  * @brief   Obtain the maximum writable plaintext length of a single record
207  *
208  * @param   ctx [IN] TLS_Ctx context
209  * @param   len [OUT] Maximum length of the plaintext
210  *
211  * @retval  HITLS_SUCCESS
212  * @retval  HITLS_INTERNAL_EXCEPTION Invalid null pointer
213  * @retval  HITLS_REC_PMTU_TOO_SMALL The PMTU is too small
214  */
215 int32_t REC_GetMaxWriteSize(const TLS_Ctx *ctx, uint32_t *len);
216 
217 /**
218  * @ingroup record
219  * @brief   TLS13 Initialize the pending state
220  *
221  * @param   ctx [IN] TLS object
222  * @param   param [IN] Security parameter
223  * @param   isOut [IN] Indicates whether is the output type
224  *
225  * @retval  HITLS_SUCCESS
226  * @retval  HITLS_MEMALLOC_FAIL Memory allocated failed
227  * @retval  HITLS_INTERNAL_EXCEPTION Invalid null pointer
228  *
229  */
230 int32_t REC_TLS13InitPendingState(const TLS_Ctx *ctx, const REC_SecParameters *param, bool isOut);
231 
232 /**
233  * @ingroup record
234  * @brief   Retransmit a record
235  *
236  * @param   recCtx [IN] Record context
237  * @param   recordType [IN] record type
238  * @param   data [IN] data
239  * @param   dataLen [IN] data length
240  */
241 int32_t REC_RetransmitListAppend(REC_Ctx *recCtx, REC_Type recordType, const uint8_t *data, uint32_t dataLen);
242 
243 /**
244  * @ingroup record
245  * @brief   Clean the retransmit list
246  *
247  * @param   recCtx [IN] Record context
248  */
249 void REC_RetransmitListClean(REC_Ctx *recCtx);
250 
251 
252 /**
253  * @ingroup record
254  * @brief   Flush the retransmit list
255  *
256  * @param   ctx [IN] TLS object
257  */
258 void REC_RetransmitListFlush(TLS_Ctx *ctx);
259 
260 REC_Type REC_GetUnexpectedMsgType(TLS_Ctx *ctx);
261 
262 bool REC_HaveReadSuiteInfo(const TLS_Ctx *ctx);
263 
264 /**
265  * @ingroup app
266  * @brief Obtain the length of the remaining readable app messages in the current record.
267  *
268  * @param ctx [IN] TLS object
269  * @return Length of the remaining readable app message
270  */
271 uint32_t APP_GetReadPendingBytes(const TLS_Ctx *ctx);
272 
273 int32_t REC_RecBufReSet(TLS_Ctx *ctx);
274 #ifdef __cplusplus
275 }
276 #endif
277 
278 #endif /* REC_H */
279