Branch data Line data Source code
1 : : /*
2 : : * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
3 : : *
4 : : * Licensed under the Apache License, Version 2.0 (the "License").
5 : : * You may not use this file except in compliance with the License.
6 : : * A copy of the License is located at
7 : : *
8 : : * http://aws.amazon.com/apache2.0
9 : : *
10 : : * or in the "license" file accompanying this file. This file is distributed
11 : : * on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either
12 : : * express or implied. See the License for the specific language governing
13 : : * permissions and limitations under the License.
14 : : */
15 : :
16 : : #include "tls/s2n_kem_preferences.h"
17 : :
18 : : #include "tls/s2n_kem.h"
19 : :
20 : : const struct s2n_kem *pq_kems_r3_2021_05[] = {
21 : : /* Round 3 Algorithms */
22 : : &s2n_kyber_512_r3,
23 : : };
24 : :
25 : : const struct s2n_kem_group *pq_kem_groups_r3_2021_05[] = {
26 : : &s2n_x25519_kyber_512_r3,
27 : : &s2n_secp256r1_kyber_512_r3,
28 : : };
29 : :
30 : : const struct s2n_kem_group *pq_kem_groups_r3_2023_06[] = {
31 : : &s2n_secp256r1_kyber_768_r3,
32 : : &s2n_x25519_kyber_768_r3,
33 : : &s2n_secp384r1_kyber_768_r3,
34 : : &s2n_secp521r1_kyber_1024_r3,
35 : : &s2n_secp256r1_kyber_512_r3,
36 : : &s2n_x25519_kyber_512_r3,
37 : : };
38 : :
39 : : const struct s2n_kem_group *pq_kem_groups_r3_2023_12[] = {
40 : : &s2n_secp256r1_kyber_768_r3,
41 : : &s2n_secp384r1_kyber_768_r3,
42 : : &s2n_secp521r1_kyber_1024_r3,
43 : : &s2n_secp256r1_kyber_512_r3,
44 : : };
45 : :
46 : : /* Includes only IETF standard KEM Groups. */
47 : : const struct s2n_kem_group *pq_kem_groups_ietf_2024_10[] = {
48 : : &s2n_x25519_mlkem_768,
49 : : &s2n_secp256r1_mlkem_768,
50 : : };
51 : :
52 : : const struct s2n_kem_group *pq_kem_groups_ietf_2025_07[] = {
53 : : &s2n_x25519_mlkem_768,
54 : : &s2n_secp256r1_mlkem_768,
55 : : &s2n_secp384r1_mlkem_1024,
56 : : };
57 : :
58 : : /* Includes both IETF standard KEM Groups, and earlier draft standards with Kyber. */
59 : : const struct s2n_kem_group *pq_kem_groups_mixed_2024_10[] = {
60 : : &s2n_x25519_mlkem_768,
61 : : &s2n_secp256r1_mlkem_768,
62 : : &s2n_secp256r1_kyber_768_r3,
63 : : &s2n_x25519_kyber_768_r3,
64 : : &s2n_secp384r1_kyber_768_r3,
65 : : &s2n_secp521r1_kyber_1024_r3,
66 : : &s2n_secp256r1_kyber_512_r3,
67 : : &s2n_x25519_kyber_512_r3,
68 : : };
69 : :
70 : : const struct s2n_kem_preferences kem_preferences_pq_tls_1_0_2021_05 = {
71 : : .kem_count = 0,
72 : : .kems = NULL,
73 : : .tls13_kem_group_count = s2n_array_len(pq_kem_groups_r3_2021_05),
74 : : .tls13_kem_groups = pq_kem_groups_r3_2021_05,
75 : : .tls13_pq_hybrid_draft_revision = 0
76 : : };
77 : :
78 : : const struct s2n_kem_preferences kem_preferences_pq_tls_1_0_2023_01 = {
79 : : .kem_count = 0,
80 : : .kems = NULL,
81 : : .tls13_kem_group_count = s2n_array_len(pq_kem_groups_r3_2021_05),
82 : : .tls13_kem_groups = pq_kem_groups_r3_2021_05,
83 : : .tls13_pq_hybrid_draft_revision = 5
84 : : };
85 : :
86 : : /* TLS 1.3 specifies KEMS via SupportedGroups extension, not TLS 1.2's KEM-specific extension. */
87 : : const struct s2n_kem_preferences kem_preferences_pq_tls_1_3_2023_06 = {
88 : : .kem_count = 0,
89 : : .kems = NULL,
90 : : .tls13_kem_group_count = s2n_array_len(pq_kem_groups_r3_2023_06),
91 : : .tls13_kem_groups = pq_kem_groups_r3_2023_06,
92 : : .tls13_pq_hybrid_draft_revision = 5
93 : : };
94 : :
95 : : /* Same as kem_preferences_pq_tls_1_3_2023_06, but without x25519 */
96 : : const struct s2n_kem_preferences kem_preferences_pq_tls_1_3_2023_12 = {
97 : : .kem_count = 0,
98 : : .kems = NULL,
99 : : .tls13_kem_group_count = s2n_array_len(pq_kem_groups_r3_2023_12),
100 : : .tls13_kem_groups = pq_kem_groups_r3_2023_12,
101 : : .tls13_pq_hybrid_draft_revision = 5
102 : : };
103 : :
104 : : const struct s2n_kem_preferences kem_preferences_pq_tls_1_3_ietf_2024_10 = {
105 : : .kem_count = 0,
106 : : .kems = NULL,
107 : : .tls13_kem_group_count = s2n_array_len(pq_kem_groups_ietf_2024_10),
108 : : .tls13_kem_groups = pq_kem_groups_ietf_2024_10,
109 : : .tls13_pq_hybrid_draft_revision = 5
110 : : };
111 : :
112 : : const struct s2n_kem_preferences kem_preferences_pq_tls_1_3_ietf_2025_07 = {
113 : : .kem_count = 0,
114 : : .kems = NULL,
115 : : .tls13_kem_group_count = s2n_array_len(pq_kem_groups_ietf_2025_07),
116 : : .tls13_kem_groups = pq_kem_groups_ietf_2025_07,
117 : : .tls13_pq_hybrid_draft_revision = 5
118 : : };
119 : :
120 : : const struct s2n_kem_preferences kem_preferences_pq_tls_1_3_mixed_2024_10 = {
121 : : .kem_count = 0,
122 : : .kems = NULL,
123 : : .tls13_kem_group_count = s2n_array_len(pq_kem_groups_mixed_2024_10),
124 : : .tls13_kem_groups = pq_kem_groups_mixed_2024_10,
125 : : .tls13_pq_hybrid_draft_revision = 5
126 : : };
127 : :
128 : : const struct s2n_kem_preferences kem_preferences_all = {
129 : : .kem_count = 0,
130 : : .kems = NULL,
131 : : .tls13_kem_group_count = S2N_KEM_GROUPS_COUNT,
132 : : .tls13_kem_groups = ALL_SUPPORTED_KEM_GROUPS,
133 : : .tls13_pq_hybrid_draft_revision = 5
134 : : };
135 : :
136 : : const struct s2n_kem_preferences kem_preferences_null = {
137 : : .kem_count = 0,
138 : : .kems = NULL,
139 : : .tls13_kem_group_count = 0,
140 : : .tls13_kem_groups = NULL,
141 : : .tls13_pq_hybrid_draft_revision = 0
142 : : };
143 : :
144 : : /* Determines if query_iana_id corresponds to a tls13_kem_group for these KEM preferences. */
145 : : bool s2n_kem_preferences_includes_tls13_kem_group(const struct s2n_kem_preferences *kem_preferences,
146 : : uint16_t query_iana_id)
147 : 21 : {
148 [ - + ]: 21 : if (kem_preferences == NULL) {
149 : 0 : return false;
150 : 0 : }
151 : :
152 [ + + ]: 57 : for (size_t i = 0; i < kem_preferences->tls13_kem_group_count; i++) {
153 [ + + ]: 46 : if (query_iana_id == kem_preferences->tls13_kem_groups[i]->iana_id) {
154 : 10 : return true;
155 : 10 : }
156 : 46 : }
157 : :
158 : 11 : return false;
159 : 21 : }
160 : :
161 : : /* Whether the client must include the length prefix in the PQ TLS 1.3 KEM KeyShares that it sends. Draft 0 of
162 : : * the PQ TLS 1.3 standard required length prefixing, and drafts 1-5 removed this length prefix. To not break
163 : : * backwards compatibility, we check what revision of the draft standard is configured to determine whether to send it. */
164 : : bool s2n_tls13_client_must_use_hybrid_kem_length_prefix(const struct s2n_kem_preferences *kem_pref)
165 : 15 : {
166 [ + - ][ - + ]: 15 : return kem_pref && (kem_pref->tls13_pq_hybrid_draft_revision == 0);
167 : 15 : }
168 : :
169 : : S2N_RESULT s2n_kem_preferences_groups_available(const struct s2n_kem_preferences *kem_preferences, uint32_t *groups_available)
170 : 131 : {
171 [ # # ][ - + ]: 131 : RESULT_ENSURE_REF(kem_preferences);
172 [ - + ][ # # ]: 131 : RESULT_ENSURE_REF(groups_available);
173 : :
174 : 131 : uint32_t count = 0;
175 [ + + ]: 308 : for (int i = 0; i < kem_preferences->tls13_kem_group_count; i++) {
176 [ - + ]: 177 : if (s2n_kem_group_is_available(kem_preferences->tls13_kem_groups[i])) {
177 : 0 : count++;
178 : 0 : }
179 : 177 : }
180 : 131 : *groups_available = count;
181 : 131 : return S2N_RESULT_OK;
182 : 131 : }
183 : :
184 : : const struct s2n_kem_group *s2n_kem_preferences_get_highest_priority_group(const struct s2n_kem_preferences *kem_preferences)
185 : 1 : {
186 [ - + ][ # # ]: 1 : PTR_ENSURE_REF(kem_preferences);
187 [ + + ]: 10 : for (size_t i = 0; i < kem_preferences->tls13_kem_group_count; i++) {
188 [ - + ]: 9 : if (s2n_kem_group_is_available(kem_preferences->tls13_kem_groups[i])) {
189 : 0 : return kem_preferences->tls13_kem_groups[i];
190 : 0 : }
191 : 9 : }
192 : 1 : return NULL;
193 : 1 : }
|