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 TLS_H 17 #define TLS_H 18 19 #include <stdint.h> 20 #include <stdbool.h> 21 #include "hitls_build.h" 22 #include "cipher_suite.h" 23 #include "tls_config.h" 24 #include "hitls_error.h" 25 #include "custom_extensions.h" 26 27 #ifdef __cplusplus 28 extern "C" { 29 #endif 30 31 #define MAX_DIGEST_SIZE 64UL /* The longest known value is SHA512 */ 32 33 #define DTLS_DEFAULT_PMTU 1500uL 34 35 /* RFC 6083 4.1. Mapping of DTLS Records: 36 The supported maximum length of SCTP user messages MUST be at least 37 2^14 + 2048 + 13 = 18445 bytes (2^14 + 2048 is the maximum length of 38 the DTLSCiphertext.fragment, and 13 is the size of the DTLS record 39 header). */ 40 #define DTLS_SCTP_PMTU 18445uL 41 42 #define IS_DTLS_VERSION(version) (((version) & 0x8u) == 0x8u) 43 44 #define IS_SUPPORT_STREAM(versionBits) (((versionBits) & STREAM_VERSION_BITS) != 0x0u) 45 #define IS_SUPPORT_DATAGRAM(versionBits) (((versionBits) & DATAGRAM_VERSION_BITS) != 0x0u) 46 #define IS_SUPPORT_TLCP(versionBits) (((versionBits) & TLCP_VERSION_BITS) != 0x0u) 47 48 #define DTLS_COOKIE_LEN 255 49 50 #define MAC_KEY_LEN 32u /* the length of mac key */ 51 52 #define UNPROCESSED_APP_MSG_COUNT_MAX 50 /* number of APP data cached */ 53 54 #define RANDOM_SIZE 32u /* the size of random number */ 55 56 typedef struct TlsCtx TLS_Ctx; 57 typedef struct HsCtx HS_Ctx; 58 typedef struct CcsCtx CCS_Ctx; 59 typedef struct AlertCtx ALERT_Ctx; 60 typedef struct RecCtx REC_Ctx; 61 62 typedef enum { 63 CCS_CMD_RECV_READY, /* CCS allowed to be received */ 64 CCS_CMD_RECV_EXIT_READY, /* CCS cannot be received */ 65 CCS_CMD_RECV_ACTIVE_CIPHER_SPEC, /* CCS active change cipher spec */ 66 } CCS_Cmd; 67 68 /* Check whether the CCS message is received */ 69 typedef bool (*IsRecvCcsCallback)(const TLS_Ctx *ctx); 70 /* Send a CCS message */ 71 typedef int32_t (*SendCcsCallback)(TLS_Ctx *ctx); 72 /* Control the CCS */ 73 typedef int32_t (*CtrlCcsCallback)(TLS_Ctx *ctx, CCS_Cmd cmd); 74 75 typedef enum { 76 ALERT_LEVEL_WARNING = 1, 77 ALERT_LEVEL_FATAL = 2, 78 ALERT_LEVEL_UNKNOWN = 255, 79 } ALERT_Level; 80 81 typedef enum { 82 ALERT_CLOSE_NOTIFY = 0, 83 ALERT_UNEXPECTED_MESSAGE = 10, 84 ALERT_BAD_RECORD_MAC = 20, 85 ALERT_DECRYPTION_FAILED = 21, 86 ALERT_RECORD_OVERFLOW = 22, 87 ALERT_DECOMPRESSION_FAILURE = 30, 88 ALERT_HANDSHAKE_FAILURE = 40, 89 ALERT_NO_CERTIFICATE_RESERVED = 41, 90 ALERT_BAD_CERTIFICATE = 42, 91 ALERT_UNSUPPORTED_CERTIFICATE = 43, 92 ALERT_CERTIFICATE_REVOKED = 44, 93 ALERT_CERTIFICATE_EXPIRED = 45, 94 ALERT_CERTIFICATE_UNKNOWN = 46, 95 ALERT_ILLEGAL_PARAMETER = 47, 96 ALERT_UNKNOWN_CA = 48, 97 ALERT_ACCESS_DENIED = 49, 98 ALERT_DECODE_ERROR = 50, 99 ALERT_DECRYPT_ERROR = 51, 100 ALERT_EXPORT_RESTRICTION_RESERVED = 60, 101 ALERT_PROTOCOL_VERSION = 70, 102 ALERT_INSUFFICIENT_SECURITY = 71, 103 ALERT_INTERNAL_ERROR = 80, 104 ALERT_INAPPROPRIATE_FALLBACK = 86, 105 ALERT_USER_CANCELED = 90, 106 ALERT_NO_RENEGOTIATION = 100, 107 ALERT_MISSING_EXTENSION = 109, 108 ALERT_UNSUPPORTED_EXTENSION = 110, 109 ALERT_CERTIFICATE_UNOBTAINABLE = 111, 110 ALERT_UNRECOGNIZED_NAME = 112, 111 ALERT_BAD_CERTIFICATE_STATUS_RESPONSE = 113, 112 ALERT_BAD_CERTIFICATE_HASH_VALUE = 114, 113 ALERT_UNKNOWN_PSK_IDENTITY = 115, 114 ALERT_CERTIFICATE_REQUIRED = 116, 115 ALERT_NO_APPLICATION_PROTOCOL = 120, 116 ALERT_UNKNOWN = 255 117 } ALERT_Description; 118 119 /** Connection management state */ 120 typedef enum { 121 CM_STATE_IDLE, 122 CM_STATE_HANDSHAKING, 123 CM_STATE_TRANSPORTING, 124 CM_STATE_RENEGOTIATION, 125 CM_STATE_ALERTING, 126 CM_STATE_ALERTED, 127 CM_STATE_CLOSED, 128 CM_STATE_END 129 } CM_State; 130 131 /** post-handshake auth */ 132 typedef enum { 133 PHA_NONE, /* not support pha */ 134 PHA_EXTENSION, /* pha extension send or received */ 135 PHA_PENDING, /* try to send certificate request */ 136 PHA_REQUESTED /* certificate request has been sent or received */ 137 } PHA_State; 138 139 /* Describes the handshake status */ 140 typedef enum { 141 TLS_IDLE, /* initial state */ 142 TLS_CONNECTED, /* Handshake succeeded */ 143 TRY_SEND_HELLO_REQUEST, /* sends hello request message */ 144 TRY_SEND_CLIENT_HELLO, /* sends client hello message */ 145 TRY_SEND_HELLO_RETRY_REQUEST, /* sends hello retry request message */ 146 TRY_SEND_SERVER_HELLO, /* sends server hello message */ 147 TRY_SEND_HELLO_VERIFY_REQUEST, /* sends hello verify request message */ 148 TRY_SEND_ENCRYPTED_EXTENSIONS, /* sends encrypted extensions message */ 149 TRY_SEND_CERTIFICATE, /* sends certificate message */ 150 TRY_SEND_SERVER_KEY_EXCHANGE, /* sends server key exchange message */ 151 TRY_SEND_CERTIFICATE_REQUEST, /* sends certificate request message */ 152 TRY_SEND_SERVER_HELLO_DONE, /* sends server hello done message */ 153 TRY_SEND_CLIENT_KEY_EXCHANGE, /* sends client key exchange message */ 154 TRY_SEND_CERTIFICATE_VERIFY, /* sends certificate verify message */ 155 TRY_SEND_NEW_SESSION_TICKET, /* sends new session ticket message */ 156 TRY_SEND_CHANGE_CIPHER_SPEC, /* sends change cipher spec message */ 157 TRY_SEND_END_OF_EARLY_DATA, /* sends end of early data message */ 158 TRY_SEND_FINISH, /* sends finished message */ 159 TRY_SEND_KEY_UPDATE, /* sends keyupdate message */ 160 TRY_RECV_CLIENT_HELLO, /* attempts to receive client hello message */ 161 TRY_RECV_SERVER_HELLO, /* attempts to receive server hello message */ 162 TRY_RECV_HELLO_VERIFY_REQUEST, /* attempts to receive hello verify request message */ 163 TRY_RECV_ENCRYPTED_EXTENSIONS, /* attempts to receive encrypted extensions message */ 164 TRY_RECV_CERTIFICATE, /* attempts to receive certificate message */ 165 TRY_RECV_SERVER_KEY_EXCHANGE, /* attempts to receive server key exchange message */ 166 TRY_RECV_CERTIFICATE_REQUEST, /* attempts to receive certificate request message */ 167 TRY_RECV_SERVER_HELLO_DONE, /* attempts to receive server hello done message */ 168 TRY_RECV_CLIENT_KEY_EXCHANGE, /* attempts to receive client key exchange message */ 169 TRY_RECV_CERTIFICATE_VERIFY, /* attempts to receive certificate verify message */ 170 TRY_RECV_NEW_SESSION_TICKET, /* attempts to receive new session ticket message */ 171 TRY_RECV_END_OF_EARLY_DATA, /* attempts to receive end of early data message */ 172 TRY_RECV_FINISH, /* attempts to receive finished message */ 173 TRY_RECV_KEY_UPDATE, /* attempts to receive keyupdate message */ 174 TRY_RECV_HELLO_REQUEST, /* attempts to receive hello request message */ 175 HS_STATE_BUTT = 255 /* enumerated Maximum Value */ 176 } HITLS_HandshakeState; 177 178 typedef void (*SendAlertCallback)(const TLS_Ctx *ctx, ALERT_Level level, ALERT_Description description); 179 180 typedef bool (*GetAlertFlagCallback)(const TLS_Ctx *ctx); 181 182 typedef int32_t (*UnexpectMsgHandleCallback)(TLS_Ctx *ctx, uint32_t msgType, const uint8_t *data, uint32_t dataLen, 183 bool isPlain); 184 185 /** Connection management configure */ 186 typedef struct TLSCtxConfig { 187 void *userData; /* user data */ 188 uint16_t pmtu; /* Maximum transport unit of a path (bytes) */ 189 190 bool isSupportPto; /* is support process based TLS offload */ 191 uint8_t reserved[1]; /* four-byte alignment */ 192 193 TLS_Config tlsConfig; /* tls configure context */ 194 } TLS_CtxConfig; 195 196 typedef struct { 197 uint32_t algRemainTime; /* current key usage times */ 198 uint8_t preMacKey[MAC_KEY_LEN]; /* previous random key */ 199 uint8_t macKey[MAC_KEY_LEN]; /* random key used by the current algorithm */ 200 } CookieInfo; 201 202 typedef struct { 203 uint16_t version; /* negotiated version */ 204 uint16_t clientVersion; /* version field of client hello */ 205 uint32_t cookieSize; /* cookie length */ 206 uint8_t *cookie; /* cookie data */ 207 CookieInfo cookieInfo; /* cookie info with calculation and verification */ 208 CipherSuiteInfo cipherSuiteInfo; /* cipher suite info */ 209 HITLS_SignHashAlgo signScheme; /* sign algorithm used by the local */ 210 uint8_t *alpnSelected; /* alpn proto */ 211 uint32_t alpnSelectedSize; 212 uint8_t clientVerifyData[MAX_DIGEST_SIZE]; /* client verify data */ 213 uint8_t serverVerifyData[MAX_DIGEST_SIZE]; /* server verify data */ 214 uint8_t clientRandom[RANDOM_SIZE]; /* client random number */ 215 uint8_t serverRandom[RANDOM_SIZE]; /* server random number */ 216 uint32_t clientVerifyDataSize; /* client verify data size */ 217 uint32_t serverVerifyDataSize; /* server verify data size */ 218 uint32_t renegotiationNum; /* the number of renegotiation */ 219 uint32_t certReqSendTime; /* certificate request sending times */ 220 uint32_t tls13BasicKeyExMode; /* TLS13_KE_MODE_PSK_ONLY || TLS13_KE_MODE_PSK_WITH_DHE || 221 TLS13_CERT_AUTH_WITH_DHE */ 222 223 uint16_t negotiatedGroup; /* negotiated group */ 224 uint16_t recordSizeLimit; /* read record size limit */ 225 uint16_t renegoRecordSizeLimit; 226 uint16_t peerRecordSizeLimit; /* write record size limit */ 227 bool isResume; /* whether to resume the session */ 228 bool isRenegotiation; /* whether to renegotiate */ 229 230 bool isSecureRenegotiation; /* whether security renegotiation */ 231 bool isExtendedMasterSecret; /* whether to calculate the extended master sercret */ 232 bool isEncryptThenMac; /* Whether to enable EncryptThenMac */ 233 bool isEncryptThenMacRead; /* Whether to enable EncryptThenMacRead */ 234 bool isEncryptThenMacWrite; /* Whether to enable EncryptThenMacWrite */ 235 bool isTicket; /* whether to negotiate tickets, only below tls1.3 */ 236 bool isSniStateOK; /* Whether server successfully processes the server_name callback */ 237 } TLS_NegotiatedInfo; 238 239 typedef struct { 240 uint16_t *groups; /* all groups sent by the peer end */ 241 uint32_t groupsSize; /* size of a group */ 242 uint16_t *cipherSuites; /* all cipher suites sent by the peer end */ 243 uint16_t cipherSuitesSize; /* size of a cipher suites */ 244 HITLS_SignHashAlgo peerSignHashAlg; /* peer signature algorithm */ 245 HITLS_ERROR verifyResult; /* record the certificate verification result of the peer end */ 246 HITLS_TrustedCAList *caList; /* peer trusted ca list */ 247 } PeerInfo; 248 249 struct TlsCtx { 250 bool isClient; /* is Client */ 251 bool userShutDown; /* record whether the local end invokes the HITLS_Close */ 252 bool userRenego; /* record whether the local end initiates renegotiation */ 253 uint8_t rwstate; /* record the current internal read and write state */ 254 CM_State preState; 255 CM_State state; 256 257 uint32_t shutdownState; /* Record the shutdown state */ 258 259 void *rUio; /* read uio */ 260 void *uio; /* write uio */ 261 void *bUio; /* Storing uio */ 262 HS_Ctx *hsCtx; /* handshake context */ 263 CCS_Ctx *ccsCtx; /* ChangeCipherSpec context */ 264 ALERT_Ctx *alertCtx; /* alert context */ 265 REC_Ctx *recCtx; /* record context */ 266 struct { 267 IsRecvCcsCallback isRecvCCS; 268 SendCcsCallback sendCCS; /* send a CCS message */ 269 CtrlCcsCallback ctrlCCS; /* controlling CCS */ 270 SendAlertCallback sendAlert; /* set the alert message to be sent */ 271 GetAlertFlagCallback getAlertFlag; /* get alert state */ 272 UnexpectMsgHandleCallback unexpectedMsgProcessCb; /* the callback for unexpected messages */ 273 } method; 274 275 PeerInfo peerInfo; /* Temporarily save the messages sent by the peer end */ 276 TLS_CtxConfig config; /* private configuration */ 277 TLS_Config *globalConfig; /* global configuration */ 278 TLS_NegotiatedInfo negotiatedInfo; /* TLS negotiation information */ 279 HITLS_Session *session; /* session information */ 280 281 uint8_t clientAppTrafficSecret[MAX_DIGEST_SIZE]; /* TLS1.3 client app traffic secret */ 282 uint8_t serverAppTrafficSecret[MAX_DIGEST_SIZE]; /* TLS1.3 server app traffic secret */ 283 uint8_t resumptionMasterSecret[MAX_DIGEST_SIZE]; /* TLS1.3 session resume secret */ 284 285 uint32_t bytesLeftToRead; /* bytes left to read after hs header has parsed */ 286 uint32_t keyUpdateType; /* TLS1.3 key update type */ 287 bool isKeyUpdateRequest; /* TLS1.3 Check whether there are unsent key update messages */ 288 bool haveClientPointFormats; /* whether the EC point format extension in the client hello is processed */ 289 uint8_t peekFlag; /* peekFlag equals 0, read mode; otherwise, peek mode */ 290 bool hasParsedHsMsgHeader; /* has parsed current hs msg header */ 291 int32_t errorCode; /* Record the tls error code */ 292 293 HITLS_HASH_Ctx *phaHash; /* tls1.3 pha: Handshake main process hash */ 294 HITLS_HASH_Ctx *phaCurHash; /* tls1.3 pha: Temporarily store the current pha hash */ 295 PHA_State phaState; /* tls1.3 pha state */ 296 uint8_t *certificateReqCtx; /* tls1.3 pha certificate_request_context */ 297 uint32_t certificateReqCtxSize; /* tls1.3 pha certificate_request_context */ 298 bool isDtlsListen; 299 bool plainAlertForbid; /* tls1.3 forbid to receive plain alert message */ 300 bool allowAppOut; /* whether user used HITLS_read to start renegotiation */ 301 }; 302 303 #define LIBCTX_FROM_CTX(ctx) ((ctx == NULL) ? NULL : (ctx)->config.tlsConfig.libCtx) 304 #define ATTRIBUTE_FROM_CTX(ctx) ((ctx == NULL) ? NULL : (ctx)->config.tlsConfig.attrName) 305 306 #define CUSTOM_EXT_FROM_CTX(ctx) ((ctx == NULL) ? NULL : (ctx)->config.tlsConfig.customExts) 307 308 #ifdef __cplusplus 309 } 310 #endif 311 312 #endif /* TLS_H */ 313