| Hanno Becker | be9d664 | 2020-08-21 13:20:06 +0100 | [diff] [blame] | 1 | /* | 
|  | 2 | *  TLS 1.3 key schedule | 
|  | 3 | * | 
|  | 4 | *  Copyright The Mbed TLS Contributors | 
|  | 5 | *  SPDX-License-Identifier: Apache-2.0 | 
|  | 6 | * | 
|  | 7 | *  Licensed under the Apache License, Version 2.0 ( the "License" ); you may | 
|  | 8 | *  not use this file except in compliance with the License. | 
|  | 9 | *  You may obtain a copy of the License at | 
|  | 10 | * | 
|  | 11 | *  http://www.apache.org/licenses/LICENSE-2.0 | 
|  | 12 | * | 
|  | 13 | *  Unless required by applicable law or agreed to in writing, software | 
|  | 14 | *  distributed under the License is distributed on an "AS IS" BASIS, WITHOUT | 
|  | 15 | *  WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | 
|  | 16 | *  See the License for the specific language governing permissions and | 
|  | 17 | *  limitations under the License. | 
|  | 18 | */ | 
|  | 19 | #if !defined(MBEDTLS_SSL_TLS1_3_KEYS_H) | 
|  | 20 | #define MBEDTLS_SSL_TLS1_3_KEYS_H | 
|  | 21 |  | 
| Hanno Becker | 70d7fb0 | 2020-09-09 10:11:21 +0100 | [diff] [blame] | 22 | /* This requires MBEDTLS_SSL_TLS1_3_LABEL( idx, name, string ) to be defined at | 
| Hanno Becker | a3a5a4e | 2020-09-08 11:33:48 +0100 | [diff] [blame] | 23 | * the point of use. See e.g. the definition of mbedtls_ssl_tls1_3_labels_union | 
|  | 24 | * below. */ | 
| Hanno Becker | e4435ea | 2020-09-08 10:43:52 +0100 | [diff] [blame] | 25 | #define MBEDTLS_SSL_TLS1_3_LABEL_LIST                               \ | 
| Hanno Becker | 1413bd8 | 2020-09-09 12:46:09 +0100 | [diff] [blame] | 26 | MBEDTLS_SSL_TLS1_3_LABEL( finished    , "finished"     ) \ | 
|  | 27 | MBEDTLS_SSL_TLS1_3_LABEL( resumption  , "resumption"   ) \ | 
|  | 28 | MBEDTLS_SSL_TLS1_3_LABEL( traffic_upd , "traffic upd"  ) \ | 
|  | 29 | MBEDTLS_SSL_TLS1_3_LABEL( exporter    , "exporter"     ) \ | 
|  | 30 | MBEDTLS_SSL_TLS1_3_LABEL( key         , "key"          ) \ | 
|  | 31 | MBEDTLS_SSL_TLS1_3_LABEL( iv          , "iv"           ) \ | 
|  | 32 | MBEDTLS_SSL_TLS1_3_LABEL( c_hs_traffic, "c hs traffic" ) \ | 
|  | 33 | MBEDTLS_SSL_TLS1_3_LABEL( c_ap_traffic, "c ap traffic" ) \ | 
|  | 34 | MBEDTLS_SSL_TLS1_3_LABEL( c_e_traffic , "c e traffic"  ) \ | 
|  | 35 | MBEDTLS_SSL_TLS1_3_LABEL( s_hs_traffic, "s hs traffic" ) \ | 
|  | 36 | MBEDTLS_SSL_TLS1_3_LABEL( s_ap_traffic, "s ap traffic" ) \ | 
|  | 37 | MBEDTLS_SSL_TLS1_3_LABEL( s_e_traffic , "s e traffic"  ) \ | 
|  | 38 | MBEDTLS_SSL_TLS1_3_LABEL( e_exp_master, "e exp master" ) \ | 
|  | 39 | MBEDTLS_SSL_TLS1_3_LABEL( res_master  , "res master"   ) \ | 
|  | 40 | MBEDTLS_SSL_TLS1_3_LABEL( exp_master  , "exp master"   ) \ | 
|  | 41 | MBEDTLS_SSL_TLS1_3_LABEL( ext_binder  , "ext binder"   ) \ | 
|  | 42 | MBEDTLS_SSL_TLS1_3_LABEL( res_binder  , "res binder"   ) \ | 
|  | 43 | MBEDTLS_SSL_TLS1_3_LABEL( derived     , "derived"      ) | 
| Hanno Becker | e4435ea | 2020-09-08 10:43:52 +0100 | [diff] [blame] | 44 |  | 
| Hanno Becker | 1413bd8 | 2020-09-09 12:46:09 +0100 | [diff] [blame] | 45 | #define MBEDTLS_SSL_TLS1_3_LABEL( name, string )       \ | 
| Hanno Becker | e4435ea | 2020-09-08 10:43:52 +0100 | [diff] [blame] | 46 | const unsigned char name    [ sizeof(string) - 1 ]; | 
| Hanno Becker | be9d664 | 2020-08-21 13:20:06 +0100 | [diff] [blame] | 47 |  | 
|  | 48 | union mbedtls_ssl_tls1_3_labels_union | 
|  | 49 | { | 
|  | 50 | MBEDTLS_SSL_TLS1_3_LABEL_LIST | 
|  | 51 | }; | 
|  | 52 | struct mbedtls_ssl_tls1_3_labels_struct | 
|  | 53 | { | 
|  | 54 | MBEDTLS_SSL_TLS1_3_LABEL_LIST | 
|  | 55 | }; | 
| Hanno Becker | a3a5a4e | 2020-09-08 11:33:48 +0100 | [diff] [blame] | 56 | #undef MBEDTLS_SSL_TLS1_3_LABEL | 
| Hanno Becker | e4435ea | 2020-09-08 10:43:52 +0100 | [diff] [blame] | 57 |  | 
| Hanno Becker | be9d664 | 2020-08-21 13:20:06 +0100 | [diff] [blame] | 58 | extern const struct mbedtls_ssl_tls1_3_labels_struct mbedtls_ssl_tls1_3_labels; | 
|  | 59 |  | 
|  | 60 | #define MBEDTLS_SSL_TLS1_3_LBL_WITH_LEN( LABEL )  \ | 
|  | 61 | mbedtls_ssl_tls1_3_labels.LABEL,              \ | 
|  | 62 | sizeof(mbedtls_ssl_tls1_3_labels.LABEL) | 
|  | 63 |  | 
|  | 64 | #define MBEDTLS_SSL_TLS1_3_KEY_SCHEDULE_MAX_LABEL_LEN  \ | 
|  | 65 | sizeof( union mbedtls_ssl_tls1_3_labels_union ) | 
|  | 66 |  | 
| Hanno Becker | 61baae7 | 2020-09-16 09:24:14 +0100 | [diff] [blame] | 67 | /* The maximum length of HKDF contexts used in the TLS 1.3 standard. | 
| Hanno Becker | be9d664 | 2020-08-21 13:20:06 +0100 | [diff] [blame] | 68 | * Since contexts are always hashes of message transcripts, this can | 
|  | 69 | * be approximated from above by the maximum hash size. */ | 
|  | 70 | #define MBEDTLS_SSL_TLS1_3_KEY_SCHEDULE_MAX_CONTEXT_LEN  \ | 
|  | 71 | MBEDTLS_MD_MAX_SIZE | 
|  | 72 |  | 
|  | 73 | /* Maximum desired length for expanded key material generated | 
| Hanno Becker | 531fe30 | 2020-09-16 09:45:27 +0100 | [diff] [blame] | 74 | * by HKDF-Expand-Label. | 
|  | 75 | * | 
|  | 76 | * Warning: If this ever needs to be increased, the implementation | 
|  | 77 | * ssl_tls1_3_hkdf_encode_label() in ssl_tls13_keys.c needs to be | 
|  | 78 | * adjusted since it currently assumes that HKDF key expansion | 
|  | 79 | * is never used with more than 255 Bytes of output. */ | 
| Hanno Becker | be9d664 | 2020-08-21 13:20:06 +0100 | [diff] [blame] | 80 | #define MBEDTLS_SSL_TLS1_3_KEY_SCHEDULE_MAX_EXPANSION_LEN 255 | 
|  | 81 |  | 
|  | 82 | /** | 
|  | 83 | * \brief           The \c HKDF-Expand-Label function from | 
|  | 84 | *                  the TLS 1.3 standard RFC 8446. | 
|  | 85 | * | 
|  | 86 | * <tt> | 
|  | 87 | *                  HKDF-Expand-Label( Secret, Label, Context, Length ) = | 
|  | 88 | *                       HKDF-Expand( Secret, HkdfLabel, Length ) | 
|  | 89 | * </tt> | 
|  | 90 | * | 
|  | 91 | * \param hash_alg  The identifier for the hash algorithm to use. | 
|  | 92 | * \param secret    The \c Secret argument to \c HKDF-Expand-Label. | 
|  | 93 | *                  This must be a readable buffer of length \p slen Bytes. | 
|  | 94 | * \param slen      The length of \p secret in Bytes. | 
|  | 95 | * \param label     The \c Label argument to \c HKDF-Expand-Label. | 
|  | 96 | *                  This must be a readable buffer of length \p llen Bytes. | 
|  | 97 | * \param llen      The length of \p label in Bytes. | 
|  | 98 | * \param ctx       The \c Context argument to \c HKDF-Expand-Label. | 
|  | 99 | *                  This must be a readable buffer of length \p clen Bytes. | 
|  | 100 | * \param clen      The length of \p context in Bytes. | 
|  | 101 | * \param buf       The destination buffer to hold the expanded secret. | 
| Hanno Becker | 61baae7 | 2020-09-16 09:24:14 +0100 | [diff] [blame] | 102 | *                  This must be a writable buffer of length \p blen Bytes. | 
| Hanno Becker | be9d664 | 2020-08-21 13:20:06 +0100 | [diff] [blame] | 103 | * \param blen      The desired size of the expanded secret in Bytes. | 
|  | 104 | * | 
|  | 105 | * \returns         \c 0 on success. | 
|  | 106 | * \return          A negative error code on failure. | 
|  | 107 | */ | 
|  | 108 |  | 
|  | 109 | int mbedtls_ssl_tls1_3_hkdf_expand_label( | 
|  | 110 | mbedtls_md_type_t hash_alg, | 
|  | 111 | const unsigned char *secret, size_t slen, | 
|  | 112 | const unsigned char *label, size_t llen, | 
|  | 113 | const unsigned char *ctx, size_t clen, | 
|  | 114 | unsigned char *buf, size_t blen ); | 
|  | 115 |  | 
| Hanno Becker | 3385a4d | 2020-08-21 13:03:34 +0100 | [diff] [blame] | 116 | /** | 
|  | 117 | * \brief           This function is part of the TLS 1.3 key schedule. | 
|  | 118 | *                  It extracts key and IV for the actual client/server traffic | 
|  | 119 | *                  from the client/server traffic secrets. | 
|  | 120 | * | 
|  | 121 | * From RFC 8446: | 
|  | 122 | * | 
|  | 123 | * <tt> | 
|  | 124 | *   [sender]_write_key = HKDF-Expand-Label(Secret, "key", "", key_length) | 
|  | 125 | *   [sender]_write_iv  = HKDF-Expand-Label(Secret, "iv", "", iv_length)* | 
|  | 126 | * </tt> | 
|  | 127 | * | 
|  | 128 | * \param hash_alg      The identifier for the hash algorithm to be used | 
|  | 129 | *                      for the HKDF-based expansion of the secret. | 
|  | 130 | * \param client_secret The client traffic secret. | 
|  | 131 | *                      This must be a readable buffer of size \p slen Bytes | 
|  | 132 | * \param server_secret The server traffic secret. | 
|  | 133 | *                      This must be a readable buffer of size \p slen Bytes | 
|  | 134 | * \param slen          Length of the secrets \p client_secret and | 
|  | 135 | *                      \p server_secret in Bytes. | 
| Hanno Becker | 493ea7f | 2020-09-08 11:01:00 +0100 | [diff] [blame] | 136 | * \param key_len       The desired length of the key to be extracted in Bytes. | 
|  | 137 | * \param iv_len        The desired length of the IV to be extracted in Bytes. | 
| Hanno Becker | 3385a4d | 2020-08-21 13:03:34 +0100 | [diff] [blame] | 138 | * \param keys          The address of the structure holding the generated | 
|  | 139 | *                      keys and IVs. | 
|  | 140 | * | 
|  | 141 | * \returns             \c 0 on success. | 
|  | 142 | * \returns             A negative error code on failure. | 
|  | 143 | */ | 
|  | 144 |  | 
|  | 145 | int mbedtls_ssl_tls1_3_make_traffic_keys( | 
|  | 146 | mbedtls_md_type_t hash_alg, | 
|  | 147 | const unsigned char *client_secret, | 
|  | 148 | const unsigned char *server_secret, | 
| Hanno Becker | 493ea7f | 2020-09-08 11:01:00 +0100 | [diff] [blame] | 149 | size_t slen, size_t key_len, size_t iv_len, | 
| Hanno Becker | 3385a4d | 2020-08-21 13:03:34 +0100 | [diff] [blame] | 150 | mbedtls_ssl_key_set *keys ); | 
|  | 151 |  | 
| Hanno Becker | 0973ff9 | 2020-09-09 12:56:28 +0100 | [diff] [blame] | 152 |  | 
|  | 153 | #define MBEDTLS_SSL_TLS1_3_CONTEXT_UNHASHED 0 | 
|  | 154 | #define MBEDTLS_SSL_TLS1_3_CONTEXT_HASHED   1 | 
|  | 155 |  | 
| Hanno Becker | b35d522 | 2020-08-21 13:27:44 +0100 | [diff] [blame] | 156 | /** | 
|  | 157 | * \brief The \c Derive-Secret function from the TLS 1.3 standard RFC 8446. | 
|  | 158 | * | 
|  | 159 | * <tt> | 
|  | 160 | *   Derive-Secret( Secret, Label, Messages ) = | 
|  | 161 | *      HKDF-Expand-Label( Secret, Label, | 
|  | 162 | *                         Hash( Messages ), | 
|  | 163 | *                         Hash.Length ) ) | 
|  | 164 | * </tt> | 
|  | 165 | * | 
| Hanno Becker | 0c42fd9 | 2020-09-09 12:58:29 +0100 | [diff] [blame] | 166 | * \param hash_alg   The identifier for the hash function used for the | 
|  | 167 | *                   applications of HKDF. | 
|  | 168 | * \param secret     The \c Secret argument to the \c Derive-Secret function. | 
|  | 169 | *                   This must be a readable buffer of length \p slen Bytes. | 
|  | 170 | * \param slen       The length of \p secret in Bytes. | 
|  | 171 | * \param label      The \c Label argument to the \c Derive-Secret function. | 
|  | 172 | *                   This must be a readable buffer of length \p llen Bytes. | 
|  | 173 | * \param llen       The length of \p label in Bytes. | 
|  | 174 | * \param ctx        The hash of the \c Messages argument to the | 
|  | 175 | *                   \c Derive-Secret function, or the \c Messages argument | 
|  | 176 | *                   itself, depending on \p context_already_hashed. | 
|  | 177 | * \param clen       The length of \p hash. | 
|  | 178 | * \param ctx_hashed This indicates whether the \p ctx contains the hash of | 
|  | 179 | *                   the \c Messages argument in the application of the | 
|  | 180 | *                   \c Derive-Secret function | 
|  | 181 | *                   (value MBEDTLS_SSL_TLS1_3_CONTEXT_HASHED), or whether | 
|  | 182 | *                   it is the content of \c Messages itself, in which case | 
|  | 183 | *                   the function takes care of the hashing | 
|  | 184 | *                   (value MBEDTLS_SSL_TLS1_3_CONTEXT_UNHASHED). | 
|  | 185 | * \param dstbuf     The target buffer to write the output of | 
|  | 186 | *                   \c Derive-Secret to. This must be a writable buffer of | 
|  | 187 | *                   size \p buflen Bytes. | 
|  | 188 | * \param buflen     The length of \p dstbuf in Bytes. | 
| Hanno Becker | b35d522 | 2020-08-21 13:27:44 +0100 | [diff] [blame] | 189 | * | 
|  | 190 | * \returns        \c 0 on success. | 
|  | 191 | * \returns        A negative error code on failure. | 
|  | 192 | */ | 
| Hanno Becker | b35d522 | 2020-08-21 13:27:44 +0100 | [diff] [blame] | 193 | int mbedtls_ssl_tls1_3_derive_secret( | 
|  | 194 | mbedtls_md_type_t hash_alg, | 
|  | 195 | const unsigned char *secret, size_t slen, | 
|  | 196 | const unsigned char *label, size_t llen, | 
|  | 197 | const unsigned char *ctx, size_t clen, | 
| Hanno Becker | 0c42fd9 | 2020-09-09 12:58:29 +0100 | [diff] [blame] | 198 | int ctx_hashed, | 
| Hanno Becker | b35d522 | 2020-08-21 13:27:44 +0100 | [diff] [blame] | 199 | unsigned char *dstbuf, size_t buflen ); | 
|  | 200 |  | 
| Hanno Becker | e9cccb4 | 2020-08-20 13:42:46 +0100 | [diff] [blame] | 201 | /** | 
|  | 202 | * \brief Compute the next secret in the TLS 1.3 key schedule | 
|  | 203 | * | 
|  | 204 | * The TLS 1.3 key schedule proceeds as follows to compute | 
|  | 205 | * the three main secrets during the handshake: The early | 
|  | 206 | * secret for early data, the handshake secret for all | 
|  | 207 | * other encrypted handshake messages, and the master | 
|  | 208 | * secret for all application traffic. | 
|  | 209 | * | 
|  | 210 | * <tt> | 
|  | 211 | *                    0 | 
|  | 212 | *                    | | 
|  | 213 | *                    v | 
|  | 214 | *     PSK ->  HKDF-Extract = Early Secret | 
|  | 215 | *                    | | 
|  | 216 | *                    v | 
|  | 217 | *     Derive-Secret( ., "derived", "" ) | 
|  | 218 | *                    | | 
|  | 219 | *                    v | 
|  | 220 | *  (EC)DHE -> HKDF-Extract = Handshake Secret | 
|  | 221 | *                    | | 
|  | 222 | *                    v | 
|  | 223 | *     Derive-Secret( ., "derived", "" ) | 
|  | 224 | *                    | | 
|  | 225 | *                    v | 
|  | 226 | *     0 -> HKDF-Extract = Master Secret | 
|  | 227 | * </tt> | 
|  | 228 | * | 
|  | 229 | * Each of the three secrets in turn is the basis for further | 
|  | 230 | * key derivations, such as the derivation of traffic keys and IVs; | 
|  | 231 | * see e.g. mbedtls_ssl_tls1_3_make_traffic_keys(). | 
|  | 232 | * | 
|  | 233 | * This function implements one step in this evolution of secrets: | 
|  | 234 | * | 
|  | 235 | * <tt> | 
|  | 236 | *                old_secret | 
|  | 237 | *                    | | 
|  | 238 | *                    v | 
|  | 239 | *     Derive-Secret( ., "derived", "" ) | 
|  | 240 | *                    | | 
|  | 241 | *                    v | 
|  | 242 | *     input -> HKDF-Extract = new_secret | 
|  | 243 | * </tt> | 
|  | 244 | * | 
|  | 245 | * \param hash_alg    The identifier for the hash function used for the | 
|  | 246 | *                    applications of HKDF. | 
|  | 247 | * \param secret_old  The address of the buffer holding the old secret | 
|  | 248 | *                    on function entry. If not \c NULL, this must be a | 
|  | 249 | *                    readable buffer whose size matches the output size | 
|  | 250 | *                    of the hash function represented by \p hash_alg. | 
|  | 251 | *                    If \c NULL, an all \c 0 array will be used instead. | 
|  | 252 | * \param input       The address of the buffer holding the additional | 
|  | 253 | *                    input for the key derivation (e.g., the PSK or the | 
|  | 254 | *                    ephemeral (EC)DH secret). If not \c NULL, this must be | 
|  | 255 | *                    a readable buffer whose size \p input_len Bytes. | 
|  | 256 | *                    If \c NULL, an all \c 0 array will be used instead. | 
|  | 257 | * \param input_len   The length of \p input in Bytes. | 
|  | 258 | * \param secret_new  The address of the buffer holding the new secret | 
|  | 259 | *                    on function exit. This must be a writable buffer | 
|  | 260 | *                    whose size matches the output size of the hash | 
|  | 261 | *                    function represented by \p hash_alg. | 
|  | 262 | *                    This may be the same as \p secret_old. | 
|  | 263 | * | 
|  | 264 | * \returns           \c 0 on success. | 
|  | 265 | * \returns           A negative error code on failure. | 
|  | 266 | */ | 
|  | 267 |  | 
|  | 268 | int mbedtls_ssl_tls1_3_evolve_secret( | 
|  | 269 | mbedtls_md_type_t hash_alg, | 
|  | 270 | const unsigned char *secret_old, | 
|  | 271 | const unsigned char *input, size_t input_len, | 
|  | 272 | unsigned char *secret_new ); | 
|  | 273 |  | 
| Hanno Becker | be9d664 | 2020-08-21 13:20:06 +0100 | [diff] [blame] | 274 | #endif /* MBEDTLS_SSL_TLS1_3_KEYS_H */ |