]> git.saurik.com Git - apple/security.git/blob - protocol/SecProtocolHelper.m
Security-59306.11.20.tar.gz
[apple/security.git] / protocol / SecProtocolHelper.m
1 //
2 // SecProtocolHelper.m
3 // Security_ios
4 //
5 //
6
7 #import "SecProtocolInternal.h"
8
9 #define DefineTLSCiphersuiteGroupList(XXX, ...) \
10 static const tls_ciphersuite_t List##XXX[] = { \
11 __VA_ARGS__ \
12 };
13
14 DefineTLSCiphersuiteGroupList(tls_ciphersuite_group_default,
15 CiphersuitesTLS13,
16 CiphersuitesPFS);
17 DefineTLSCiphersuiteGroupList(tls_ciphersuite_group_compatibility,
18 CiphersuitesNonPFS,
19 CiphersuitesTLS10,
20 CiphersuitesTLS10_3DES);
21 DefineTLSCiphersuiteGroupList(tls_ciphersuite_group_legacy,
22 CiphersuitesDHE);
23 DefineTLSCiphersuiteGroupList(tls_ciphersuite_group_ats,
24 CiphersuitesTLS13,
25 CiphersuitesPFS);
26 DefineTLSCiphersuiteGroupList(tls_ciphersuite_group_ats_compatibility,
27 CiphersuitesNonPFS);
28
29 typedef struct tls_ciphersuite_definition {
30 tls_ciphersuite_t ciphersuite;
31 tls_protocol_version_t min_version;
32 tls_protocol_version_t max_version;
33 char ciphersuite_name[64];
34 } *tls_ciphersuite_definition_t;
35
36 #define DefineTLSCiphersuiteDefinition(XXX, MIN_VERSION, MAX_VERSION) \
37 { \
38 .ciphersuite = XXX, \
39 .ciphersuite_name = "##XXX", \
40 .min_version = MIN_VERSION, \
41 .max_version = MAX_VERSION, \
42 }
43
44 static const struct tls_ciphersuite_definition tls_ciphersuite_definitions[] = {
45 // TLS 1.3 ciphersuites
46 DefineTLSCiphersuiteDefinition(TLS_AES_128_GCM_SHA256, tls_protocol_version_TLSv13, tls_protocol_version_TLSv13),
47 DefineTLSCiphersuiteDefinition(TLS_AES_256_GCM_SHA384, tls_protocol_version_TLSv13, tls_protocol_version_TLSv13),
48 DefineTLSCiphersuiteDefinition(TLS_CHACHA20_POLY1305_SHA256, tls_protocol_version_TLSv13, tls_protocol_version_TLSv13),
49
50 // RFC 7905: ChaCha20-Poly1305 Cipher Suites for Transport Layer Security (TLS)
51 DefineTLSCiphersuiteDefinition(TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256, tls_protocol_version_TLSv12, tls_protocol_version_TLSv12),
52 DefineTLSCiphersuiteDefinition(TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256, tls_protocol_version_TLSv12, tls_protocol_version_TLSv12),
53
54 // RFC 5289: TLS Elliptic Curve Cipher Suites with SHA-256/384 and AES Galois Counter Mode (GCM)
55 DefineTLSCiphersuiteDefinition(TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384, tls_protocol_version_TLSv12, tls_protocol_version_TLSv12),
56 DefineTLSCiphersuiteDefinition(TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, tls_protocol_version_TLSv12, tls_protocol_version_TLSv12),
57 DefineTLSCiphersuiteDefinition(TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384, tls_protocol_version_TLSv12, tls_protocol_version_TLSv12),
58 DefineTLSCiphersuiteDefinition(TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256, tls_protocol_version_TLSv12, tls_protocol_version_TLSv12),
59 DefineTLSCiphersuiteDefinition(TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384, tls_protocol_version_TLSv12, tls_protocol_version_TLSv12),
60 DefineTLSCiphersuiteDefinition(TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256, tls_protocol_version_TLSv12, tls_protocol_version_TLSv12),
61 DefineTLSCiphersuiteDefinition(TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384, tls_protocol_version_TLSv12, tls_protocol_version_TLSv12),
62 DefineTLSCiphersuiteDefinition(TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256, tls_protocol_version_TLSv12, tls_protocol_version_TLSv12),
63
64 // RFC 5288: AES Galois Counter Mode (GCM) Cipher Suites for TLS
65 DefineTLSCiphersuiteDefinition(TLS_RSA_WITH_AES_256_GCM_SHA384, tls_protocol_version_TLSv12, tls_protocol_version_TLSv12),
66 DefineTLSCiphersuiteDefinition(TLS_RSA_WITH_AES_128_GCM_SHA256, tls_protocol_version_TLSv12, tls_protocol_version_TLSv12),
67 DefineTLSCiphersuiteDefinition(TLS_DHE_RSA_WITH_AES_256_GCM_SHA384, tls_protocol_version_TLSv12, tls_protocol_version_TLSv12),
68 DefineTLSCiphersuiteDefinition(TLS_DHE_RSA_WITH_AES_128_GCM_SHA256, tls_protocol_version_TLSv12, tls_protocol_version_TLSv12),
69
70 // RFC 5246: The Transport Layer Security (TLS) Protocol Version 1.2
71 DefineTLSCiphersuiteDefinition(TLS_RSA_WITH_AES_256_CBC_SHA256, tls_protocol_version_TLSv12, tls_protocol_version_TLSv12),
72 DefineTLSCiphersuiteDefinition(TLS_RSA_WITH_AES_128_CBC_SHA256, tls_protocol_version_TLSv12, tls_protocol_version_TLSv12),
73 DefineTLSCiphersuiteDefinition(SSL_DHE_RSA_WITH_3DES_EDE_CBC_SHA, tls_protocol_version_TLSv12, tls_protocol_version_TLSv12),
74 DefineTLSCiphersuiteDefinition(SSL_RSA_WITH_3DES_EDE_CBC_SHA, tls_protocol_version_TLSv12, tls_protocol_version_TLSv12),
75 DefineTLSCiphersuiteDefinition(TLS_DHE_RSA_WITH_AES_256_CBC_SHA256, tls_protocol_version_TLSv12, tls_protocol_version_TLSv12),
76 DefineTLSCiphersuiteDefinition(TLS_DHE_RSA_WITH_AES_128_CBC_SHA256, tls_protocol_version_TLSv12, tls_protocol_version_TLSv12),
77
78 // RFC 4492: Elliptic Curve Cryptography (ECC) Cipher Suites for Transport Layer Security (TLS)
79 DefineTLSCiphersuiteDefinition(TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA, tls_protocol_version_TLSv10, tls_protocol_version_TLSv11),
80 DefineTLSCiphersuiteDefinition(TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA, tls_protocol_version_TLSv10, tls_protocol_version_TLSv11),
81 DefineTLSCiphersuiteDefinition(TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA, tls_protocol_version_TLSv10, tls_protocol_version_TLSv11),
82 DefineTLSCiphersuiteDefinition(TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA, tls_protocol_version_TLSv10, tls_protocol_version_TLSv11),
83 DefineTLSCiphersuiteDefinition(TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA, tls_protocol_version_TLSv10, tls_protocol_version_TLSv11),
84 DefineTLSCiphersuiteDefinition(TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA, tls_protocol_version_TLSv10, tls_protocol_version_TLSv11),
85
86 // RFC 3268: Advanced Encryption Standard (AES) Ciphersuites for Transport Layer Security (TLS)
87 DefineTLSCiphersuiteDefinition(TLS_RSA_WITH_AES_256_CBC_SHA, tls_protocol_version_TLSv10, tls_protocol_version_TLSv11),
88 DefineTLSCiphersuiteDefinition(TLS_RSA_WITH_AES_128_CBC_SHA, tls_protocol_version_TLSv10, tls_protocol_version_TLSv11),
89 DefineTLSCiphersuiteDefinition(TLS_RSA_WITH_AES_256_CBC_SHA, tls_protocol_version_TLSv10, tls_protocol_version_TLSv11),
90 DefineTLSCiphersuiteDefinition(TLS_DHE_RSA_WITH_AES_256_CBC_SHA, tls_protocol_version_TLSv10, tls_protocol_version_TLSv11),
91 DefineTLSCiphersuiteDefinition(TLS_RSA_WITH_AES_128_CBC_SHA, tls_protocol_version_TLSv10, tls_protocol_version_TLSv11),
92 DefineTLSCiphersuiteDefinition(TLS_DHE_RSA_WITH_AES_128_CBC_SHA, tls_protocol_version_TLSv10, tls_protocol_version_TLSv11),
93 DefineTLSCiphersuiteDefinition(TLS_DHE_RSA_WITH_AES_256_CBC_SHA, tls_protocol_version_TLSv10, tls_protocol_version_TLSv11),
94 DefineTLSCiphersuiteDefinition(TLS_DHE_RSA_WITH_AES_128_CBC_SHA, tls_protocol_version_TLSv10, tls_protocol_version_TLSv11),
95 };
96
97 // Size of the definition list
98 static const size_t tls_ciphersuite_definitions_length = \
99 sizeof(tls_ciphersuite_definitions) / sizeof(struct tls_ciphersuite_definition);
100
101 // Remove macro definitions
102 #undef CiphersuitesTLS13
103 #undef CiphersuitesPFS
104 #undef CiphersuitesNonPFS
105 #undef CiphersuitesTLS10_3DES
106 #undef CiphersuitesTLS10
107 #undef CiphersuitesDHE
108 #undef DefineTLSCiphersuiteGroupList
109 #undef DefineTLSCiphersuiteDefinition
110
111 const tls_ciphersuite_t *
112 sec_protocol_helper_ciphersuite_group_to_ciphersuite_list(tls_ciphersuite_group_t group, size_t *list_count)
113 {
114 if (list_count == NULL) {
115 return NULL;
116 }
117
118 const tls_ciphersuite_t *ciphersuites = NULL;
119 size_t count = 0;
120
121 #define CASE_CONFIG(GROUPNAME) \
122 case GROUPNAME: \
123 ciphersuites = List##GROUPNAME; \
124 count = sizeof(List##GROUPNAME) / sizeof(tls_ciphersuite_t); \
125 break;
126
127 switch (group) {
128 CASE_CONFIG(tls_ciphersuite_group_default);
129 CASE_CONFIG(tls_ciphersuite_group_compatibility);
130 CASE_CONFIG(tls_ciphersuite_group_legacy);
131 CASE_CONFIG(tls_ciphersuite_group_ats);
132 CASE_CONFIG(tls_ciphersuite_group_ats_compatibility);
133 }
134
135 #undef CASE_CONFIG
136
137 if (ciphersuites != NULL) {
138 *list_count = count;
139 return ciphersuites;
140 }
141
142 *list_count = 0;
143 return NULL;
144 }
145
146 bool
147 sec_protocol_helper_ciphersuite_group_contains_ciphersuite(tls_ciphersuite_group_t group, tls_ciphersuite_t suite)
148 {
149 size_t list_size = 0;
150 const tls_ciphersuite_t *list = sec_protocol_helper_ciphersuite_group_to_ciphersuite_list(group, &list_size);
151 if (list == NULL) {
152 return false;
153 }
154
155 for (size_t i = 0; i < list_size; i++) {
156 tls_ciphersuite_t other = list[i];
157 if (other == suite) {
158 return true;
159 }
160 }
161
162 return false;
163 }
164
165 tls_protocol_version_t
166 sec_protocol_helper_ciphersuite_minimum_TLS_version(tls_ciphersuite_t ciphersuite)
167 {
168 for (size_t i = 0; i < tls_ciphersuite_definitions_length; i++) {
169 if (tls_ciphersuite_definitions[i].ciphersuite == ciphersuite) {
170 return tls_ciphersuite_definitions[i].min_version;
171 }
172 }
173 return 0;
174 }
175
176 tls_protocol_version_t
177 sec_protocol_helper_ciphersuite_maximum_TLS_version(tls_ciphersuite_t ciphersuite)
178 {
179 for (size_t i = 0; i < tls_ciphersuite_definitions_length; i++) {
180 if (tls_ciphersuite_definitions[i].ciphersuite == ciphersuite) {
181 return tls_ciphersuite_definitions[i].max_version;
182 }
183 }
184 return 0;
185 }
186
187 const char *
188 sec_protocol_helper_get_ciphersuite_name(tls_ciphersuite_t ciphersuite)
189 {
190 #define CIPHERSUITE_TO_NAME(ciphersuite) \
191 case ciphersuite: { \
192 return #ciphersuite; \
193 }
194
195 switch (ciphersuite) {
196 CIPHERSUITE_TO_NAME(TLS_AES_128_GCM_SHA256);
197 CIPHERSUITE_TO_NAME(TLS_AES_256_GCM_SHA384);
198 CIPHERSUITE_TO_NAME(TLS_CHACHA20_POLY1305_SHA256);
199 CIPHERSUITE_TO_NAME(TLS_RSA_WITH_AES_256_GCM_SHA384);
200 CIPHERSUITE_TO_NAME(TLS_RSA_WITH_AES_128_GCM_SHA256);
201 CIPHERSUITE_TO_NAME(TLS_RSA_WITH_AES_256_CBC_SHA256);
202 CIPHERSUITE_TO_NAME(TLS_RSA_WITH_AES_128_CBC_SHA256);
203 CIPHERSUITE_TO_NAME(TLS_RSA_WITH_AES_256_CBC_SHA);
204 CIPHERSUITE_TO_NAME(TLS_RSA_WITH_AES_128_CBC_SHA);
205 CIPHERSUITE_TO_NAME(TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA);
206 CIPHERSUITE_TO_NAME(TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA);
207 CIPHERSUITE_TO_NAME(TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA);
208 CIPHERSUITE_TO_NAME(TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA);
209 CIPHERSUITE_TO_NAME(TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA);
210 CIPHERSUITE_TO_NAME(TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA);
211 CIPHERSUITE_TO_NAME(SSL_RSA_WITH_3DES_EDE_CBC_SHA);
212 CIPHERSUITE_TO_NAME(TLS_DHE_RSA_WITH_AES_256_GCM_SHA384);
213 CIPHERSUITE_TO_NAME(TLS_DHE_RSA_WITH_AES_128_GCM_SHA256);
214 CIPHERSUITE_TO_NAME(TLS_DHE_RSA_WITH_AES_256_CBC_SHA256);
215 CIPHERSUITE_TO_NAME(TLS_DHE_RSA_WITH_AES_128_CBC_SHA256);
216 CIPHERSUITE_TO_NAME(TLS_DHE_RSA_WITH_AES_256_CBC_SHA);
217 CIPHERSUITE_TO_NAME(TLS_DHE_RSA_WITH_AES_128_CBC_SHA);
218 CIPHERSUITE_TO_NAME(SSL_DHE_RSA_WITH_3DES_EDE_CBC_SHA);
219 CIPHERSUITE_TO_NAME(TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384);
220 CIPHERSUITE_TO_NAME(TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256);
221 CIPHERSUITE_TO_NAME(TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384);
222 CIPHERSUITE_TO_NAME(TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256);
223 CIPHERSUITE_TO_NAME(TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256);
224 CIPHERSUITE_TO_NAME(TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384);
225 CIPHERSUITE_TO_NAME(TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256);
226 CIPHERSUITE_TO_NAME(TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384);
227 CIPHERSUITE_TO_NAME(TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256);
228 CIPHERSUITE_TO_NAME(TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256);
229 }
230
231 #undef CIPHERSUITE_TO_NAME
232 return NULL;
233 }
234
235 #define KeyExchangeGroupsDefault \
236 tls_key_exchange_group_X25519, \
237 tls_key_exchange_group_X448
238 #define KeyExchangeGroupsCompatibility \
239 tls_key_exchange_group_Secp256r1, \
240 tls_key_exchange_group_Secp384r1, \
241 tls_key_exchange_group_Secp521r1
242 #define KeyExchangeGroupsLegacy \
243 tls_key_exchange_group_FFDHE2048, \
244 tls_key_exchange_group_FFDHE3072, \
245 tls_key_exchange_group_FFDHE4096, \
246 tls_key_exchange_group_FFDHE6144, \
247 tls_key_exchange_group_FFDHE8192
248
249 #define DefineTLSKeyExchangeGroupList(XXX, ...) \
250 static const tls_key_exchange_group_t List##XXX[] = { \
251 __VA_ARGS__ \
252 };
253
254 DefineTLSKeyExchangeGroupList(tls_key_exchange_group_set_default,
255 KeyExchangeGroupsDefault);
256 DefineTLSKeyExchangeGroupList(tls_key_exchange_group_set_compatibility,
257 KeyExchangeGroupsCompatibility);
258 DefineTLSKeyExchangeGroupList(tls_key_exchange_group_set_legacy,
259 KeyExchangeGroupsLegacy);
260
261 const tls_key_exchange_group_t *
262 sec_protocol_helper_tls_key_exchange_group_set_to_key_exchange_group_list(tls_key_exchange_group_set_t set, size_t *listSize)
263 {
264 if (listSize == NULL) {
265 return NULL;
266 }
267
268 const tls_key_exchange_group_t *groups = NULL;
269 size_t count = 0;
270
271 #define CASE_CONFIG(SETNAME) \
272 case SETNAME: \
273 groups = List##SETNAME; \
274 count = sizeof(List##SETNAME) / sizeof(SSLKeyExchangeGroup); \
275 break;
276
277 switch (set) {
278 CASE_CONFIG(tls_key_exchange_group_set_default);
279 CASE_CONFIG(tls_key_exchange_group_set_compatibility);
280 CASE_CONFIG(tls_key_exchange_group_set_legacy);
281 }
282
283 #undef CASE_CONFIG
284
285 if (groups != NULL) {
286 *listSize = count;
287 return groups;
288 }
289
290 *listSize = 0;
291 return NULL;
292 }
293
294 #undef DefineTLSKeyExchangeGroupList
295 #undef KeyExchangeGroupsDefault
296 #undef KeyExchangeGroupsCompatibility
297 #undef KeyExchangeGroupsLegacy
298
299 bool
300 sec_protocol_helper_dispatch_data_equal(dispatch_data_t left, dispatch_data_t right)
301 {
302 if (!left || !right || left == right) {
303 return left == right;
304 }
305 if (dispatch_data_get_size(left) != dispatch_data_get_size(right)) {
306 return false;
307 }
308 __block bool is_equal = true;
309 dispatch_data_apply(left,
310 ^bool(__unused dispatch_data_t _Nonnull lregion, size_t loffset, const void *_Nonnull lbuffer, size_t lsize) {
311 dispatch_data_apply(right,
312 ^bool(__unused dispatch_data_t _Nonnull rregion, size_t roffset, const void *_Nonnull rbuffer,
313 size_t rsize) {
314 // There is some overlap
315 const size_t start = MAX(loffset, roffset);
316 const size_t end = MIN(loffset + lsize, roffset + rsize);
317 if (start < end) {
318 is_equal = memcmp(&((const uint8_t *)rbuffer)[start - roffset],
319 &((const uint8_t *)lbuffer)[start - loffset], end - start) == 0;
320 } else {
321 if (roffset > loffset + lsize) {
322 // Iteration of right has gone past where we're at on left, bail out of inner apply
323 // left |---|
324 // right |---|
325 return false;
326 } else if (roffset + rsize < loffset) {
327 // Iteration of right has not yet reached where we're at on left, keep going
328 // left |---|
329 // right |--|
330 return true;
331 }
332 }
333
334 return is_equal;
335 });
336 return is_equal;
337 });
338 return is_equal;
339 }