blob: 0c376b875891d0bd084181a2a32453fd8ba7b4a5 [file] [log] [blame]
David Benjamin2e521212014-07-16 14:37:51 -04001/* Copyright (c) 2014, Google Inc.
2 *
3 * Permission to use, copy, modify, and/or distribute this software for any
4 * purpose with or without fee is hereby granted, provided that the above
5 * copyright notice and this permission notice appear in all copies.
6 *
7 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
8 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
9 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
10 * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
11 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
12 * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
13 * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */
14
15#include <stdio.h>
David Benjamin751e8892014-10-19 00:59:36 -040016#include <string.h>
David Benjamin1269ddd2015-10-18 15:18:55 -040017#include <time.h>
David Benjamin2e521212014-07-16 14:37:51 -040018
David Benjamin0f653952015-10-18 14:28:01 -040019#include <algorithm>
David Benjamin1d77e562015-03-22 17:22:08 -040020#include <string>
David Benjamin4f6acaf2015-11-21 03:00:50 -050021#include <utility>
David Benjamin1d77e562015-03-22 17:22:08 -040022#include <vector>
23
David Benjamin751e8892014-10-19 00:59:36 -040024#include <openssl/base64.h>
25#include <openssl/bio.h>
David Benjamin3c51d9b2016-11-01 17:50:42 -040026#include <openssl/cipher.h>
David Benjamin7a1eefd2015-10-17 23:39:22 -040027#include <openssl/crypto.h>
David Benjaminbb0a17c2014-09-20 15:35:39 -040028#include <openssl/err.h>
David Benjamin3c51d9b2016-11-01 17:50:42 -040029#include <openssl/hmac.h>
David Benjaminde942382016-02-11 12:02:01 -050030#include <openssl/pem.h>
David Benjamin25490f22016-07-14 00:22:54 -040031#include <openssl/sha.h>
David Benjaminbb0a17c2014-09-20 15:35:39 -040032#include <openssl/ssl.h>
David Benjamin3c51d9b2016-11-01 17:50:42 -040033#include <openssl/rand.h>
David Benjaminde942382016-02-11 12:02:01 -050034#include <openssl/x509.h>
David Benjaminbb0a17c2014-09-20 15:35:39 -040035
Steven Valdez87eab492016-06-27 16:34:59 -040036#include "internal.h"
Steven Valdezcb966542016-08-17 16:56:14 -040037#include "../crypto/internal.h"
Sigbjorn Vik2b23d242015-06-29 15:07:26 +020038#include "../crypto/test/test_util.h"
39
David Benjamin721e8b72016-08-03 13:13:17 -040040#if defined(OPENSSL_WINDOWS)
41/* Windows defines struct timeval in winsock2.h. */
42OPENSSL_MSVC_PRAGMA(warning(push, 3))
43#include <winsock2.h>
44OPENSSL_MSVC_PRAGMA(warning(pop))
45#else
46#include <sys/time.h>
47#endif
48
David Benjamin1d77e562015-03-22 17:22:08 -040049
50struct ExpectedCipher {
51 unsigned long id;
David Benjaminbb0a17c2014-09-20 15:35:39 -040052 int in_group_flag;
David Benjamin1d77e562015-03-22 17:22:08 -040053};
David Benjaminbb0a17c2014-09-20 15:35:39 -040054
David Benjamin1d77e562015-03-22 17:22:08 -040055struct CipherTest {
56 // The rule string to apply.
David Benjaminbb0a17c2014-09-20 15:35:39 -040057 const char *rule;
David Benjaminfb974e62015-12-16 19:34:22 -050058 // The list of expected ciphers, in order.
59 std::vector<ExpectedCipher> expected;
David Benjamin1d77e562015-03-22 17:22:08 -040060};
David Benjaminbb0a17c2014-09-20 15:35:39 -040061
Alessandro Ghedini5fd18072016-09-28 21:04:25 +010062struct CurveTest {
63 // The rule string to apply.
64 const char *rule;
65 // The list of expected curves, in order.
66 std::vector<uint16_t> expected;
67};
68
David Benjaminfb974e62015-12-16 19:34:22 -050069static const CipherTest kCipherTests[] = {
70 // Selecting individual ciphers should work.
71 {
72 "ECDHE-ECDSA-CHACHA20-POLY1305:"
73 "ECDHE-RSA-CHACHA20-POLY1305:"
74 "ECDHE-ECDSA-AES128-GCM-SHA256:"
75 "ECDHE-RSA-AES128-GCM-SHA256",
76 {
77 {TLS1_CK_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256, 0},
78 {TLS1_CK_ECDHE_ECDSA_CHACHA20_POLY1305_OLD, 0},
79 {TLS1_CK_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256, 0},
80 {TLS1_CK_ECDHE_RSA_CHACHA20_POLY1305_OLD, 0},
81 {TLS1_CK_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, 0},
82 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 0},
83 },
84 },
85 // + reorders selected ciphers to the end, keeping their relative order.
86 {
87 "ECDHE-ECDSA-CHACHA20-POLY1305:"
88 "ECDHE-RSA-CHACHA20-POLY1305:"
89 "ECDHE-ECDSA-AES128-GCM-SHA256:"
90 "ECDHE-RSA-AES128-GCM-SHA256:"
91 "+aRSA",
92 {
93 {TLS1_CK_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256, 0},
94 {TLS1_CK_ECDHE_ECDSA_CHACHA20_POLY1305_OLD, 0},
95 {TLS1_CK_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, 0},
96 {TLS1_CK_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256, 0},
97 {TLS1_CK_ECDHE_RSA_CHACHA20_POLY1305_OLD, 0},
98 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 0},
99 },
100 },
101 // ! banishes ciphers from future selections.
102 {
103 "!aRSA:"
104 "ECDHE-ECDSA-CHACHA20-POLY1305:"
105 "ECDHE-RSA-CHACHA20-POLY1305:"
106 "ECDHE-ECDSA-AES128-GCM-SHA256:"
107 "ECDHE-RSA-AES128-GCM-SHA256",
108 {
109 {TLS1_CK_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256, 0},
110 {TLS1_CK_ECDHE_ECDSA_CHACHA20_POLY1305_OLD, 0},
111 {TLS1_CK_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, 0},
112 },
113 },
114 // Multiple masks can be ANDed in a single rule.
115 {
116 "kRSA+AESGCM+AES128",
117 {
118 {TLS1_CK_RSA_WITH_AES_128_GCM_SHA256, 0},
119 },
120 },
121 // - removes selected ciphers, but preserves their order for future
122 // selections. Select AES_128_GCM, but order the key exchanges RSA, DHE_RSA,
123 // ECDHE_RSA.
124 {
125 "ALL:-kECDHE:-kDHE:-kRSA:-ALL:"
126 "AESGCM+AES128+aRSA",
127 {
128 {TLS1_CK_RSA_WITH_AES_128_GCM_SHA256, 0},
129 {TLS1_CK_DHE_RSA_WITH_AES_128_GCM_SHA256, 0},
130 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 0},
131 },
132 },
133 // Unknown selectors are no-ops.
134 {
135 "ECDHE-ECDSA-CHACHA20-POLY1305:"
136 "ECDHE-RSA-CHACHA20-POLY1305:"
137 "ECDHE-ECDSA-AES128-GCM-SHA256:"
138 "ECDHE-RSA-AES128-GCM-SHA256:"
139 "BOGUS1:-BOGUS2:+BOGUS3:!BOGUS4",
140 {
141 {TLS1_CK_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256, 0},
142 {TLS1_CK_ECDHE_ECDSA_CHACHA20_POLY1305_OLD, 0},
143 {TLS1_CK_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256, 0},
144 {TLS1_CK_ECDHE_RSA_CHACHA20_POLY1305_OLD, 0},
145 {TLS1_CK_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, 0},
146 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 0},
147 },
148 },
149 // Square brackets specify equi-preference groups.
150 {
151 "[ECDHE-ECDSA-CHACHA20-POLY1305|ECDHE-ECDSA-AES128-GCM-SHA256]:"
152 "[ECDHE-RSA-CHACHA20-POLY1305]:"
153 "ECDHE-RSA-AES128-GCM-SHA256",
154 {
155 {TLS1_CK_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256, 1},
156 {TLS1_CK_ECDHE_ECDSA_CHACHA20_POLY1305_OLD, 1},
157 {TLS1_CK_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, 0},
158 {TLS1_CK_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256, 1},
159 {TLS1_CK_ECDHE_RSA_CHACHA20_POLY1305_OLD, 0},
160 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 0},
161 },
162 },
163 // @STRENGTH performs a stable strength-sort of the selected ciphers and
164 // only the selected ciphers.
165 {
166 // To simplify things, banish all but {ECDHE_RSA,RSA} x
Matthew Braithwaite8aaa9e12016-09-07 15:09:58 -0700167 // {CHACHA20,AES_256_CBC,AES_128_CBC} x SHA1.
David Benjaminfb974e62015-12-16 19:34:22 -0500168 "!kEDH:!AESGCM:!3DES:!SHA256:!MD5:!SHA384:"
169 // Order some ciphers backwards by strength.
Matthew Braithwaite8aaa9e12016-09-07 15:09:58 -0700170 "ALL:-CHACHA20:-AES256:-AES128:-ALL:"
David Benjaminfb974e62015-12-16 19:34:22 -0500171 // Select ECDHE ones and sort them by strength. Ties should resolve
172 // based on the order above.
173 "kECDHE:@STRENGTH:-ALL:"
174 // Now bring back everything uses RSA. ECDHE_RSA should be first, sorted
175 // by strength. Then RSA, backwards by strength.
176 "aRSA",
177 {
178 {TLS1_CK_ECDHE_RSA_WITH_AES_256_CBC_SHA, 0},
179 {TLS1_CK_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256, 0},
180 {TLS1_CK_ECDHE_RSA_CHACHA20_POLY1305_OLD, 0},
David Benjaminfb974e62015-12-16 19:34:22 -0500181 {TLS1_CK_ECDHE_RSA_WITH_AES_128_CBC_SHA, 0},
David Benjaminfb974e62015-12-16 19:34:22 -0500182 {TLS1_CK_RSA_WITH_AES_128_SHA, 0},
183 {TLS1_CK_RSA_WITH_AES_256_SHA, 0},
184 },
185 },
186 // Exact ciphers may not be used in multi-part rules; they are treated
187 // as unknown aliases.
188 {
189 "ECDHE-ECDSA-AES128-GCM-SHA256:"
190 "ECDHE-RSA-AES128-GCM-SHA256:"
191 "!ECDHE-RSA-AES128-GCM-SHA256+RSA:"
192 "!ECDSA+ECDHE-ECDSA-AES128-GCM-SHA256",
193 {
194 {TLS1_CK_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, 0},
195 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 0},
196 },
197 },
198 // SSLv3 matches everything that existed before TLS 1.2.
199 {
200 "AES128-SHA:AES128-SHA256:!SSLv3",
201 {
202 {TLS1_CK_RSA_WITH_AES_128_SHA256, 0},
203 },
204 },
205 // TLSv1.2 matches everything added in TLS 1.2.
206 {
207 "AES128-SHA:AES128-SHA256:!TLSv1.2",
208 {
209 {TLS1_CK_RSA_WITH_AES_128_SHA, 0},
210 },
211 },
212 // The two directives have no intersection.
213 {
214 "AES128-SHA:AES128-SHA256:!TLSv1.2+SSLv3",
215 {
216 {TLS1_CK_RSA_WITH_AES_128_SHA, 0},
217 {TLS1_CK_RSA_WITH_AES_128_SHA256, 0},
218 },
219 },
220 // The shared name of the CHACHA20_POLY1305 variants behaves like a cipher
221 // name and not an alias. It may not be used in a multipart rule. (That the
222 // shared name works is covered by the standard tests.)
223 {
224 "ECDHE-ECDSA-CHACHA20-POLY1305:"
225 "ECDHE-RSA-CHACHA20-POLY1305:"
226 "!ECDHE-RSA-CHACHA20-POLY1305+RSA:"
227 "!ECDSA+ECDHE-ECDSA-CHACHA20-POLY1305",
228 {
229 {TLS1_CK_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256, 0},
230 {TLS1_CK_ECDHE_ECDSA_CHACHA20_POLY1305_OLD, 0},
231 {TLS1_CK_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256, 0},
232 {TLS1_CK_ECDHE_RSA_CHACHA20_POLY1305_OLD, 0},
233 },
234 },
David Benjaminbb0a17c2014-09-20 15:35:39 -0400235};
236
237static const char *kBadRules[] = {
David Benjamin1d77e562015-03-22 17:22:08 -0400238 // Invalid brackets.
David Benjaminbb0a17c2014-09-20 15:35:39 -0400239 "[ECDHE-RSA-CHACHA20-POLY1305|ECDHE-RSA-AES128-GCM-SHA256",
240 "RSA]",
241 "[[RSA]]",
David Benjamin1d77e562015-03-22 17:22:08 -0400242 // Operators inside brackets.
David Benjaminbb0a17c2014-09-20 15:35:39 -0400243 "[+RSA]",
David Benjamin1d77e562015-03-22 17:22:08 -0400244 // Unknown directive.
David Benjaminbb0a17c2014-09-20 15:35:39 -0400245 "@BOGUS",
David Benjamin1d77e562015-03-22 17:22:08 -0400246 // Empty cipher lists error at SSL_CTX_set_cipher_list.
David Benjaminbb0a17c2014-09-20 15:35:39 -0400247 "",
248 "BOGUS",
David Benjamin32fbdf22015-04-07 01:14:06 -0400249 // COMPLEMENTOFDEFAULT is empty.
250 "COMPLEMENTOFDEFAULT",
David Benjamin1d77e562015-03-22 17:22:08 -0400251 // Invalid command.
David Benjaminbb0a17c2014-09-20 15:35:39 -0400252 "?BAR",
David Benjamin1d77e562015-03-22 17:22:08 -0400253 // Special operators are not allowed if groups are used.
David Benjamin37d92462014-09-20 17:54:24 -0400254 "[ECDHE-RSA-CHACHA20-POLY1305|ECDHE-RSA-AES128-GCM-SHA256]:+FOO",
255 "[ECDHE-RSA-CHACHA20-POLY1305|ECDHE-RSA-AES128-GCM-SHA256]:!FOO",
256 "[ECDHE-RSA-CHACHA20-POLY1305|ECDHE-RSA-AES128-GCM-SHA256]:-FOO",
257 "[ECDHE-RSA-CHACHA20-POLY1305|ECDHE-RSA-AES128-GCM-SHA256]:@STRENGTH",
Adam Langleyf99f2442016-10-02 09:53:38 -0700258 // Opcode supplied, but missing selector.
259 "+",
David Benjaminbb0a17c2014-09-20 15:35:39 -0400260};
261
Matt Braithwaiteaf096752015-09-02 19:48:16 -0700262static const char *kMustNotIncludeNull[] = {
263 "ALL",
264 "DEFAULT",
265 "ALL:!eNULL",
266 "ALL:!NULL",
David Benjamind6e9eec2015-11-18 09:48:55 -0500267 "HIGH",
Matt Braithwaiteaf096752015-09-02 19:48:16 -0700268 "FIPS",
269 "SHA",
270 "SHA1",
271 "RSA",
272 "SSLv3",
273 "TLSv1",
274 "TLSv1.2",
Matt Braithwaiteaf096752015-09-02 19:48:16 -0700275};
276
Alessandro Ghedini5fd18072016-09-28 21:04:25 +0100277static const CurveTest kCurveTests[] = {
278 {
279 "P-256",
280 { SSL_CURVE_SECP256R1 },
281 },
282 {
283 "P-256:P-384:P-521:X25519",
284 {
285 SSL_CURVE_SECP256R1,
286 SSL_CURVE_SECP384R1,
287 SSL_CURVE_SECP521R1,
288 SSL_CURVE_X25519,
289 },
290 },
291};
292
293static const char *kBadCurvesLists[] = {
294 "",
295 ":",
296 "::",
297 "P-256::X25519",
298 "RSA:P-256",
299 "P-256:RSA",
300 "X25519:P-256:",
301 ":X25519:P-256",
302};
303
David Benjamin1d77e562015-03-22 17:22:08 -0400304static void PrintCipherPreferenceList(ssl_cipher_preference_list_st *list) {
305 bool in_group = false;
306 for (size_t i = 0; i < sk_SSL_CIPHER_num(list->ciphers); i++) {
David Benjaminbb0a17c2014-09-20 15:35:39 -0400307 const SSL_CIPHER *cipher = sk_SSL_CIPHER_value(list->ciphers, i);
308 if (!in_group && list->in_group_flags[i]) {
309 fprintf(stderr, "\t[\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400310 in_group = true;
David Benjaminbb0a17c2014-09-20 15:35:39 -0400311 }
312 fprintf(stderr, "\t");
313 if (in_group) {
314 fprintf(stderr, " ");
315 }
316 fprintf(stderr, "%s\n", SSL_CIPHER_get_name(cipher));
317 if (in_group && !list->in_group_flags[i]) {
318 fprintf(stderr, "\t]\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400319 in_group = false;
David Benjaminbb0a17c2014-09-20 15:35:39 -0400320 }
321 }
322}
323
David Benjaminfb974e62015-12-16 19:34:22 -0500324static bool TestCipherRule(const CipherTest &t) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700325 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
David Benjamin1d77e562015-03-22 17:22:08 -0400326 if (!ctx) {
327 return false;
David Benjamin65226252015-02-05 16:49:47 -0500328 }
329
David Benjaminfb974e62015-12-16 19:34:22 -0500330 if (!SSL_CTX_set_cipher_list(ctx.get(), t.rule)) {
331 fprintf(stderr, "Error testing cipher rule '%s'\n", t.rule);
David Benjamin1d77e562015-03-22 17:22:08 -0400332 return false;
David Benjaminbb0a17c2014-09-20 15:35:39 -0400333 }
334
David Benjamin1d77e562015-03-22 17:22:08 -0400335 // Compare the two lists.
David Benjaminfb974e62015-12-16 19:34:22 -0500336 if (sk_SSL_CIPHER_num(ctx->cipher_list->ciphers) != t.expected.size()) {
337 fprintf(stderr, "Error: cipher rule '%s' evaluated to:\n", t.rule);
338 PrintCipherPreferenceList(ctx->cipher_list);
339 return false;
340 }
341
342 for (size_t i = 0; i < t.expected.size(); i++) {
David Benjaminbb0a17c2014-09-20 15:35:39 -0400343 const SSL_CIPHER *cipher =
344 sk_SSL_CIPHER_value(ctx->cipher_list->ciphers, i);
David Benjaminfb974e62015-12-16 19:34:22 -0500345 if (t.expected[i].id != SSL_CIPHER_get_id(cipher) ||
346 t.expected[i].in_group_flag != ctx->cipher_list->in_group_flags[i]) {
347 fprintf(stderr, "Error: cipher rule '%s' evaluated to:\n", t.rule);
David Benjamin1d77e562015-03-22 17:22:08 -0400348 PrintCipherPreferenceList(ctx->cipher_list);
349 return false;
David Benjaminbb0a17c2014-09-20 15:35:39 -0400350 }
351 }
352
David Benjamin1d77e562015-03-22 17:22:08 -0400353 return true;
David Benjaminbb0a17c2014-09-20 15:35:39 -0400354}
355
Matt Braithwaiteaf096752015-09-02 19:48:16 -0700356static bool TestRuleDoesNotIncludeNull(const char *rule) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700357 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(SSLv23_server_method()));
Matt Braithwaiteaf096752015-09-02 19:48:16 -0700358 if (!ctx) {
359 return false;
360 }
361 if (!SSL_CTX_set_cipher_list(ctx.get(), rule)) {
362 fprintf(stderr, "Error: cipher rule '%s' failed\n", rule);
363 return false;
364 }
365 for (size_t i = 0; i < sk_SSL_CIPHER_num(ctx->cipher_list->ciphers); i++) {
366 if (SSL_CIPHER_is_NULL(sk_SSL_CIPHER_value(ctx->cipher_list->ciphers, i))) {
367 fprintf(stderr, "Error: cipher rule '%s' includes NULL\n",rule);
368 return false;
369 }
370 }
371 return true;
372}
373
David Benjamin1d77e562015-03-22 17:22:08 -0400374static bool TestCipherRules() {
David Benjaminfb974e62015-12-16 19:34:22 -0500375 for (const CipherTest &test : kCipherTests) {
376 if (!TestCipherRule(test)) {
David Benjamin1d77e562015-03-22 17:22:08 -0400377 return false;
David Benjaminbb0a17c2014-09-20 15:35:39 -0400378 }
379 }
380
David Benjaminfb974e62015-12-16 19:34:22 -0500381 for (const char *rule : kBadRules) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700382 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(SSLv23_server_method()));
David Benjamin1d77e562015-03-22 17:22:08 -0400383 if (!ctx) {
384 return false;
David Benjamin65226252015-02-05 16:49:47 -0500385 }
David Benjaminfb974e62015-12-16 19:34:22 -0500386 if (SSL_CTX_set_cipher_list(ctx.get(), rule)) {
387 fprintf(stderr, "Cipher rule '%s' unexpectedly succeeded\n", rule);
David Benjamin1d77e562015-03-22 17:22:08 -0400388 return false;
David Benjaminbb0a17c2014-09-20 15:35:39 -0400389 }
390 ERR_clear_error();
David Benjaminbb0a17c2014-09-20 15:35:39 -0400391 }
392
David Benjaminfb974e62015-12-16 19:34:22 -0500393 for (const char *rule : kMustNotIncludeNull) {
394 if (!TestRuleDoesNotIncludeNull(rule)) {
Matt Braithwaiteaf096752015-09-02 19:48:16 -0700395 return false;
396 }
397 }
398
David Benjamin1d77e562015-03-22 17:22:08 -0400399 return true;
David Benjaminbb0a17c2014-09-20 15:35:39 -0400400}
David Benjamin2e521212014-07-16 14:37:51 -0400401
Alessandro Ghedini5fd18072016-09-28 21:04:25 +0100402static bool TestCurveRule(const CurveTest &t) {
403 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
404 if (!ctx) {
405 return false;
406 }
407
408 if (!SSL_CTX_set1_curves_list(ctx.get(), t.rule)) {
409 fprintf(stderr, "Error testing curves list '%s'\n", t.rule);
410 return false;
411 }
412
413 // Compare the two lists.
414 if (ctx->supported_group_list_len != t.expected.size()) {
415 fprintf(stderr, "Error testing curves list '%s': length\n", t.rule);
416 return false;
417 }
418
419 for (size_t i = 0; i < t.expected.size(); i++) {
420 if (t.expected[i] != ctx->supported_group_list[i]) {
421 fprintf(stderr, "Error testing curves list '%s': mismatch\n", t.rule);
422 return false;
423 }
424 }
425
426 return true;
427}
428
429static bool TestCurveRules() {
430 for (const CurveTest &test : kCurveTests) {
431 if (!TestCurveRule(test)) {
432 return false;
433 }
434 }
435
436 for (const char *rule : kBadCurvesLists) {
437 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(SSLv23_server_method()));
438 if (!ctx) {
439 return false;
440 }
441 if (SSL_CTX_set1_curves_list(ctx.get(), rule)) {
442 fprintf(stderr, "Curves list '%s' unexpectedly succeeded\n", rule);
443 return false;
444 }
445 ERR_clear_error();
446 }
447
448 return true;
449}
450
Adam Langley364f7a62016-12-12 10:51:00 -0800451// kOpenSSLSession is a serialized SSL_SESSION.
Adam Langley10f97f32016-07-12 08:09:33 -0700452static const char kOpenSSLSession[] =
Adam Langley364f7a62016-12-12 10:51:00 -0800453 "MIIFqgIBAQICAwMEAsAvBCAG5Q1ndq4Yfmbeo1zwLkNRKmCXGdNgWvGT3cskV0yQ"
Adam Langley10f97f32016-07-12 08:09:33 -0700454 "kAQwJlrlzkAWBOWiLj/jJ76D7l+UXoizP2KI2C7I2FccqMmIfFmmkUy32nIJ0mZH"
455 "IWoJoQYCBFRDO46iBAICASyjggR6MIIEdjCCA16gAwIBAgIIK9dUvsPWSlUwDQYJ"
456 "KoZIhvcNAQEFBQAwSTELMAkGA1UEBhMCVVMxEzARBgNVBAoTCkdvb2dsZSBJbmMx"
457 "JTAjBgNVBAMTHEdvb2dsZSBJbnRlcm5ldCBBdXRob3JpdHkgRzIwHhcNMTQxMDA4"
458 "MTIwNzU3WhcNMTUwMTA2MDAwMDAwWjBoMQswCQYDVQQGEwJVUzETMBEGA1UECAwK"
459 "Q2FsaWZvcm5pYTEWMBQGA1UEBwwNTW91bnRhaW4gVmlldzETMBEGA1UECgwKR29v"
460 "Z2xlIEluYzEXMBUGA1UEAwwOd3d3Lmdvb2dsZS5jb20wggEiMA0GCSqGSIb3DQEB"
461 "AQUAA4IBDwAwggEKAoIBAQCcKeLrplAC+Lofy8t/wDwtB6eu72CVp0cJ4V3lknN6"
462 "huH9ct6FFk70oRIh/VBNBBz900jYy+7111Jm1b8iqOTQ9aT5C7SEhNcQFJvqzH3e"
463 "MPkb6ZSWGm1yGF7MCQTGQXF20Sk/O16FSjAynU/b3oJmOctcycWYkY0ytS/k3LBu"
464 "Id45PJaoMqjB0WypqvNeJHC3q5JjCB4RP7Nfx5jjHSrCMhw8lUMW4EaDxjaR9KDh"
465 "PLgjsk+LDIySRSRDaCQGhEOWLJZVLzLo4N6/UlctCHEllpBUSvEOyFga52qroGjg"
466 "rf3WOQ925MFwzd6AK+Ich0gDRg8sQfdLH5OuP1cfLfU1AgMBAAGjggFBMIIBPTAd"
467 "BgNVHSUEFjAUBggrBgEFBQcDAQYIKwYBBQUHAwIwGQYDVR0RBBIwEIIOd3d3Lmdv"
468 "b2dsZS5jb20waAYIKwYBBQUHAQEEXDBaMCsGCCsGAQUFBzAChh9odHRwOi8vcGtp"
469 "Lmdvb2dsZS5jb20vR0lBRzIuY3J0MCsGCCsGAQUFBzABhh9odHRwOi8vY2xpZW50"
470 "czEuZ29vZ2xlLmNvbS9vY3NwMB0GA1UdDgQWBBQ7a+CcxsZByOpc+xpYFcIbnUMZ"
471 "hTAMBgNVHRMBAf8EAjAAMB8GA1UdIwQYMBaAFErdBhYbvPZotXb1gba7Yhq6WoEv"
472 "MBcGA1UdIAQQMA4wDAYKKwYBBAHWeQIFATAwBgNVHR8EKTAnMCWgI6Ahhh9odHRw"
473 "Oi8vcGtpLmdvb2dsZS5jb20vR0lBRzIuY3JsMA0GCSqGSIb3DQEBBQUAA4IBAQCa"
474 "OXCBdoqUy5bxyq+Wrh1zsyyCFim1PH5VU2+yvDSWrgDY8ibRGJmfff3r4Lud5kal"
475 "dKs9k8YlKD3ITG7P0YT/Rk8hLgfEuLcq5cc0xqmE42xJ+Eo2uzq9rYorc5emMCxf"
476 "5L0TJOXZqHQpOEcuptZQ4OjdYMfSxk5UzueUhA3ogZKRcRkdB3WeWRp+nYRhx4St"
477 "o2rt2A0MKmY9165GHUqMK9YaaXHDXqBu7Sefr1uSoAP9gyIJKeihMivsGqJ1TD6Z"
478 "cc6LMe+dN2P8cZEQHtD1y296ul4Mivqk3jatUVL8/hCwgch9A8O4PGZq9WqBfEWm"
479 "IyHh1dPtbg1lOXdYCWtjpAIEAKUDAgEUqQUCAwGJwKqBpwSBpBwUQvoeOk0Kg36S"
480 "YTcLEkXqKwOBfF9vE4KX0NxeLwjcDTpsuh3qXEaZ992r1N38VDcyS6P7I6HBYN9B"
481 "sNHM362zZnY27GpTw+Kwd751CLoXFPoaMOe57dbBpXoro6Pd3BTbf/Tzr88K06yE"
482 "OTDKPNj3+inbMaVigtK4PLyPq+Topyzvx9USFgRvyuoxn0Hgb+R0A3j6SLRuyOdA"
Adam Langley364f7a62016-12-12 10:51:00 -0800483 "i4gv7Y5oliyntgMBAQA=";
Adam Langley10f97f32016-07-12 08:09:33 -0700484
485// kCustomSession is a custom serialized SSL_SESSION generated by
486// filling in missing fields from |kOpenSSLSession|. This includes
487// providing |peer_sha256|, so |peer| is not serialized.
488static const char kCustomSession[] =
489 "MIIBdgIBAQICAwMEAsAvBCAG5Q1ndq4Yfmbeo1zwLkNRKmCXGdNgWvGT3cskV0yQ"
490 "kAQwJlrlzkAWBOWiLj/jJ76D7l+UXoizP2KI2C7I2FccqMmIfFmmkUy32nIJ0mZH"
491 "IWoJoQYCBFRDO46iBAICASykAwQBAqUDAgEUphAEDnd3dy5nb29nbGUuY29tqAcE"
492 "BXdvcmxkqQUCAwGJwKqBpwSBpBwUQvoeOk0Kg36SYTcLEkXqKwOBfF9vE4KX0Nxe"
493 "LwjcDTpsuh3qXEaZ992r1N38VDcyS6P7I6HBYN9BsNHM362zZnY27GpTw+Kwd751"
494 "CLoXFPoaMOe57dbBpXoro6Pd3BTbf/Tzr88K06yEOTDKPNj3+inbMaVigtK4PLyP"
495 "q+Topyzvx9USFgRvyuoxn0Hgb+R0A3j6SLRuyOdAi4gv7Y5oliynrSIEIAYGBgYG"
496 "BgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGrgMEAQevAwQBBLADBAEF";
497
498// kBoringSSLSession is a serialized SSL_SESSION generated from bssl client.
499static const char kBoringSSLSession[] =
500 "MIIRwQIBAQICAwMEAsAvBCDdoGxGK26mR+8lM0uq6+k9xYuxPnwAjpcF9n0Yli9R"
501 "kQQwbyshfWhdi5XQ1++7n2L1qqrcVlmHBPpr6yknT/u4pUrpQB5FZ7vqvNn8MdHf"
502 "9rWgoQYCBFXgs7uiBAICHCCjggR6MIIEdjCCA16gAwIBAgIIf+yfD7Y6UicwDQYJ"
503 "KoZIhvcNAQELBQAwSTELMAkGA1UEBhMCVVMxEzARBgNVBAoTCkdvb2dsZSBJbmMx"
504 "JTAjBgNVBAMTHEdvb2dsZSBJbnRlcm5ldCBBdXRob3JpdHkgRzIwHhcNMTUwODEy"
505 "MTQ1MzE1WhcNMTUxMTEwMDAwMDAwWjBoMQswCQYDVQQGEwJVUzETMBEGA1UECAwK"
506 "Q2FsaWZvcm5pYTEWMBQGA1UEBwwNTW91bnRhaW4gVmlldzETMBEGA1UECgwKR29v"
507 "Z2xlIEluYzEXMBUGA1UEAwwOd3d3Lmdvb2dsZS5jb20wggEiMA0GCSqGSIb3DQEB"
508 "AQUAA4IBDwAwggEKAoIBAQC0MeG5YGQ0t+IeJeoneP/PrhEaieibeKYkbKVLNZpo"
509 "PLuBinvhkXZo3DC133NpCBpy6ZktBwamqyixAyuk/NU6OjgXqwwxfQ7di1AInLIU"
510 "792c7hFyNXSUCG7At8Ifi3YwBX9Ba6u/1d6rWTGZJrdCq3QU11RkKYyTq2KT5mce"
511 "Tv9iGKqSkSTlp8puy/9SZ/3DbU3U+BuqCFqeSlz7zjwFmk35acdCilpJlVDDN5C/"
512 "RCh8/UKc8PaL+cxlt531qoTENvYrflBno14YEZlCBZsPiFeUSILpKEj3Ccwhy0eL"
513 "EucWQ72YZU8mUzXBoXGn0zA0crFl5ci/2sTBBGZsylNBAgMBAAGjggFBMIIBPTAd"
514 "BgNVHSUEFjAUBggrBgEFBQcDAQYIKwYBBQUHAwIwGQYDVR0RBBIwEIIOd3d3Lmdv"
515 "b2dsZS5jb20waAYIKwYBBQUHAQEEXDBaMCsGCCsGAQUFBzAChh9odHRwOi8vcGtp"
516 "Lmdvb2dsZS5jb20vR0lBRzIuY3J0MCsGCCsGAQUFBzABhh9odHRwOi8vY2xpZW50"
517 "czEuZ29vZ2xlLmNvbS9vY3NwMB0GA1UdDgQWBBS/bzHxcE73Q4j3slC4BLbMtLjG"
518 "GjAMBgNVHRMBAf8EAjAAMB8GA1UdIwQYMBaAFErdBhYbvPZotXb1gba7Yhq6WoEv"
519 "MBcGA1UdIAQQMA4wDAYKKwYBBAHWeQIFATAwBgNVHR8EKTAnMCWgI6Ahhh9odHRw"
520 "Oi8vcGtpLmdvb2dsZS5jb20vR0lBRzIuY3JsMA0GCSqGSIb3DQEBCwUAA4IBAQAb"
521 "qdWPZEHk0X7iKPCTHL6S3w6q1eR67goxZGFSM1lk1hjwyu7XcLJuvALVV9uY3ovE"
522 "kQZSHwT+pyOPWQhsSjO+1GyjvCvK/CAwiUmBX+bQRGaqHsRcio7xSbdVcajQ3bXd"
523 "X+s0WdbOpn6MStKAiBVloPlSxEI8pxY6x/BBCnTIk/+DMB17uZlOjG3vbAnkDkP+"
524 "n0OTucD9sHV7EVj9XUxi51nOfNBCN/s7lpUjDS/NJ4k3iwOtbCPswiot8vLO779a"
525 "f07vR03r349Iz/KTzk95rlFtX0IU+KYNxFNsanIXZ+C9FYGRXkwhHcvFb4qMUB1y"
526 "TTlM80jBMOwyjZXmjRAhpAIEAKUDAgEUqQUCAwGJwKqBpwSBpOgebbmn9NRUtMWH"
527 "+eJpqA5JLMFSMCChOsvKey3toBaCNGU7HfAEiiXNuuAdCBoK262BjQc2YYfqFzqH"
528 "zuppopXCvhohx7j/tnCNZIMgLYt/O9SXK2RYI5z8FhCCHvB4CbD5G0LGl5EFP27s"
529 "Jb6S3aTTYPkQe8yZSlxevg6NDwmTogLO9F7UUkaYmVcMQhzssEE2ZRYNwSOU6KjE"
530 "0Yj+8fAiBtbQriIEIN2L8ZlpaVrdN5KFNdvcmOxJu81P8q53X55xQyGTnGWwsgMC"
531 "ARezggvvMIIEdjCCA16gAwIBAgIIf+yfD7Y6UicwDQYJKoZIhvcNAQELBQAwSTEL"
532 "MAkGA1UEBhMCVVMxEzARBgNVBAoTCkdvb2dsZSBJbmMxJTAjBgNVBAMTHEdvb2ds"
533 "ZSBJbnRlcm5ldCBBdXRob3JpdHkgRzIwHhcNMTUwODEyMTQ1MzE1WhcNMTUxMTEw"
534 "MDAwMDAwWjBoMQswCQYDVQQGEwJVUzETMBEGA1UECAwKQ2FsaWZvcm5pYTEWMBQG"
535 "A1UEBwwNTW91bnRhaW4gVmlldzETMBEGA1UECgwKR29vZ2xlIEluYzEXMBUGA1UE"
536 "AwwOd3d3Lmdvb2dsZS5jb20wggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIB"
537 "AQC0MeG5YGQ0t+IeJeoneP/PrhEaieibeKYkbKVLNZpoPLuBinvhkXZo3DC133Np"
538 "CBpy6ZktBwamqyixAyuk/NU6OjgXqwwxfQ7di1AInLIU792c7hFyNXSUCG7At8If"
539 "i3YwBX9Ba6u/1d6rWTGZJrdCq3QU11RkKYyTq2KT5mceTv9iGKqSkSTlp8puy/9S"
540 "Z/3DbU3U+BuqCFqeSlz7zjwFmk35acdCilpJlVDDN5C/RCh8/UKc8PaL+cxlt531"
541 "qoTENvYrflBno14YEZlCBZsPiFeUSILpKEj3Ccwhy0eLEucWQ72YZU8mUzXBoXGn"
542 "0zA0crFl5ci/2sTBBGZsylNBAgMBAAGjggFBMIIBPTAdBgNVHSUEFjAUBggrBgEF"
543 "BQcDAQYIKwYBBQUHAwIwGQYDVR0RBBIwEIIOd3d3Lmdvb2dsZS5jb20waAYIKwYB"
544 "BQUHAQEEXDBaMCsGCCsGAQUFBzAChh9odHRwOi8vcGtpLmdvb2dsZS5jb20vR0lB"
545 "RzIuY3J0MCsGCCsGAQUFBzABhh9odHRwOi8vY2xpZW50czEuZ29vZ2xlLmNvbS9v"
546 "Y3NwMB0GA1UdDgQWBBS/bzHxcE73Q4j3slC4BLbMtLjGGjAMBgNVHRMBAf8EAjAA"
547 "MB8GA1UdIwQYMBaAFErdBhYbvPZotXb1gba7Yhq6WoEvMBcGA1UdIAQQMA4wDAYK"
548 "KwYBBAHWeQIFATAwBgNVHR8EKTAnMCWgI6Ahhh9odHRwOi8vcGtpLmdvb2dsZS5j"
549 "b20vR0lBRzIuY3JsMA0GCSqGSIb3DQEBCwUAA4IBAQAbqdWPZEHk0X7iKPCTHL6S"
550 "3w6q1eR67goxZGFSM1lk1hjwyu7XcLJuvALVV9uY3ovEkQZSHwT+pyOPWQhsSjO+"
551 "1GyjvCvK/CAwiUmBX+bQRGaqHsRcio7xSbdVcajQ3bXdX+s0WdbOpn6MStKAiBVl"
552 "oPlSxEI8pxY6x/BBCnTIk/+DMB17uZlOjG3vbAnkDkP+n0OTucD9sHV7EVj9XUxi"
553 "51nOfNBCN/s7lpUjDS/NJ4k3iwOtbCPswiot8vLO779af07vR03r349Iz/KTzk95"
554 "rlFtX0IU+KYNxFNsanIXZ+C9FYGRXkwhHcvFb4qMUB1yTTlM80jBMOwyjZXmjRAh"
555 "MIID8DCCAtigAwIBAgIDAjqDMA0GCSqGSIb3DQEBCwUAMEIxCzAJBgNVBAYTAlVT"
556 "MRYwFAYDVQQKEw1HZW9UcnVzdCBJbmMuMRswGQYDVQQDExJHZW9UcnVzdCBHbG9i"
557 "YWwgQ0EwHhcNMTMwNDA1MTUxNTU2WhcNMTYxMjMxMjM1OTU5WjBJMQswCQYDVQQG"
558 "EwJVUzETMBEGA1UEChMKR29vZ2xlIEluYzElMCMGA1UEAxMcR29vZ2xlIEludGVy"
559 "bmV0IEF1dGhvcml0eSBHMjCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEB"
560 "AJwqBHdc2FCROgajguDYUEi8iT/xGXAaiEZ+4I/F8YnOIe5a/mENtzJEiaB0C1NP"
561 "VaTOgmKV7utZX8bhBYASxF6UP7xbSDj0U/ck5vuR6RXEz/RTDfRK/J9U3n2+oGtv"
562 "h8DQUB8oMANA2ghzUWx//zo8pzcGjr1LEQTrfSTe5vn8MXH7lNVg8y5Kr0LSy+rE"
563 "ahqyzFPdFUuLH8gZYR/Nnag+YyuENWllhMgZxUYi+FOVvuOAShDGKuy6lyARxzmZ"
564 "EASg8GF6lSWMTlJ14rbtCMoU/M4iarNOz0YDl5cDfsCx3nuvRTPPuj5xt970JSXC"
565 "DTWJnZ37DhF5iR43xa+OcmkCAwEAAaOB5zCB5DAfBgNVHSMEGDAWgBTAephojYn7"
566 "qwVkDBF9qn1luMrMTjAdBgNVHQ4EFgQUSt0GFhu89mi1dvWBtrtiGrpagS8wDgYD"
567 "VR0PAQH/BAQDAgEGMC4GCCsGAQUFBwEBBCIwIDAeBggrBgEFBQcwAYYSaHR0cDov"
568 "L2cuc3ltY2QuY29tMBIGA1UdEwEB/wQIMAYBAf8CAQAwNQYDVR0fBC4wLDAqoCig"
569 "JoYkaHR0cDovL2cuc3ltY2IuY29tL2NybHMvZ3RnbG9iYWwuY3JsMBcGA1UdIAQQ"
570 "MA4wDAYKKwYBBAHWeQIFATANBgkqhkiG9w0BAQsFAAOCAQEAqvqpIM1qZ4PtXtR+"
571 "3h3Ef+AlBgDFJPupyC1tft6dgmUsgWM0Zj7pUsIItMsv91+ZOmqcUHqFBYx90SpI"
572 "hNMJbHzCzTWf84LuUt5oX+QAihcglvcpjZpNy6jehsgNb1aHA30DP9z6eX0hGfnI"
573 "Oi9RdozHQZJxjyXON/hKTAAj78Q1EK7gI4BzfE00LshukNYQHpmEcxpw8u1VDu4X"
574 "Bupn7jLrLN1nBz/2i8Jw3lsA5rsb0zYaImxssDVCbJAJPZPpZAkiDoUGn8JzIdPm"
575 "X4DkjYUiOnMDsWCOrmji9D6X52ASCWg23jrW4kOVWzeBkoEfu43XrVJkFleW2V40"
576 "fsg12DCCA30wggLmoAMCAQICAxK75jANBgkqhkiG9w0BAQUFADBOMQswCQYDVQQG"
577 "EwJVUzEQMA4GA1UEChMHRXF1aWZheDEtMCsGA1UECxMkRXF1aWZheCBTZWN1cmUg"
578 "Q2VydGlmaWNhdGUgQXV0aG9yaXR5MB4XDTAyMDUyMTA0MDAwMFoXDTE4MDgyMTA0"
579 "MDAwMFowQjELMAkGA1UEBhMCVVMxFjAUBgNVBAoTDUdlb1RydXN0IEluYy4xGzAZ"
580 "BgNVBAMTEkdlb1RydXN0IEdsb2JhbCBDQTCCASIwDQYJKoZIhvcNAQEBBQADggEP"
581 "ADCCAQoCggEBANrMGGMw/fQXIxpWflvfPGw45HG3eJHUvKHYTPioQ7YD6U0hBwiI"
582 "2lgvZjkpvQV4i5046AW3an5xpObEYKaw74DkiSgPniXW7YPzraaRx5jJQhg1FJ2t"
583 "mEaSLk/K8YdDwRaVVy1Q74ktgHpXrfLuX2vSAI25FPgUFTXZwEaje3LIkb/JVSvN"
584 "0Jc+nCZkzN/Ogxlxyk7m1NV7qRnNVd7I7NJeOFPlXE+MLf5QIzb8ZubLjqQ5GQC3"
585 "lQI5kQsO/jgu0R0FmvZNPm8PBx2vLB6PYDni+jZTEznUXiYr2z2oFL0y6xgDKFIE"
586 "ceWrMz3hOLsHNoRinHnqFjD0X8Ar6HFr5PkCAwEAAaOB8DCB7TAfBgNVHSMEGDAW"
587 "gBRI5mj5K9KylddH2CMgEE8zmJCf1DAdBgNVHQ4EFgQUwHqYaI2J+6sFZAwRfap9"
588 "ZbjKzE4wDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMCAQYwOgYDVR0fBDMw"
589 "MTAvoC2gK4YpaHR0cDovL2NybC5nZW90cnVzdC5jb20vY3Jscy9zZWN1cmVjYS5j"
590 "cmwwTgYDVR0gBEcwRTBDBgRVHSAAMDswOQYIKwYBBQUHAgEWLWh0dHBzOi8vd3d3"
591 "Lmdlb3RydXN0LmNvbS9yZXNvdXJjZXMvcmVwb3NpdG9yeTANBgkqhkiG9w0BAQUF"
592 "AAOBgQB24RJuTksWEoYwBrKBCM/wCMfHcX5m7sLt1Dsf//DwyE7WQziwuTB9GNBV"
593 "g6JqyzYRnOhIZqNtf7gT1Ef+i1pcc/yu2RsyGTirlzQUqpbS66McFAhJtrvlke+D"
594 "NusdVm/K2rxzY5Dkf3s+Iss9B+1fOHSc4wNQTqGvmO5h8oQ/Eg==";
595
596// kBadSessionExtraField is a custom serialized SSL_SESSION generated by replacing
597// the final (optional) element of |kCustomSession| with tag number 30.
598static const char kBadSessionExtraField[] =
599 "MIIBdgIBAQICAwMEAsAvBCAG5Q1ndq4Yfmbeo1zwLkNRKmCXGdNgWvGT3cskV0yQ"
600 "kAQwJlrlzkAWBOWiLj/jJ76D7l+UXoizP2KI2C7I2FccqMmIfFmmkUy32nIJ0mZH"
601 "IWoJoQYCBFRDO46iBAICASykAwQBAqUDAgEUphAEDnd3dy5nb29nbGUuY29tqAcE"
602 "BXdvcmxkqQUCAwGJwKqBpwSBpBwUQvoeOk0Kg36SYTcLEkXqKwOBfF9vE4KX0Nxe"
603 "LwjcDTpsuh3qXEaZ992r1N38VDcyS6P7I6HBYN9BsNHM362zZnY27GpTw+Kwd751"
604 "CLoXFPoaMOe57dbBpXoro6Pd3BTbf/Tzr88K06yEOTDKPNj3+inbMaVigtK4PLyP"
605 "q+Topyzvx9USFgRvyuoxn0Hgb+R0A3j6SLRuyOdAi4gv7Y5oliynrSIEIAYGBgYG"
606 "BgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGrgMEAQevAwQBBL4DBAEF";
607
608// kBadSessionVersion is a custom serialized SSL_SESSION generated by replacing
609// the version of |kCustomSession| with 2.
610static const char kBadSessionVersion[] =
611 "MIIBdgIBAgICAwMEAsAvBCAG5Q1ndq4Yfmbeo1zwLkNRKmCXGdNgWvGT3cskV0yQ"
612 "kAQwJlrlzkAWBOWiLj/jJ76D7l+UXoizP2KI2C7I2FccqMmIfFmmkUy32nIJ0mZH"
613 "IWoJoQYCBFRDO46iBAICASykAwQBAqUDAgEUphAEDnd3dy5nb29nbGUuY29tqAcE"
614 "BXdvcmxkqQUCAwGJwKqBpwSBpBwUQvoeOk0Kg36SYTcLEkXqKwOBfF9vE4KX0Nxe"
615 "LwjcDTpsuh3qXEaZ992r1N38VDcyS6P7I6HBYN9BsNHM362zZnY27GpTw+Kwd751"
616 "CLoXFPoaMOe57dbBpXoro6Pd3BTbf/Tzr88K06yEOTDKPNj3+inbMaVigtK4PLyP"
617 "q+Topyzvx9USFgRvyuoxn0Hgb+R0A3j6SLRuyOdAi4gv7Y5oliynrSIEIAYGBgYG"
618 "BgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGrgMEAQevAwQBBLADBAEF";
619
620// kBadSessionTrailingData is a custom serialized SSL_SESSION with trailing data
621// appended.
622static const char kBadSessionTrailingData[] =
623 "MIIBdgIBAQICAwMEAsAvBCAG5Q1ndq4Yfmbeo1zwLkNRKmCXGdNgWvGT3cskV0yQ"
624 "kAQwJlrlzkAWBOWiLj/jJ76D7l+UXoizP2KI2C7I2FccqMmIfFmmkUy32nIJ0mZH"
625 "IWoJoQYCBFRDO46iBAICASykAwQBAqUDAgEUphAEDnd3dy5nb29nbGUuY29tqAcE"
626 "BXdvcmxkqQUCAwGJwKqBpwSBpBwUQvoeOk0Kg36SYTcLEkXqKwOBfF9vE4KX0Nxe"
627 "LwjcDTpsuh3qXEaZ992r1N38VDcyS6P7I6HBYN9BsNHM362zZnY27GpTw+Kwd751"
628 "CLoXFPoaMOe57dbBpXoro6Pd3BTbf/Tzr88K06yEOTDKPNj3+inbMaVigtK4PLyP"
629 "q+Topyzvx9USFgRvyuoxn0Hgb+R0A3j6SLRuyOdAi4gv7Y5oliynrSIEIAYGBgYG"
630 "BgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGrgMEAQevAwQBBLADBAEFAAAA";
631
David Benjamin1d77e562015-03-22 17:22:08 -0400632static bool DecodeBase64(std::vector<uint8_t> *out, const char *in) {
David Benjamin751e8892014-10-19 00:59:36 -0400633 size_t len;
David Benjamin751e8892014-10-19 00:59:36 -0400634 if (!EVP_DecodedLength(&len, strlen(in))) {
635 fprintf(stderr, "EVP_DecodedLength failed\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400636 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400637 }
638
David Benjamin1d77e562015-03-22 17:22:08 -0400639 out->resize(len);
David Benjaminef14b2d2015-11-11 14:01:27 -0800640 if (!EVP_DecodeBase64(out->data(), &len, len, (const uint8_t *)in,
David Benjamin751e8892014-10-19 00:59:36 -0400641 strlen(in))) {
642 fprintf(stderr, "EVP_DecodeBase64 failed\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400643 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400644 }
David Benjamin1d77e562015-03-22 17:22:08 -0400645 out->resize(len);
646 return true;
David Benjamin751e8892014-10-19 00:59:36 -0400647}
648
David Benjamin1d77e562015-03-22 17:22:08 -0400649static bool TestSSL_SESSIONEncoding(const char *input_b64) {
David Benjamin751e8892014-10-19 00:59:36 -0400650 const uint8_t *cptr;
651 uint8_t *ptr;
David Benjamin751e8892014-10-19 00:59:36 -0400652
David Benjamin1d77e562015-03-22 17:22:08 -0400653 // Decode the input.
654 std::vector<uint8_t> input;
655 if (!DecodeBase64(&input, input_b64)) {
656 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400657 }
658
David Benjamin1d77e562015-03-22 17:22:08 -0400659 // Verify the SSL_SESSION decodes.
Adam Langleyc0fc7a12016-12-09 15:05:34 -0800660 bssl::UniquePtr<SSL_SESSION> session(SSL_SESSION_from_bytes(input.data(), input.size()));
David Benjaminfd67aa82015-06-15 19:41:48 -0400661 if (!session) {
662 fprintf(stderr, "SSL_SESSION_from_bytes failed\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400663 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400664 }
665
David Benjamin1d77e562015-03-22 17:22:08 -0400666 // Verify the SSL_SESSION encoding round-trips.
667 size_t encoded_len;
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700668 bssl::UniquePtr<uint8_t> encoded;
David Benjamin1d77e562015-03-22 17:22:08 -0400669 uint8_t *encoded_raw;
670 if (!SSL_SESSION_to_bytes(session.get(), &encoded_raw, &encoded_len)) {
David Benjamin3cac4502014-10-21 01:46:30 -0400671 fprintf(stderr, "SSL_SESSION_to_bytes failed\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400672 return false;
David Benjamin3cac4502014-10-21 01:46:30 -0400673 }
David Benjamin1d77e562015-03-22 17:22:08 -0400674 encoded.reset(encoded_raw);
675 if (encoded_len != input.size() ||
David Benjamin17cf2cb2016-12-13 01:07:13 -0500676 OPENSSL_memcmp(input.data(), encoded.get(), input.size()) != 0) {
David Benjamin3cac4502014-10-21 01:46:30 -0400677 fprintf(stderr, "SSL_SESSION_to_bytes did not round-trip\n");
Sigbjorn Vik2b23d242015-06-29 15:07:26 +0200678 hexdump(stderr, "Before: ", input.data(), input.size());
679 hexdump(stderr, "After: ", encoded_raw, encoded_len);
David Benjamin1d77e562015-03-22 17:22:08 -0400680 return false;
David Benjamin3cac4502014-10-21 01:46:30 -0400681 }
David Benjamin3cac4502014-10-21 01:46:30 -0400682
David Benjaminfd67aa82015-06-15 19:41:48 -0400683 // Verify the SSL_SESSION also decodes with the legacy API.
David Benjaminef14b2d2015-11-11 14:01:27 -0800684 cptr = input.data();
David Benjaminfd67aa82015-06-15 19:41:48 -0400685 session.reset(d2i_SSL_SESSION(NULL, &cptr, input.size()));
David Benjaminef14b2d2015-11-11 14:01:27 -0800686 if (!session || cptr != input.data() + input.size()) {
David Benjaminfd67aa82015-06-15 19:41:48 -0400687 fprintf(stderr, "d2i_SSL_SESSION failed\n");
688 return false;
689 }
690
David Benjamin1d77e562015-03-22 17:22:08 -0400691 // Verify the SSL_SESSION encoding round-trips via the legacy API.
692 int len = i2d_SSL_SESSION(session.get(), NULL);
693 if (len < 0 || (size_t)len != input.size()) {
David Benjamin751e8892014-10-19 00:59:36 -0400694 fprintf(stderr, "i2d_SSL_SESSION(NULL) returned invalid length\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400695 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400696 }
697
David Benjamin1d77e562015-03-22 17:22:08 -0400698 encoded.reset((uint8_t *)OPENSSL_malloc(input.size()));
699 if (!encoded) {
David Benjamin751e8892014-10-19 00:59:36 -0400700 fprintf(stderr, "malloc failed\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400701 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400702 }
David Benjamin1d77e562015-03-22 17:22:08 -0400703
704 ptr = encoded.get();
705 len = i2d_SSL_SESSION(session.get(), &ptr);
706 if (len < 0 || (size_t)len != input.size()) {
David Benjamin751e8892014-10-19 00:59:36 -0400707 fprintf(stderr, "i2d_SSL_SESSION returned invalid length\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400708 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400709 }
David Benjamin1d77e562015-03-22 17:22:08 -0400710 if (ptr != encoded.get() + input.size()) {
David Benjamin751e8892014-10-19 00:59:36 -0400711 fprintf(stderr, "i2d_SSL_SESSION did not advance ptr correctly\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400712 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400713 }
David Benjamin17cf2cb2016-12-13 01:07:13 -0500714 if (OPENSSL_memcmp(input.data(), encoded.get(), input.size()) != 0) {
David Benjamin751e8892014-10-19 00:59:36 -0400715 fprintf(stderr, "i2d_SSL_SESSION did not round-trip\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400716 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400717 }
718
David Benjamin1d77e562015-03-22 17:22:08 -0400719 return true;
David Benjamin751e8892014-10-19 00:59:36 -0400720}
721
David Benjaminf297e022015-05-28 19:55:29 -0400722static bool TestBadSSL_SESSIONEncoding(const char *input_b64) {
723 std::vector<uint8_t> input;
724 if (!DecodeBase64(&input, input_b64)) {
725 return false;
726 }
727
728 // Verify that the SSL_SESSION fails to decode.
Adam Langleyc0fc7a12016-12-09 15:05:34 -0800729 bssl::UniquePtr<SSL_SESSION> session(SSL_SESSION_from_bytes(input.data(), input.size()));
David Benjaminf297e022015-05-28 19:55:29 -0400730 if (session) {
David Benjaminfd67aa82015-06-15 19:41:48 -0400731 fprintf(stderr, "SSL_SESSION_from_bytes unexpectedly succeeded\n");
David Benjaminf297e022015-05-28 19:55:29 -0400732 return false;
733 }
734 ERR_clear_error();
735 return true;
736}
737
David Benjamin10e664b2016-06-20 22:20:47 -0400738static bool TestDefaultVersion(uint16_t min_version, uint16_t max_version,
David Benjamin1d77e562015-03-22 17:22:08 -0400739 const SSL_METHOD *(*method)(void)) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700740 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(method()));
David Benjamin1d77e562015-03-22 17:22:08 -0400741 if (!ctx) {
742 return false;
David Benjamin82c9e902014-12-12 15:55:27 -0500743 }
David Benjaminb6a0a512016-06-21 10:33:21 -0400744 if (ctx->min_version != min_version || ctx->max_version != max_version) {
745 fprintf(stderr, "Got min %04x, max %04x; wanted min %04x, max %04x\n",
746 ctx->min_version, ctx->max_version, min_version, max_version);
747 return false;
748 }
749 return true;
David Benjamin82c9e902014-12-12 15:55:27 -0500750}
751
David Benjamin1d77e562015-03-22 17:22:08 -0400752static bool CipherGetRFCName(std::string *out, uint16_t value) {
David Benjamin2bdb35c2015-02-21 11:03:06 -0500753 const SSL_CIPHER *cipher = SSL_get_cipher_by_value(value);
754 if (cipher == NULL) {
David Benjamin1d77e562015-03-22 17:22:08 -0400755 return false;
David Benjamin65226252015-02-05 16:49:47 -0500756 }
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700757 bssl::UniquePtr<char> rfc_name(SSL_CIPHER_get_rfc_name(cipher));
David Benjamin3fa65f02015-05-15 19:11:57 -0400758 if (!rfc_name) {
759 return false;
760 }
David Benjamin67be0482015-04-20 16:19:00 -0400761 out->assign(rfc_name.get());
David Benjamin1d77e562015-03-22 17:22:08 -0400762 return true;
David Benjamin65226252015-02-05 16:49:47 -0500763}
764
765typedef struct {
David Benjamin2bdb35c2015-02-21 11:03:06 -0500766 int id;
David Benjamin65226252015-02-05 16:49:47 -0500767 const char *rfc_name;
768} CIPHER_RFC_NAME_TEST;
769
770static const CIPHER_RFC_NAME_TEST kCipherRFCNameTests[] = {
Steven Valdez803c77a2016-09-06 14:13:43 -0400771 {SSL3_CK_RSA_DES_192_CBC3_SHA, "TLS_RSA_WITH_3DES_EDE_CBC_SHA"},
772 {TLS1_CK_RSA_WITH_AES_128_SHA, "TLS_RSA_WITH_AES_128_CBC_SHA"},
773 {TLS1_CK_DHE_RSA_WITH_AES_256_SHA, "TLS_DHE_RSA_WITH_AES_256_CBC_SHA"},
774 {TLS1_CK_DHE_RSA_WITH_AES_256_SHA256,
775 "TLS_DHE_RSA_WITH_AES_256_CBC_SHA256"},
776 {TLS1_CK_ECDHE_RSA_WITH_AES_128_SHA256,
777 "TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256"},
778 {TLS1_CK_ECDHE_RSA_WITH_AES_256_SHA384,
779 "TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384"},
780 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256,
781 "TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256"},
782 {TLS1_CK_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256,
783 "TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256"},
784 {TLS1_CK_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384,
785 "TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384"},
786 {TLS1_CK_ECDHE_PSK_WITH_AES_128_CBC_SHA,
787 "TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA"},
788 {TLS1_CK_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256,
789 "TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256"},
790 {TLS1_CK_AES_256_GCM_SHA384, "TLS_AES_256_GCM_SHA384"},
791 {TLS1_CK_AES_128_GCM_SHA256, "TLS_AES_128_GCM_SHA256"},
792 {TLS1_CK_CHACHA20_POLY1305_SHA256, "TLS_CHACHA20_POLY1305_SHA256"},
793
794 // These names are non-standard:
795 {TLS1_CK_ECDHE_RSA_CHACHA20_POLY1305_OLD,
796 "TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256"},
797 {TLS1_CK_ECDHE_ECDSA_CHACHA20_POLY1305_OLD,
798 "TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256"},
David Benjamin65226252015-02-05 16:49:47 -0500799};
800
David Benjamin1d77e562015-03-22 17:22:08 -0400801static bool TestCipherGetRFCName(void) {
802 for (size_t i = 0;
Steven Valdezcb966542016-08-17 16:56:14 -0400803 i < OPENSSL_ARRAY_SIZE(kCipherRFCNameTests); i++) {
David Benjamin65226252015-02-05 16:49:47 -0500804 const CIPHER_RFC_NAME_TEST *test = &kCipherRFCNameTests[i];
David Benjamin1d77e562015-03-22 17:22:08 -0400805 std::string rfc_name;
806 if (!CipherGetRFCName(&rfc_name, test->id & 0xffff)) {
807 fprintf(stderr, "SSL_CIPHER_get_rfc_name failed\n");
808 return false;
David Benjamin65226252015-02-05 16:49:47 -0500809 }
David Benjamin1d77e562015-03-22 17:22:08 -0400810 if (rfc_name != test->rfc_name) {
David Benjamin65226252015-02-05 16:49:47 -0500811 fprintf(stderr, "SSL_CIPHER_get_rfc_name: got '%s', wanted '%s'\n",
David Benjamin1d77e562015-03-22 17:22:08 -0400812 rfc_name.c_str(), test->rfc_name);
813 return false;
David Benjamin65226252015-02-05 16:49:47 -0500814 }
David Benjamin65226252015-02-05 16:49:47 -0500815 }
David Benjamin1d77e562015-03-22 17:22:08 -0400816 return true;
David Benjamin65226252015-02-05 16:49:47 -0500817}
818
Steven Valdeza833c352016-11-01 13:39:36 -0400819// CreateSessionWithTicket returns a sample |SSL_SESSION| with the specified
820// version and ticket length or nullptr on failure.
821static bssl::UniquePtr<SSL_SESSION> CreateSessionWithTicket(uint16_t version,
822 size_t ticket_len) {
David Benjamin422fe082015-07-21 22:03:43 -0400823 std::vector<uint8_t> der;
824 if (!DecodeBase64(&der, kOpenSSLSession)) {
825 return nullptr;
826 }
Steven Valdeza833c352016-11-01 13:39:36 -0400827 bssl::UniquePtr<SSL_SESSION> session(
828 SSL_SESSION_from_bytes(der.data(), der.size()));
David Benjamin422fe082015-07-21 22:03:43 -0400829 if (!session) {
830 return nullptr;
831 }
832
Steven Valdeza833c352016-11-01 13:39:36 -0400833 session->ssl_version = version;
834
David Benjamin422fe082015-07-21 22:03:43 -0400835 // Swap out the ticket for a garbage one.
836 OPENSSL_free(session->tlsext_tick);
837 session->tlsext_tick = reinterpret_cast<uint8_t*>(OPENSSL_malloc(ticket_len));
838 if (session->tlsext_tick == nullptr) {
839 return nullptr;
840 }
David Benjamin17cf2cb2016-12-13 01:07:13 -0500841 OPENSSL_memset(session->tlsext_tick, 'a', ticket_len);
David Benjamin422fe082015-07-21 22:03:43 -0400842 session->tlsext_ticklen = ticket_len;
David Benjamin1269ddd2015-10-18 15:18:55 -0400843
844 // Fix up the timeout.
David Benjamin9b63f292016-11-15 00:44:05 -0500845#if defined(BORINGSSL_UNSAFE_DETERMINISTIC_MODE)
846 session->time = 1234;
847#else
David Benjamin1269ddd2015-10-18 15:18:55 -0400848 session->time = time(NULL);
David Benjamin9b63f292016-11-15 00:44:05 -0500849#endif
David Benjamin422fe082015-07-21 22:03:43 -0400850 return session;
851}
852
David Benjaminafc64de2016-07-19 17:12:41 +0200853static bool GetClientHello(SSL *ssl, std::vector<uint8_t> *out) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700854 bssl::UniquePtr<BIO> bio(BIO_new(BIO_s_mem()));
David Benjaminafc64de2016-07-19 17:12:41 +0200855 if (!bio) {
856 return false;
857 }
858 // Do not configure a reading BIO, but record what's written to a memory BIO.
David Benjamin96a16cd2016-08-11 12:14:47 -0400859 BIO_up_ref(bio.get());
860 SSL_set_bio(ssl, nullptr /* rbio */, bio.get());
David Benjaminafc64de2016-07-19 17:12:41 +0200861 int ret = SSL_connect(ssl);
862 if (ret > 0) {
863 // SSL_connect should fail without a BIO to write to.
864 return false;
865 }
866 ERR_clear_error();
867
868 const uint8_t *client_hello;
869 size_t client_hello_len;
870 if (!BIO_mem_contents(bio.get(), &client_hello, &client_hello_len)) {
871 return false;
872 }
873 *out = std::vector<uint8_t>(client_hello, client_hello + client_hello_len);
874 return true;
875}
876
Steven Valdeza833c352016-11-01 13:39:36 -0400877// GetClientHelloLen creates a client SSL connection with the specified version
878// and ticket length. It returns the length of the ClientHello, not including
879// the record header, on success and zero on error.
880static size_t GetClientHelloLen(uint16_t max_version, uint16_t session_version,
881 size_t ticket_len) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700882 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
Steven Valdeza833c352016-11-01 13:39:36 -0400883 bssl::UniquePtr<SSL_SESSION> session =
884 CreateSessionWithTicket(session_version, ticket_len);
David Benjamin422fe082015-07-21 22:03:43 -0400885 if (!ctx || !session) {
886 return 0;
887 }
Steven Valdeza833c352016-11-01 13:39:36 -0400888
889 // Set a one-element cipher list so the baseline ClientHello is unpadded.
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700890 bssl::UniquePtr<SSL> ssl(SSL_new(ctx.get()));
Steven Valdez2c62fe92016-10-14 12:08:12 -0400891 if (!ssl || !SSL_set_session(ssl.get(), session.get()) ||
Steven Valdeza833c352016-11-01 13:39:36 -0400892 !SSL_set_cipher_list(ssl.get(), "ECDHE-RSA-AES128-GCM-SHA256") ||
893 !SSL_set_max_proto_version(ssl.get(), max_version)) {
David Benjamin422fe082015-07-21 22:03:43 -0400894 return 0;
895 }
Steven Valdeza833c352016-11-01 13:39:36 -0400896
David Benjaminafc64de2016-07-19 17:12:41 +0200897 std::vector<uint8_t> client_hello;
898 if (!GetClientHello(ssl.get(), &client_hello) ||
899 client_hello.size() <= SSL3_RT_HEADER_LENGTH) {
David Benjamin422fe082015-07-21 22:03:43 -0400900 return 0;
901 }
Steven Valdeza833c352016-11-01 13:39:36 -0400902
David Benjaminafc64de2016-07-19 17:12:41 +0200903 return client_hello.size() - SSL3_RT_HEADER_LENGTH;
David Benjamin422fe082015-07-21 22:03:43 -0400904}
905
906struct PaddingTest {
907 size_t input_len, padded_len;
908};
909
910static const PaddingTest kPaddingTests[] = {
911 // ClientHellos of length below 0x100 do not require padding.
912 {0xfe, 0xfe},
913 {0xff, 0xff},
914 // ClientHellos of length 0x100 through 0x1fb are padded up to 0x200.
915 {0x100, 0x200},
916 {0x123, 0x200},
917 {0x1fb, 0x200},
918 // ClientHellos of length 0x1fc through 0x1ff get padded beyond 0x200. The
919 // padding extension takes a minimum of four bytes plus one required content
920 // byte. (To work around yet more server bugs, we avoid empty final
921 // extensions.)
922 {0x1fc, 0x201},
923 {0x1fd, 0x202},
924 {0x1fe, 0x203},
925 {0x1ff, 0x204},
926 // Finally, larger ClientHellos need no padding.
927 {0x200, 0x200},
928 {0x201, 0x201},
929};
930
Steven Valdeza833c352016-11-01 13:39:36 -0400931static bool TestPaddingExtension(uint16_t max_version,
932 uint16_t session_version) {
David Benjamin422fe082015-07-21 22:03:43 -0400933 // Sample a baseline length.
Steven Valdeza833c352016-11-01 13:39:36 -0400934 size_t base_len = GetClientHelloLen(max_version, session_version, 1);
David Benjamin422fe082015-07-21 22:03:43 -0400935 if (base_len == 0) {
936 return false;
937 }
938
939 for (const PaddingTest &test : kPaddingTests) {
940 if (base_len > test.input_len) {
Steven Valdeza833c352016-11-01 13:39:36 -0400941 fprintf(stderr,
942 "Baseline ClientHello too long (max_version = %04x, "
943 "session_version = %04x).\n",
944 max_version, session_version);
David Benjamin422fe082015-07-21 22:03:43 -0400945 return false;
946 }
947
Steven Valdeza833c352016-11-01 13:39:36 -0400948 size_t padded_len = GetClientHelloLen(max_version, session_version,
949 1 + test.input_len - base_len);
David Benjamin422fe082015-07-21 22:03:43 -0400950 if (padded_len != test.padded_len) {
Steven Valdeza833c352016-11-01 13:39:36 -0400951 fprintf(stderr,
952 "%u-byte ClientHello padded to %u bytes, not %u (max_version = "
953 "%04x, session_version = %04x).\n",
David Benjamin422fe082015-07-21 22:03:43 -0400954 static_cast<unsigned>(test.input_len),
955 static_cast<unsigned>(padded_len),
Steven Valdeza833c352016-11-01 13:39:36 -0400956 static_cast<unsigned>(test.padded_len), max_version,
957 session_version);
David Benjamin422fe082015-07-21 22:03:43 -0400958 return false;
959 }
960 }
Steven Valdeza833c352016-11-01 13:39:36 -0400961
David Benjamin422fe082015-07-21 22:03:43 -0400962 return true;
963}
964
David Benjamin1d128f32015-09-08 17:41:40 -0400965// Test that |SSL_get_client_CA_list| echoes back the configured parameter even
966// before configuring as a server.
967static bool TestClientCAList() {
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700968 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
David Benjamin1d128f32015-09-08 17:41:40 -0400969 if (!ctx) {
970 return false;
971 }
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700972 bssl::UniquePtr<SSL> ssl(SSL_new(ctx.get()));
David Benjamin1d128f32015-09-08 17:41:40 -0400973 if (!ssl) {
974 return false;
975 }
976
977 STACK_OF(X509_NAME) *stack = sk_X509_NAME_new_null();
978 if (stack == nullptr) {
979 return false;
980 }
981 // |SSL_set_client_CA_list| takes ownership.
982 SSL_set_client_CA_list(ssl.get(), stack);
983
984 return SSL_get_client_CA_list(ssl.get()) == stack;
985}
986
David Benjamin0f653952015-10-18 14:28:01 -0400987static void AppendSession(SSL_SESSION *session, void *arg) {
988 std::vector<SSL_SESSION*> *out =
989 reinterpret_cast<std::vector<SSL_SESSION*>*>(arg);
990 out->push_back(session);
991}
992
993// ExpectCache returns true if |ctx|'s session cache consists of |expected|, in
994// order.
995static bool ExpectCache(SSL_CTX *ctx,
996 const std::vector<SSL_SESSION*> &expected) {
997 // Check the linked list.
998 SSL_SESSION *ptr = ctx->session_cache_head;
999 for (SSL_SESSION *session : expected) {
1000 if (ptr != session) {
1001 return false;
1002 }
1003 // TODO(davidben): This is an absurd way to denote the end of the list.
1004 if (ptr->next ==
1005 reinterpret_cast<SSL_SESSION *>(&ctx->session_cache_tail)) {
1006 ptr = nullptr;
1007 } else {
1008 ptr = ptr->next;
1009 }
1010 }
1011 if (ptr != nullptr) {
1012 return false;
1013 }
1014
1015 // Check the hash table.
1016 std::vector<SSL_SESSION*> actual, expected_copy;
1017 lh_SSL_SESSION_doall_arg(SSL_CTX_sessions(ctx), AppendSession, &actual);
1018 expected_copy = expected;
1019
1020 std::sort(actual.begin(), actual.end());
1021 std::sort(expected_copy.begin(), expected_copy.end());
1022
1023 return actual == expected_copy;
1024}
1025
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001026static bssl::UniquePtr<SSL_SESSION> CreateTestSession(uint32_t number) {
1027 bssl::UniquePtr<SSL_SESSION> ret(SSL_SESSION_new());
David Benjamin0f653952015-10-18 14:28:01 -04001028 if (!ret) {
1029 return nullptr;
1030 }
1031
1032 ret->session_id_length = SSL3_SSL_SESSION_ID_LENGTH;
David Benjamin17cf2cb2016-12-13 01:07:13 -05001033 OPENSSL_memset(ret->session_id, 0, ret->session_id_length);
1034 OPENSSL_memcpy(ret->session_id, &number, sizeof(number));
David Benjamin0f653952015-10-18 14:28:01 -04001035 return ret;
1036}
1037
David Benjamin0f653952015-10-18 14:28:01 -04001038// Test that the internal session cache behaves as expected.
1039static bool TestInternalSessionCache() {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001040 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
David Benjamin0f653952015-10-18 14:28:01 -04001041 if (!ctx) {
1042 return false;
1043 }
1044
1045 // Prepare 10 test sessions.
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001046 std::vector<bssl::UniquePtr<SSL_SESSION>> sessions;
David Benjamin0f653952015-10-18 14:28:01 -04001047 for (int i = 0; i < 10; i++) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001048 bssl::UniquePtr<SSL_SESSION> session = CreateTestSession(i);
David Benjamin0f653952015-10-18 14:28:01 -04001049 if (!session) {
1050 return false;
1051 }
David Benjamin4f6acaf2015-11-21 03:00:50 -05001052 sessions.push_back(std::move(session));
David Benjamin0f653952015-10-18 14:28:01 -04001053 }
1054
1055 SSL_CTX_sess_set_cache_size(ctx.get(), 5);
1056
1057 // Insert all the test sessions.
David Benjamin4f6acaf2015-11-21 03:00:50 -05001058 for (const auto &session : sessions) {
1059 if (!SSL_CTX_add_session(ctx.get(), session.get())) {
David Benjamin0f653952015-10-18 14:28:01 -04001060 return false;
1061 }
1062 }
1063
1064 // Only the last five should be in the list.
David Benjamin4f6acaf2015-11-21 03:00:50 -05001065 std::vector<SSL_SESSION*> expected = {
1066 sessions[9].get(),
1067 sessions[8].get(),
1068 sessions[7].get(),
1069 sessions[6].get(),
1070 sessions[5].get(),
1071 };
David Benjamin0f653952015-10-18 14:28:01 -04001072 if (!ExpectCache(ctx.get(), expected)) {
1073 return false;
1074 }
1075
1076 // Inserting an element already in the cache should fail.
David Benjamin4f6acaf2015-11-21 03:00:50 -05001077 if (SSL_CTX_add_session(ctx.get(), sessions[7].get()) ||
David Benjamin0f653952015-10-18 14:28:01 -04001078 !ExpectCache(ctx.get(), expected)) {
1079 return false;
1080 }
1081
1082 // Although collisions should be impossible (256-bit session IDs), the cache
1083 // must handle them gracefully.
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001084 bssl::UniquePtr<SSL_SESSION> collision(CreateTestSession(7));
David Benjamin0f653952015-10-18 14:28:01 -04001085 if (!collision || !SSL_CTX_add_session(ctx.get(), collision.get())) {
1086 return false;
1087 }
David Benjamin4f6acaf2015-11-21 03:00:50 -05001088 expected = {
1089 collision.get(),
1090 sessions[9].get(),
1091 sessions[8].get(),
1092 sessions[6].get(),
1093 sessions[5].get(),
1094 };
David Benjamin0f653952015-10-18 14:28:01 -04001095 if (!ExpectCache(ctx.get(), expected)) {
1096 return false;
1097 }
1098
1099 // Removing sessions behaves correctly.
David Benjamin4f6acaf2015-11-21 03:00:50 -05001100 if (!SSL_CTX_remove_session(ctx.get(), sessions[6].get())) {
David Benjamin0f653952015-10-18 14:28:01 -04001101 return false;
1102 }
David Benjamin4f6acaf2015-11-21 03:00:50 -05001103 expected = {
1104 collision.get(),
1105 sessions[9].get(),
1106 sessions[8].get(),
1107 sessions[5].get(),
1108 };
David Benjamin0f653952015-10-18 14:28:01 -04001109 if (!ExpectCache(ctx.get(), expected)) {
1110 return false;
1111 }
1112
1113 // Removing sessions requires an exact match.
David Benjamin4f6acaf2015-11-21 03:00:50 -05001114 if (SSL_CTX_remove_session(ctx.get(), sessions[0].get()) ||
1115 SSL_CTX_remove_session(ctx.get(), sessions[7].get()) ||
David Benjamin0f653952015-10-18 14:28:01 -04001116 !ExpectCache(ctx.get(), expected)) {
1117 return false;
1118 }
1119
1120 return true;
1121}
1122
David Benjaminde942382016-02-11 12:02:01 -05001123static uint16_t EpochFromSequence(uint64_t seq) {
1124 return static_cast<uint16_t>(seq >> 48);
1125}
1126
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001127static bssl::UniquePtr<X509> GetTestCertificate() {
David Benjaminde942382016-02-11 12:02:01 -05001128 static const char kCertPEM[] =
1129 "-----BEGIN CERTIFICATE-----\n"
1130 "MIICWDCCAcGgAwIBAgIJAPuwTC6rEJsMMA0GCSqGSIb3DQEBBQUAMEUxCzAJBgNV\n"
1131 "BAYTAkFVMRMwEQYDVQQIDApTb21lLVN0YXRlMSEwHwYDVQQKDBhJbnRlcm5ldCBX\n"
1132 "aWRnaXRzIFB0eSBMdGQwHhcNMTQwNDIzMjA1MDQwWhcNMTcwNDIyMjA1MDQwWjBF\n"
1133 "MQswCQYDVQQGEwJBVTETMBEGA1UECAwKU29tZS1TdGF0ZTEhMB8GA1UECgwYSW50\n"
1134 "ZXJuZXQgV2lkZ2l0cyBQdHkgTHRkMIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKB\n"
1135 "gQDYK8imMuRi/03z0K1Zi0WnvfFHvwlYeyK9Na6XJYaUoIDAtB92kWdGMdAQhLci\n"
1136 "HnAjkXLI6W15OoV3gA/ElRZ1xUpxTMhjP6PyY5wqT5r6y8FxbiiFKKAnHmUcrgfV\n"
1137 "W28tQ+0rkLGMryRtrukXOgXBv7gcrmU7G1jC2a7WqmeI8QIDAQABo1AwTjAdBgNV\n"
1138 "HQ4EFgQUi3XVrMsIvg4fZbf6Vr5sp3Xaha8wHwYDVR0jBBgwFoAUi3XVrMsIvg4f\n"
1139 "Zbf6Vr5sp3Xaha8wDAYDVR0TBAUwAwEB/zANBgkqhkiG9w0BAQUFAAOBgQA76Hht\n"
1140 "ldY9avcTGSwbwoiuIqv0jTL1fHFnzy3RHMLDh+Lpvolc5DSrSJHCP5WuK0eeJXhr\n"
1141 "T5oQpHL9z/cCDLAKCKRa4uV0fhEdOWBqyR9p8y5jJtye72t6CuFUV5iqcpF4BH4f\n"
1142 "j2VNHwsSrJwkD4QUGlUtH7vwnQmyCFxZMmWAJg==\n"
1143 "-----END CERTIFICATE-----\n";
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001144 bssl::UniquePtr<BIO> bio(BIO_new_mem_buf(kCertPEM, strlen(kCertPEM)));
David Benjamin1444c3a2016-12-20 17:23:11 -05001145 return bssl::UniquePtr<X509>(
1146 PEM_read_bio_X509(bio.get(), nullptr, nullptr, nullptr));
David Benjaminde942382016-02-11 12:02:01 -05001147}
1148
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001149static bssl::UniquePtr<EVP_PKEY> GetTestKey() {
David Benjaminde942382016-02-11 12:02:01 -05001150 static const char kKeyPEM[] =
1151 "-----BEGIN RSA PRIVATE KEY-----\n"
1152 "MIICXgIBAAKBgQDYK8imMuRi/03z0K1Zi0WnvfFHvwlYeyK9Na6XJYaUoIDAtB92\n"
1153 "kWdGMdAQhLciHnAjkXLI6W15OoV3gA/ElRZ1xUpxTMhjP6PyY5wqT5r6y8FxbiiF\n"
1154 "KKAnHmUcrgfVW28tQ+0rkLGMryRtrukXOgXBv7gcrmU7G1jC2a7WqmeI8QIDAQAB\n"
1155 "AoGBAIBy09Fd4DOq/Ijp8HeKuCMKTHqTW1xGHshLQ6jwVV2vWZIn9aIgmDsvkjCe\n"
1156 "i6ssZvnbjVcwzSoByhjN8ZCf/i15HECWDFFh6gt0P5z0MnChwzZmvatV/FXCT0j+\n"
1157 "WmGNB/gkehKjGXLLcjTb6dRYVJSCZhVuOLLcbWIV10gggJQBAkEA8S8sGe4ezyyZ\n"
1158 "m4e9r95g6s43kPqtj5rewTsUxt+2n4eVodD+ZUlCULWVNAFLkYRTBCASlSrm9Xhj\n"
1159 "QpmWAHJUkQJBAOVzQdFUaewLtdOJoPCtpYoY1zd22eae8TQEmpGOR11L6kbxLQsk\n"
1160 "aMly/DOnOaa82tqAGTdqDEZgSNmCeKKknmECQAvpnY8GUOVAubGR6c+W90iBuQLj\n"
1161 "LtFp/9ihd2w/PoDwrHZaoUYVcT4VSfJQog/k7kjE4MYXYWL8eEKg3WTWQNECQQDk\n"
1162 "104Wi91Umd1PzF0ijd2jXOERJU1wEKe6XLkYYNHWQAe5l4J4MWj9OdxFXAxIuuR/\n"
1163 "tfDwbqkta4xcux67//khAkEAvvRXLHTaa6VFzTaiiO8SaFsHV3lQyXOtMrBpB5jd\n"
1164 "moZWgjHvB2W9Ckn7sDqsPB+U2tyX0joDdQEyuiMECDY8oQ==\n"
1165 "-----END RSA PRIVATE KEY-----\n";
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001166 bssl::UniquePtr<BIO> bio(BIO_new_mem_buf(kKeyPEM, strlen(kKeyPEM)));
1167 return bssl::UniquePtr<EVP_PKEY>(
David Benjaminde942382016-02-11 12:02:01 -05001168 PEM_read_bio_PrivateKey(bio.get(), nullptr, nullptr, nullptr));
1169}
1170
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001171static bssl::UniquePtr<X509> GetECDSATestCertificate() {
David Benjamin0fc37ef2016-08-17 15:29:46 -04001172 static const char kCertPEM[] =
1173 "-----BEGIN CERTIFICATE-----\n"
1174 "MIIBzzCCAXagAwIBAgIJANlMBNpJfb/rMAkGByqGSM49BAEwRTELMAkGA1UEBhMC\n"
1175 "QVUxEzARBgNVBAgMClNvbWUtU3RhdGUxITAfBgNVBAoMGEludGVybmV0IFdpZGdp\n"
1176 "dHMgUHR5IEx0ZDAeFw0xNDA0MjMyMzIxNTdaFw0xNDA1MjMyMzIxNTdaMEUxCzAJ\n"
1177 "BgNVBAYTAkFVMRMwEQYDVQQIDApTb21lLVN0YXRlMSEwHwYDVQQKDBhJbnRlcm5l\n"
1178 "dCBXaWRnaXRzIFB0eSBMdGQwWTATBgcqhkjOPQIBBggqhkjOPQMBBwNCAATmK2ni\n"
1179 "v2Wfl74vHg2UikzVl2u3qR4NRvvdqakendy6WgHn1peoChj5w8SjHlbifINI2xYa\n"
1180 "HPUdfvGULUvPciLBo1AwTjAdBgNVHQ4EFgQUq4TSrKuV8IJOFngHVVdf5CaNgtEw\n"
1181 "HwYDVR0jBBgwFoAUq4TSrKuV8IJOFngHVVdf5CaNgtEwDAYDVR0TBAUwAwEB/zAJ\n"
1182 "BgcqhkjOPQQBA0gAMEUCIQDyoDVeUTo2w4J5m+4nUIWOcAZ0lVfSKXQA9L4Vh13E\n"
1183 "BwIgfB55FGohg/B6dGh5XxSZmmi08cueFV7mHzJSYV51yRQ=\n"
1184 "-----END CERTIFICATE-----\n";
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001185 bssl::UniquePtr<BIO> bio(BIO_new_mem_buf(kCertPEM, strlen(kCertPEM)));
1186 return bssl::UniquePtr<X509>(PEM_read_bio_X509(bio.get(), nullptr, nullptr, nullptr));
David Benjamin0fc37ef2016-08-17 15:29:46 -04001187}
1188
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001189static bssl::UniquePtr<EVP_PKEY> GetECDSATestKey() {
David Benjamin0fc37ef2016-08-17 15:29:46 -04001190 static const char kKeyPEM[] =
1191 "-----BEGIN PRIVATE KEY-----\n"
1192 "MIGHAgEAMBMGByqGSM49AgEGCCqGSM49AwEHBG0wawIBAQQgBw8IcnrUoEqc3VnJ\n"
1193 "TYlodwi1b8ldMHcO6NHJzgqLtGqhRANCAATmK2niv2Wfl74vHg2UikzVl2u3qR4N\n"
1194 "Rvvdqakendy6WgHn1peoChj5w8SjHlbifINI2xYaHPUdfvGULUvPciLB\n"
1195 "-----END PRIVATE KEY-----\n";
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001196 bssl::UniquePtr<BIO> bio(BIO_new_mem_buf(kKeyPEM, strlen(kKeyPEM)));
1197 return bssl::UniquePtr<EVP_PKEY>(
David Benjamin0fc37ef2016-08-17 15:29:46 -04001198 PEM_read_bio_PrivateKey(bio.get(), nullptr, nullptr, nullptr));
1199}
1200
David Benjamin1444c3a2016-12-20 17:23:11 -05001201static bssl::UniquePtr<X509> GetChainTestCertificate() {
1202 static const char kCertPEM[] =
1203 "-----BEGIN CERTIFICATE-----\n"
1204 "MIIC0jCCAbqgAwIBAgICEAAwDQYJKoZIhvcNAQELBQAwDzENMAsGA1UEAwwEQiBD\n"
1205 "QTAeFw0xNjAyMjgyMDI3MDNaFw0yNjAyMjUyMDI3MDNaMBgxFjAUBgNVBAMMDUNs\n"
1206 "aWVudCBDZXJ0IEEwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDRvaz8\n"
1207 "CC/cshpCafJo4jLkHEoBqDLhdgFelJoAiQUyIqyWl2O7YHPnpJH+TgR7oelzNzt/\n"
1208 "kLRcH89M/TszB6zqyLTC4aqmvzKL0peD/jL2LWBucR0WXIvjA3zoRuF/x86+rYH3\n"
1209 "tHb+xs2PSs8EGL/Ev+ss+qTzTGEn26fuGNHkNw6tOwPpc+o8+wUtzf/kAthamo+c\n"
1210 "IDs2rQ+lP7+aLZTLeU/q4gcLutlzcK5imex5xy2jPkweq48kijK0kIzl1cPlA5d1\n"
1211 "z7C8jU50Pj9X9sQDJTN32j7UYRisJeeYQF8GaaN8SbrDI6zHgKzrRLyxDt/KQa9V\n"
1212 "iLeXANgZi+Xx9KgfAgMBAAGjLzAtMAwGA1UdEwEB/wQCMAAwHQYDVR0lBBYwFAYI\n"
1213 "KwYBBQUHAwEGCCsGAQUFBwMCMA0GCSqGSIb3DQEBCwUAA4IBAQBFEVbmYl+2RtNw\n"
1214 "rDftRDF1v2QUbcN2ouSnQDHxeDQdSgasLzT3ui8iYu0Rw2WWcZ0DV5e0ztGPhWq7\n"
1215 "AO0B120aFRMOY+4+bzu9Q2FFkQqc7/fKTvTDzIJI5wrMnFvUfzzvxh3OHWMYSs/w\n"
1216 "giq33hTKeHEq6Jyk3btCny0Ycecyc3yGXH10sizUfiHlhviCkDuESk8mFDwDDzqW\n"
1217 "ZF0IipzFbEDHoIxLlm3GQxpiLoEV4k8KYJp3R5KBLFyxM6UGPz8h72mIPCJp2RuK\n"
1218 "MYgF91UDvVzvnYm6TfseM2+ewKirC00GOrZ7rEcFvtxnKSqYf4ckqfNdSU1Y+RRC\n"
1219 "1ngWZ7Ih\n"
1220 "-----END CERTIFICATE-----\n";
1221 bssl::UniquePtr<BIO> bio(BIO_new_mem_buf(kCertPEM, strlen(kCertPEM)));
1222 return bssl::UniquePtr<X509>(
1223 PEM_read_bio_X509(bio.get(), nullptr, nullptr, nullptr));
1224}
1225
1226static bssl::UniquePtr<X509> GetChainTestIntermediate() {
1227 static const char kCertPEM[] =
1228 "-----BEGIN CERTIFICATE-----\n"
1229 "MIICwjCCAaqgAwIBAgICEAEwDQYJKoZIhvcNAQELBQAwFDESMBAGA1UEAwwJQyBS\n"
1230 "b290IENBMB4XDTE2MDIyODIwMjcwM1oXDTI2MDIyNTIwMjcwM1owDzENMAsGA1UE\n"
1231 "AwwEQiBDQTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBALsSCYmDip2D\n"
1232 "GkjFxw7ykz26JSjELkl6ArlYjFJ3aT/SCh8qbS4gln7RH8CPBd78oFdfhIKQrwtZ\n"
1233 "3/q21ykD9BAS3qHe2YdcJfm8/kWAy5DvXk6NXU4qX334KofBAEpgdA/igEFq1P1l\n"
1234 "HAuIfZCpMRfT+i5WohVsGi8f/NgpRvVaMONLNfgw57mz1lbtFeBEISmX0kbsuJxF\n"
1235 "Qj/Bwhi5/0HAEXG8e7zN4cEx0yPRvmOATRdVb/8dW2pwOHRJq9R5M0NUkIsTSnL7\n"
1236 "6N/z8hRAHMsV3IudC5Yd7GXW1AGu9a+iKU+Q4xcZCoj0DC99tL4VKujrV1kAeqsM\n"
1237 "cz5/dKzi6+cCAwEAAaMjMCEwDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMC\n"
1238 "AQYwDQYJKoZIhvcNAQELBQADggEBAIIeZiEeNhWWQ8Y4D+AGDwqUUeG8NjCbKrXQ\n"
1239 "BlHg5wZ8xftFaiP1Dp/UAezmx2LNazdmuwrYB8lm3FVTyaPDTKEGIPS4wJKHgqH1\n"
1240 "QPDhqNm85ey7TEtI9oYjsNim/Rb+iGkIAMXaxt58SzxbjvP0kMr1JfJIZbic9vye\n"
1241 "NwIspMFIpP3FB8ywyu0T0hWtCQgL4J47nigCHpOu58deP88fS/Nyz/fyGVWOZ76b\n"
1242 "WhWwgM3P3X95fQ3d7oFPR/bVh0YV+Cf861INwplokXgXQ3/TCQ+HNXeAMWn3JLWv\n"
1243 "XFwk8owk9dq/kQGdndGgy3KTEW4ctPX5GNhf3LJ9Q7dLji4ReQ4=\n"
1244 "-----END CERTIFICATE-----\n";
1245 bssl::UniquePtr<BIO> bio(BIO_new_mem_buf(kCertPEM, strlen(kCertPEM)));
1246 return bssl::UniquePtr<X509>(
1247 PEM_read_bio_X509(bio.get(), nullptr, nullptr, nullptr));
1248}
1249
1250static bssl::UniquePtr<EVP_PKEY> GetChainTestKey() {
1251 static const char kKeyPEM[] =
1252 "-----BEGIN PRIVATE KEY-----\n"
1253 "MIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQDRvaz8CC/cshpC\n"
1254 "afJo4jLkHEoBqDLhdgFelJoAiQUyIqyWl2O7YHPnpJH+TgR7oelzNzt/kLRcH89M\n"
1255 "/TszB6zqyLTC4aqmvzKL0peD/jL2LWBucR0WXIvjA3zoRuF/x86+rYH3tHb+xs2P\n"
1256 "Ss8EGL/Ev+ss+qTzTGEn26fuGNHkNw6tOwPpc+o8+wUtzf/kAthamo+cIDs2rQ+l\n"
1257 "P7+aLZTLeU/q4gcLutlzcK5imex5xy2jPkweq48kijK0kIzl1cPlA5d1z7C8jU50\n"
1258 "Pj9X9sQDJTN32j7UYRisJeeYQF8GaaN8SbrDI6zHgKzrRLyxDt/KQa9ViLeXANgZ\n"
1259 "i+Xx9KgfAgMBAAECggEBAK0VjSJzkyPaamcyTVSWjo7GdaBGcK60lk657RjR+lK0\n"
1260 "YJ7pkej4oM2hdsVZFsP8Cs4E33nXLa/0pDsRov/qrp0WQm2skwqGMC1I/bZ0WRPk\n"
1261 "wHaDrBBfESWnJDX/AGpVtlyOjPmgmK6J2usMPihQUDkKdAYrVWJePrMIxt1q6BMe\n"
1262 "iczs3qriMmtY3bUc4UyUwJ5fhDLjshHvfuIpYQyI6EXZM6dZksn9LylXJnigY6QJ\n"
1263 "HxOYO0BDwOsZ8yQ8J8afLk88i0GizEkgE1z3REtQUwgWfxr1WV/ud+T6/ZhSAgH9\n"
1264 "042mQvSFZnIUSEsmCvjhWuAunfxHKCTcAoYISWfzWpkCgYEA7gpf3HHU5Tn+CgUn\n"
1265 "1X5uGpG3DmcMgfeGgs2r2f/IIg/5Ac1dfYILiybL1tN9zbyLCJfcbFpWBc9hJL6f\n"
1266 "CPc5hUiwWFJqBJewxQkC1Ae/HakHbip+IZ+Jr0842O4BAArvixk4Lb7/N2Ct9sTE\n"
1267 "NJO6RtK9lbEZ5uK61DglHy8CS2UCgYEA4ZC1o36kPAMQBggajgnucb2yuUEelk0f\n"
1268 "AEr+GI32MGE+93xMr7rAhBoqLg4AITyIfEnOSQ5HwagnIHonBbv1LV/Gf9ursx8Z\n"
1269 "YOGbvT8zzzC+SU1bkDzdjAYnFQVGIjMtKOBJ3K07++ypwX1fr4QsQ8uKL8WSOWwt\n"
1270 "Z3Bym6XiZzMCgYADnhy+2OwHX85AkLt+PyGlPbmuelpyTzS4IDAQbBa6jcuW/2wA\n"
1271 "UE2km75VUXmD+u2R/9zVuLm99NzhFhSMqlUxdV1YukfqMfP5yp1EY6m/5aW7QuIP\n"
1272 "2MDa7TVL9rIFMiVZ09RKvbBbQxjhuzPQKL6X/PPspnhiTefQ+dl2k9xREQKBgHDS\n"
1273 "fMfGNEeAEKezrfSVqxphE9/tXms3L+ZpnCaT+yu/uEr5dTIAawKoQ6i9f/sf1/Sy\n"
1274 "xedsqR+IB+oKrzIDDWMgoJybN4pkZ8E5lzhVQIjFjKgFdWLzzqyW9z1gYfABQPlN\n"
1275 "FiS20WX0vgP1vcKAjdNrHzc9zyHBpgQzDmAj3NZZAoGBAI8vKCKdH7w3aL5CNkZQ\n"
1276 "2buIeWNA2HZazVwAGG5F2TU/LmXfRKnG6dX5bkU+AkBZh56jNZy//hfFSewJB4Kk\n"
1277 "buB7ERSdaNbO21zXt9FEA3+z0RfMd/Zv2vlIWOSB5nzl/7UKti3sribK6s9ZVLfi\n"
1278 "SxpiPQ8d/hmSGwn4ksrWUsJD\n"
1279 "-----END PRIVATE KEY-----\n";
1280 bssl::UniquePtr<BIO> bio(BIO_new_mem_buf(kKeyPEM, strlen(kKeyPEM)));
1281 return bssl::UniquePtr<EVP_PKEY>(
1282 PEM_read_bio_PrivateKey(bio.get(), nullptr, nullptr, nullptr));
1283}
1284
David Benjaminb79cc842016-12-07 15:57:14 -05001285static bool CompleteHandshakes(SSL *client, SSL *server) {
1286 // Drive both their handshakes to completion.
1287 for (;;) {
1288 int client_ret = SSL_do_handshake(client);
1289 int client_err = SSL_get_error(client, client_ret);
1290 if (client_err != SSL_ERROR_NONE &&
1291 client_err != SSL_ERROR_WANT_READ &&
1292 client_err != SSL_ERROR_WANT_WRITE) {
1293 fprintf(stderr, "Client error: %d\n", client_err);
1294 return false;
1295 }
1296
1297 int server_ret = SSL_do_handshake(server);
1298 int server_err = SSL_get_error(server, server_ret);
1299 if (server_err != SSL_ERROR_NONE &&
1300 server_err != SSL_ERROR_WANT_READ &&
1301 server_err != SSL_ERROR_WANT_WRITE) {
1302 fprintf(stderr, "Server error: %d\n", server_err);
1303 return false;
1304 }
1305
1306 if (client_ret == 1 && server_ret == 1) {
1307 break;
1308 }
1309 }
1310
1311 return true;
1312}
1313
1314static bool ConnectClientAndServer(bssl::UniquePtr<SSL> *out_client,
1315 bssl::UniquePtr<SSL> *out_server,
David Benjamina20e5352016-08-02 19:09:41 -04001316 SSL_CTX *client_ctx, SSL_CTX *server_ctx,
1317 SSL_SESSION *session) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001318 bssl::UniquePtr<SSL> client(SSL_new(client_ctx)), server(SSL_new(server_ctx));
David Benjaminde942382016-02-11 12:02:01 -05001319 if (!client || !server) {
1320 return false;
1321 }
1322 SSL_set_connect_state(client.get());
1323 SSL_set_accept_state(server.get());
1324
David Benjamina20e5352016-08-02 19:09:41 -04001325 SSL_set_session(client.get(), session);
1326
David Benjaminde942382016-02-11 12:02:01 -05001327 BIO *bio1, *bio2;
1328 if (!BIO_new_bio_pair(&bio1, 0, &bio2, 0)) {
1329 return false;
1330 }
1331 // SSL_set_bio takes ownership.
1332 SSL_set_bio(client.get(), bio1, bio1);
1333 SSL_set_bio(server.get(), bio2, bio2);
1334
David Benjaminb79cc842016-12-07 15:57:14 -05001335 if (!CompleteHandshakes(client.get(), server.get())) {
1336 return false;
David Benjaminde942382016-02-11 12:02:01 -05001337 }
1338
David Benjamin686bb192016-05-10 15:15:41 -04001339 *out_client = std::move(client);
1340 *out_server = std::move(server);
1341 return true;
1342}
1343
David Benjamin0fef3052016-11-18 15:11:10 +09001344static bool TestSequenceNumber(bool is_dtls, const SSL_METHOD *method,
1345 uint16_t version) {
1346 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(method));
1347 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(method));
1348 if (!server_ctx || !client_ctx ||
1349 !SSL_CTX_set_min_proto_version(client_ctx.get(), version) ||
1350 !SSL_CTX_set_max_proto_version(client_ctx.get(), version) ||
1351 !SSL_CTX_set_min_proto_version(server_ctx.get(), version) ||
1352 !SSL_CTX_set_max_proto_version(server_ctx.get(), version)) {
1353 return false;
1354 }
David Benjamin686bb192016-05-10 15:15:41 -04001355
David Benjamin0fef3052016-11-18 15:11:10 +09001356 bssl::UniquePtr<X509> cert = GetTestCertificate();
1357 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
1358 if (!cert || !key || !SSL_CTX_use_certificate(server_ctx.get(), cert.get()) ||
1359 !SSL_CTX_use_PrivateKey(server_ctx.get(), key.get())) {
1360 return false;
1361 }
David Benjamin686bb192016-05-10 15:15:41 -04001362
David Benjamin0fef3052016-11-18 15:11:10 +09001363 bssl::UniquePtr<SSL> client, server;
1364 if (!ConnectClientAndServer(&client, &server, client_ctx.get(),
1365 server_ctx.get(), nullptr /* no session */)) {
1366 return false;
1367 }
David Benjamin686bb192016-05-10 15:15:41 -04001368
David Benjamin0fef3052016-11-18 15:11:10 +09001369 // Drain any post-handshake messages to ensure there are no unread records
1370 // on either end.
1371 uint8_t byte = 0;
1372 if (SSL_read(client.get(), &byte, 1) > 0 ||
1373 SSL_read(server.get(), &byte, 1) > 0) {
1374 fprintf(stderr, "Received unexpected data.\n");
1375 return false;
1376 }
David Benjaminde942382016-02-11 12:02:01 -05001377
David Benjamin0fef3052016-11-18 15:11:10 +09001378 uint64_t client_read_seq = SSL_get_read_sequence(client.get());
1379 uint64_t client_write_seq = SSL_get_write_sequence(client.get());
1380 uint64_t server_read_seq = SSL_get_read_sequence(server.get());
1381 uint64_t server_write_seq = SSL_get_write_sequence(server.get());
Steven Valdez2c62fe92016-10-14 12:08:12 -04001382
David Benjamin0fef3052016-11-18 15:11:10 +09001383 if (is_dtls) {
1384 // Both client and server must be at epoch 1.
1385 if (EpochFromSequence(client_read_seq) != 1 ||
1386 EpochFromSequence(client_write_seq) != 1 ||
1387 EpochFromSequence(server_read_seq) != 1 ||
1388 EpochFromSequence(server_write_seq) != 1) {
1389 fprintf(stderr, "Bad epochs.\n");
1390 return false;
David Benjaminde942382016-02-11 12:02:01 -05001391 }
David Benjamin0fef3052016-11-18 15:11:10 +09001392
1393 // The next record to be written should exceed the largest received.
1394 if (client_write_seq <= server_read_seq ||
1395 server_write_seq <= client_read_seq) {
1396 fprintf(stderr, "Inconsistent sequence numbers.\n");
1397 return false;
1398 }
1399 } else {
1400 // The next record to be written should equal the next to be received.
1401 if (client_write_seq != server_read_seq ||
1402 server_write_seq != client_read_seq) {
1403 fprintf(stderr, "Inconsistent sequence numbers.\n");
1404 return false;
1405 }
1406 }
1407
1408 // Send a record from client to server.
1409 if (SSL_write(client.get(), &byte, 1) != 1 ||
1410 SSL_read(server.get(), &byte, 1) != 1) {
1411 fprintf(stderr, "Could not send byte.\n");
1412 return false;
1413 }
1414
1415 // The client write and server read sequence numbers should have
1416 // incremented.
1417 if (client_write_seq + 1 != SSL_get_write_sequence(client.get()) ||
1418 server_read_seq + 1 != SSL_get_read_sequence(server.get())) {
1419 fprintf(stderr, "Sequence numbers did not increment.\n");
1420 return false;
David Benjaminde942382016-02-11 12:02:01 -05001421 }
1422
1423 return true;
1424}
1425
David Benjamin68f37b72016-11-18 15:14:42 +09001426static bool TestOneSidedShutdown(bool is_dtls, const SSL_METHOD *method,
1427 uint16_t version) {
1428 // SSL_shutdown is a no-op in DTLS.
1429 if (is_dtls) {
1430 return true;
David Benjamin686bb192016-05-10 15:15:41 -04001431 }
1432
David Benjamin68f37b72016-11-18 15:14:42 +09001433 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(method));
1434 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(method));
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001435 bssl::UniquePtr<X509> cert = GetTestCertificate();
1436 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
David Benjamin68f37b72016-11-18 15:14:42 +09001437 if (!client_ctx || !server_ctx || !cert || !key ||
1438 !SSL_CTX_set_min_proto_version(server_ctx.get(), version) ||
1439 !SSL_CTX_set_max_proto_version(server_ctx.get(), version) ||
1440 !SSL_CTX_set_min_proto_version(client_ctx.get(), version) ||
1441 !SSL_CTX_set_max_proto_version(client_ctx.get(), version) ||
David Benjamin686bb192016-05-10 15:15:41 -04001442 !SSL_CTX_use_certificate(server_ctx.get(), cert.get()) ||
1443 !SSL_CTX_use_PrivateKey(server_ctx.get(), key.get())) {
1444 return false;
1445 }
1446
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001447 bssl::UniquePtr<SSL> client, server;
David Benjamin686bb192016-05-10 15:15:41 -04001448 if (!ConnectClientAndServer(&client, &server, client_ctx.get(),
David Benjamina20e5352016-08-02 19:09:41 -04001449 server_ctx.get(), nullptr /* no session */)) {
David Benjamin686bb192016-05-10 15:15:41 -04001450 return false;
1451 }
1452
1453 // Shut down half the connection. SSL_shutdown will return 0 to signal only
1454 // one side has shut down.
1455 if (SSL_shutdown(client.get()) != 0) {
1456 fprintf(stderr, "Could not shutdown.\n");
1457 return false;
1458 }
1459
1460 // Reading from the server should consume the EOF.
1461 uint8_t byte;
1462 if (SSL_read(server.get(), &byte, 1) != 0 ||
1463 SSL_get_error(server.get(), 0) != SSL_ERROR_ZERO_RETURN) {
1464 fprintf(stderr, "Connection was not shut down cleanly.\n");
1465 return false;
1466 }
1467
1468 // However, the server may continue to write data and then shut down the
1469 // connection.
1470 byte = 42;
1471 if (SSL_write(server.get(), &byte, 1) != 1 ||
1472 SSL_read(client.get(), &byte, 1) != 1 ||
1473 byte != 42) {
1474 fprintf(stderr, "Could not send byte.\n");
1475 return false;
1476 }
1477
1478 // The server may then shutdown the connection.
1479 if (SSL_shutdown(server.get()) != 1 ||
1480 SSL_shutdown(client.get()) != 1) {
1481 fprintf(stderr, "Could not complete shutdown.\n");
1482 return false;
1483 }
1484
1485 return true;
1486}
David Benjamin68f37b72016-11-18 15:14:42 +09001487
Steven Valdez87eab492016-06-27 16:34:59 -04001488static bool TestSessionDuplication() {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001489 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLS_method()));
1490 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(TLS_method()));
Steven Valdez87eab492016-06-27 16:34:59 -04001491 if (!client_ctx || !server_ctx) {
1492 return false;
1493 }
1494
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001495 bssl::UniquePtr<X509> cert = GetTestCertificate();
1496 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
Steven Valdez87eab492016-06-27 16:34:59 -04001497 if (!cert || !key ||
1498 !SSL_CTX_use_certificate(server_ctx.get(), cert.get()) ||
1499 !SSL_CTX_use_PrivateKey(server_ctx.get(), key.get())) {
1500 return false;
1501 }
1502
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001503 bssl::UniquePtr<SSL> client, server;
Steven Valdez87eab492016-06-27 16:34:59 -04001504 if (!ConnectClientAndServer(&client, &server, client_ctx.get(),
David Benjamina20e5352016-08-02 19:09:41 -04001505 server_ctx.get(), nullptr /* no session */)) {
Steven Valdez87eab492016-06-27 16:34:59 -04001506 return false;
1507 }
1508
1509 SSL_SESSION *session0 = SSL_get_session(client.get());
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001510 bssl::UniquePtr<SSL_SESSION> session1(SSL_SESSION_dup(session0, SSL_SESSION_DUP_ALL));
Steven Valdez87eab492016-06-27 16:34:59 -04001511 if (!session1) {
David Benjamin4501bd52016-08-01 13:39:41 -04001512 return false;
Steven Valdez87eab492016-06-27 16:34:59 -04001513 }
David Benjamin4501bd52016-08-01 13:39:41 -04001514
Steven Valdez84b5c002016-08-25 16:30:58 -04001515 session1->not_resumable = 0;
1516
Steven Valdez87eab492016-06-27 16:34:59 -04001517 uint8_t *s0_bytes, *s1_bytes;
1518 size_t s0_len, s1_len;
1519
1520 if (!SSL_SESSION_to_bytes(session0, &s0_bytes, &s0_len)) {
1521 return false;
1522 }
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001523 bssl::UniquePtr<uint8_t> free_s0(s0_bytes);
Steven Valdez87eab492016-06-27 16:34:59 -04001524
1525 if (!SSL_SESSION_to_bytes(session1.get(), &s1_bytes, &s1_len)) {
1526 return false;
1527 }
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001528 bssl::UniquePtr<uint8_t> free_s1(s1_bytes);
Steven Valdez87eab492016-06-27 16:34:59 -04001529
David Benjamin17cf2cb2016-12-13 01:07:13 -05001530 return s0_len == s1_len && OPENSSL_memcmp(s0_bytes, s1_bytes, s0_len) == 0;
Steven Valdez87eab492016-06-27 16:34:59 -04001531}
David Benjamin686bb192016-05-10 15:15:41 -04001532
David Benjamin5c0fb882016-06-14 14:03:51 -04001533static bool ExpectFDs(const SSL *ssl, int rfd, int wfd) {
1534 if (SSL_get_rfd(ssl) != rfd || SSL_get_wfd(ssl) != wfd) {
1535 fprintf(stderr, "Got fds %d and %d, wanted %d and %d.\n", SSL_get_rfd(ssl),
1536 SSL_get_wfd(ssl), rfd, wfd);
1537 return false;
1538 }
1539
1540 // The wrapper BIOs are always equal when fds are equal, even if set
1541 // individually.
1542 if (rfd == wfd && SSL_get_rbio(ssl) != SSL_get_wbio(ssl)) {
1543 fprintf(stderr, "rbio and wbio did not match.\n");
1544 return false;
1545 }
1546
1547 return true;
1548}
1549
1550static bool TestSetFD() {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001551 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
David Benjamin5c0fb882016-06-14 14:03:51 -04001552 if (!ctx) {
1553 return false;
1554 }
1555
1556 // Test setting different read and write FDs.
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001557 bssl::UniquePtr<SSL> ssl(SSL_new(ctx.get()));
David Benjamin5c0fb882016-06-14 14:03:51 -04001558 if (!ssl ||
1559 !SSL_set_rfd(ssl.get(), 1) ||
1560 !SSL_set_wfd(ssl.get(), 2) ||
1561 !ExpectFDs(ssl.get(), 1, 2)) {
1562 return false;
1563 }
1564
1565 // Test setting the same FD.
1566 ssl.reset(SSL_new(ctx.get()));
1567 if (!ssl ||
1568 !SSL_set_fd(ssl.get(), 1) ||
1569 !ExpectFDs(ssl.get(), 1, 1)) {
1570 return false;
1571 }
1572
1573 // Test setting the same FD one side at a time.
1574 ssl.reset(SSL_new(ctx.get()));
1575 if (!ssl ||
1576 !SSL_set_rfd(ssl.get(), 1) ||
1577 !SSL_set_wfd(ssl.get(), 1) ||
1578 !ExpectFDs(ssl.get(), 1, 1)) {
1579 return false;
1580 }
1581
1582 // Test setting the same FD in the other order.
1583 ssl.reset(SSL_new(ctx.get()));
1584 if (!ssl ||
1585 !SSL_set_wfd(ssl.get(), 1) ||
1586 !SSL_set_rfd(ssl.get(), 1) ||
1587 !ExpectFDs(ssl.get(), 1, 1)) {
1588 return false;
1589 }
1590
David Benjamin5c0fb882016-06-14 14:03:51 -04001591 // Test changing the read FD partway through.
1592 ssl.reset(SSL_new(ctx.get()));
1593 if (!ssl ||
1594 !SSL_set_fd(ssl.get(), 1) ||
1595 !SSL_set_rfd(ssl.get(), 2) ||
1596 !ExpectFDs(ssl.get(), 2, 1)) {
1597 return false;
1598 }
David Benjamin5c0fb882016-06-14 14:03:51 -04001599
1600 // Test changing the write FD partway through.
1601 ssl.reset(SSL_new(ctx.get()));
1602 if (!ssl ||
1603 !SSL_set_fd(ssl.get(), 1) ||
1604 !SSL_set_wfd(ssl.get(), 2) ||
1605 !ExpectFDs(ssl.get(), 1, 2)) {
1606 return false;
1607 }
1608
1609 // Test a no-op change to the read FD partway through.
1610 ssl.reset(SSL_new(ctx.get()));
1611 if (!ssl ||
1612 !SSL_set_fd(ssl.get(), 1) ||
1613 !SSL_set_rfd(ssl.get(), 1) ||
1614 !ExpectFDs(ssl.get(), 1, 1)) {
1615 return false;
1616 }
1617
1618 // Test a no-op change to the write FD partway through.
1619 ssl.reset(SSL_new(ctx.get()));
1620 if (!ssl ||
1621 !SSL_set_fd(ssl.get(), 1) ||
1622 !SSL_set_wfd(ssl.get(), 1) ||
1623 !ExpectFDs(ssl.get(), 1, 1)) {
1624 return false;
1625 }
1626
1627 // ASan builds will implicitly test that the internal |BIO| reference-counting
1628 // is correct.
1629
1630 return true;
1631}
1632
David Benjamin4501bd52016-08-01 13:39:41 -04001633static bool TestSetBIO() {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001634 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
David Benjamin4501bd52016-08-01 13:39:41 -04001635 if (!ctx) {
1636 return false;
1637 }
1638
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001639 bssl::UniquePtr<SSL> ssl(SSL_new(ctx.get()));
1640 bssl::UniquePtr<BIO> bio1(BIO_new(BIO_s_mem())), bio2(BIO_new(BIO_s_mem())),
David Benjamin4501bd52016-08-01 13:39:41 -04001641 bio3(BIO_new(BIO_s_mem()));
1642 if (!ssl || !bio1 || !bio2 || !bio3) {
1643 return false;
1644 }
1645
1646 // SSL_set_bio takes one reference when the parameters are the same.
1647 BIO_up_ref(bio1.get());
1648 SSL_set_bio(ssl.get(), bio1.get(), bio1.get());
1649
1650 // Repeating the call does nothing.
1651 SSL_set_bio(ssl.get(), bio1.get(), bio1.get());
1652
1653 // It takes one reference each when the parameters are different.
1654 BIO_up_ref(bio2.get());
1655 BIO_up_ref(bio3.get());
1656 SSL_set_bio(ssl.get(), bio2.get(), bio3.get());
1657
1658 // Repeating the call does nothing.
1659 SSL_set_bio(ssl.get(), bio2.get(), bio3.get());
1660
1661 // It takes one reference when changing only wbio.
1662 BIO_up_ref(bio1.get());
1663 SSL_set_bio(ssl.get(), bio2.get(), bio1.get());
1664
1665 // It takes one reference when changing only rbio and the two are different.
1666 BIO_up_ref(bio3.get());
1667 SSL_set_bio(ssl.get(), bio3.get(), bio1.get());
1668
1669 // If setting wbio to rbio, it takes no additional references.
1670 SSL_set_bio(ssl.get(), bio3.get(), bio3.get());
1671
1672 // From there, wbio may be switched to something else.
1673 BIO_up_ref(bio1.get());
1674 SSL_set_bio(ssl.get(), bio3.get(), bio1.get());
1675
1676 // If setting rbio to wbio, it takes no additional references.
1677 SSL_set_bio(ssl.get(), bio1.get(), bio1.get());
1678
1679 // From there, rbio may be switched to something else, but, for historical
1680 // reasons, it takes a reference to both parameters.
1681 BIO_up_ref(bio1.get());
1682 BIO_up_ref(bio2.get());
1683 SSL_set_bio(ssl.get(), bio2.get(), bio1.get());
1684
1685 // ASAN builds will implicitly test that the internal |BIO| reference-counting
1686 // is correct.
1687 return true;
1688}
1689
David Benjamin25490f22016-07-14 00:22:54 -04001690static int VerifySucceed(X509_STORE_CTX *store_ctx, void *arg) { return 1; }
1691
David Benjamin0fef3052016-11-18 15:11:10 +09001692static bool TestGetPeerCertificate(bool is_dtls, const SSL_METHOD *method,
1693 uint16_t version) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001694 bssl::UniquePtr<X509> cert = GetTestCertificate();
1695 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
David Benjaminadd5e522016-07-14 00:33:24 -04001696 if (!cert || !key) {
1697 return false;
1698 }
1699
David Benjamin0fef3052016-11-18 15:11:10 +09001700 // Configure both client and server to accept any certificate.
1701 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(method));
1702 if (!ctx ||
1703 !SSL_CTX_use_certificate(ctx.get(), cert.get()) ||
1704 !SSL_CTX_use_PrivateKey(ctx.get(), key.get()) ||
1705 !SSL_CTX_set_min_proto_version(ctx.get(), version) ||
1706 !SSL_CTX_set_max_proto_version(ctx.get(), version)) {
1707 return false;
1708 }
1709 SSL_CTX_set_verify(
1710 ctx.get(), SSL_VERIFY_PEER | SSL_VERIFY_FAIL_IF_NO_PEER_CERT, nullptr);
1711 SSL_CTX_set_cert_verify_callback(ctx.get(), VerifySucceed, NULL);
David Benjaminadd5e522016-07-14 00:33:24 -04001712
David Benjamin0fef3052016-11-18 15:11:10 +09001713 bssl::UniquePtr<SSL> client, server;
1714 if (!ConnectClientAndServer(&client, &server, ctx.get(), ctx.get(),
1715 nullptr /* no session */)) {
1716 return false;
1717 }
David Benjaminadd5e522016-07-14 00:33:24 -04001718
David Benjamin0fef3052016-11-18 15:11:10 +09001719 // Client and server should both see the leaf certificate.
1720 bssl::UniquePtr<X509> peer(SSL_get_peer_certificate(server.get()));
1721 if (!peer || X509_cmp(cert.get(), peer.get()) != 0) {
1722 fprintf(stderr, "Server peer certificate did not match.\n");
1723 return false;
1724 }
David Benjaminadd5e522016-07-14 00:33:24 -04001725
David Benjamin0fef3052016-11-18 15:11:10 +09001726 peer.reset(SSL_get_peer_certificate(client.get()));
1727 if (!peer || X509_cmp(cert.get(), peer.get()) != 0) {
1728 fprintf(stderr, "Client peer certificate did not match.\n");
1729 return false;
1730 }
David Benjaminadd5e522016-07-14 00:33:24 -04001731
David Benjamin0fef3052016-11-18 15:11:10 +09001732 // However, for historical reasons, the chain includes the leaf on the
1733 // client, but does not on the server.
1734 if (sk_X509_num(SSL_get_peer_cert_chain(client.get())) != 1) {
1735 fprintf(stderr, "Client peer chain was incorrect.\n");
1736 return false;
1737 }
David Benjaminadd5e522016-07-14 00:33:24 -04001738
David Benjamin0fef3052016-11-18 15:11:10 +09001739 if (sk_X509_num(SSL_get_peer_cert_chain(server.get())) != 0) {
1740 fprintf(stderr, "Server peer chain was incorrect.\n");
1741 return false;
David Benjaminadd5e522016-07-14 00:33:24 -04001742 }
1743
1744 return true;
1745}
1746
David Benjamin0fef3052016-11-18 15:11:10 +09001747static bool TestRetainOnlySHA256OfCerts(bool is_dtls, const SSL_METHOD *method,
1748 uint16_t version) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001749 bssl::UniquePtr<X509> cert = GetTestCertificate();
1750 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
David Benjamin25490f22016-07-14 00:22:54 -04001751 if (!cert || !key) {
1752 return false;
1753 }
1754
1755 uint8_t *cert_der = NULL;
1756 int cert_der_len = i2d_X509(cert.get(), &cert_der);
1757 if (cert_der_len < 0) {
1758 return false;
1759 }
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001760 bssl::UniquePtr<uint8_t> free_cert_der(cert_der);
David Benjamin25490f22016-07-14 00:22:54 -04001761
1762 uint8_t cert_sha256[SHA256_DIGEST_LENGTH];
1763 SHA256(cert_der, cert_der_len, cert_sha256);
1764
David Benjamin0fef3052016-11-18 15:11:10 +09001765 // Configure both client and server to accept any certificate, but the
1766 // server must retain only the SHA-256 of the peer.
1767 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(method));
1768 if (!ctx ||
1769 !SSL_CTX_use_certificate(ctx.get(), cert.get()) ||
1770 !SSL_CTX_use_PrivateKey(ctx.get(), key.get()) ||
1771 !SSL_CTX_set_min_proto_version(ctx.get(), version) ||
1772 !SSL_CTX_set_max_proto_version(ctx.get(), version)) {
1773 return false;
1774 }
1775 SSL_CTX_set_verify(
1776 ctx.get(), SSL_VERIFY_PEER | SSL_VERIFY_FAIL_IF_NO_PEER_CERT, nullptr);
1777 SSL_CTX_set_cert_verify_callback(ctx.get(), VerifySucceed, NULL);
1778 SSL_CTX_set_retain_only_sha256_of_client_certs(ctx.get(), 1);
David Benjamin25490f22016-07-14 00:22:54 -04001779
David Benjamin0fef3052016-11-18 15:11:10 +09001780 bssl::UniquePtr<SSL> client, server;
1781 if (!ConnectClientAndServer(&client, &server, ctx.get(), ctx.get(),
1782 nullptr /* no session */)) {
1783 return false;
1784 }
David Benjamin25490f22016-07-14 00:22:54 -04001785
David Benjamin0fef3052016-11-18 15:11:10 +09001786 // The peer certificate has been dropped.
1787 bssl::UniquePtr<X509> peer(SSL_get_peer_certificate(server.get()));
1788 if (peer) {
1789 fprintf(stderr, "Peer certificate was retained.\n");
1790 return false;
1791 }
David Benjamin25490f22016-07-14 00:22:54 -04001792
David Benjamin0fef3052016-11-18 15:11:10 +09001793 SSL_SESSION *session = SSL_get_session(server.get());
1794 if (!session->peer_sha256_valid) {
1795 fprintf(stderr, "peer_sha256_valid was not set.\n");
1796 return false;
1797 }
David Benjamin25490f22016-07-14 00:22:54 -04001798
David Benjamin17cf2cb2016-12-13 01:07:13 -05001799 if (OPENSSL_memcmp(cert_sha256, session->peer_sha256, SHA256_DIGEST_LENGTH) !=
1800 0) {
David Benjamin0fef3052016-11-18 15:11:10 +09001801 fprintf(stderr, "peer_sha256 did not match.\n");
1802 return false;
David Benjamin25490f22016-07-14 00:22:54 -04001803 }
1804
1805 return true;
1806}
1807
David Benjaminafc64de2016-07-19 17:12:41 +02001808static bool ClientHelloMatches(uint16_t version, const uint8_t *expected,
1809 size_t expected_len) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001810 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
David Benjamin2dc02042016-09-19 19:57:37 -04001811 if (!ctx ||
David Benjamine4706902016-09-20 15:12:23 -04001812 !SSL_CTX_set_max_proto_version(ctx.get(), version) ||
David Benjamin2dc02042016-09-19 19:57:37 -04001813 // Our default cipher list varies by CPU capabilities, so manually place
1814 // the ChaCha20 ciphers in front.
1815 !SSL_CTX_set_cipher_list(ctx.get(), "CHACHA20:ALL")) {
David Benjaminafc64de2016-07-19 17:12:41 +02001816 return false;
1817 }
David Benjamin2dc02042016-09-19 19:57:37 -04001818
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001819 bssl::UniquePtr<SSL> ssl(SSL_new(ctx.get()));
David Benjaminafc64de2016-07-19 17:12:41 +02001820 if (!ssl) {
1821 return false;
1822 }
1823 std::vector<uint8_t> client_hello;
1824 if (!GetClientHello(ssl.get(), &client_hello)) {
1825 return false;
1826 }
1827
1828 // Zero the client_random.
1829 constexpr size_t kRandomOffset = 1 + 2 + 2 + // record header
1830 1 + 3 + // handshake message header
1831 2; // client_version
1832 if (client_hello.size() < kRandomOffset + SSL3_RANDOM_SIZE) {
1833 fprintf(stderr, "ClientHello for version %04x too short.\n", version);
1834 return false;
1835 }
David Benjamin17cf2cb2016-12-13 01:07:13 -05001836 OPENSSL_memset(client_hello.data() + kRandomOffset, 0, SSL3_RANDOM_SIZE);
David Benjaminafc64de2016-07-19 17:12:41 +02001837
1838 if (client_hello.size() != expected_len ||
David Benjamin17cf2cb2016-12-13 01:07:13 -05001839 OPENSSL_memcmp(client_hello.data(), expected, expected_len) != 0) {
David Benjaminafc64de2016-07-19 17:12:41 +02001840 fprintf(stderr, "ClientHello for version %04x did not match:\n", version);
1841 fprintf(stderr, "Got:\n\t");
1842 for (size_t i = 0; i < client_hello.size(); i++) {
1843 fprintf(stderr, "0x%02x, ", client_hello[i]);
1844 }
1845 fprintf(stderr, "\nWanted:\n\t");
1846 for (size_t i = 0; i < expected_len; i++) {
1847 fprintf(stderr, "0x%02x, ", expected[i]);
1848 }
1849 fprintf(stderr, "\n");
1850 return false;
1851 }
1852
1853 return true;
1854}
1855
1856// Tests that our ClientHellos do not change unexpectedly.
1857static bool TestClientHello() {
1858 static const uint8_t kSSL3ClientHello[] = {
Matt Braithwaite9c8c4182016-08-24 14:36:54 -07001859 0x16,
1860 0x03, 0x00,
1861 0x00, 0x3f,
1862 0x01,
1863 0x00, 0x00, 0x3b,
1864 0x03, 0x00,
1865 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1866 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1867 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1868 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1869 0x00,
1870 0x00, 0x14,
1871 0xc0, 0x09,
1872 0xc0, 0x13,
1873 0x00, 0x33,
1874 0xc0, 0x0a,
1875 0xc0, 0x14,
1876 0x00, 0x39,
1877 0x00, 0x2f,
1878 0x00, 0x35,
1879 0x00, 0x0a,
1880 0x00, 0xff, 0x01, 0x00,
David Benjaminafc64de2016-07-19 17:12:41 +02001881 };
1882 if (!ClientHelloMatches(SSL3_VERSION, kSSL3ClientHello,
1883 sizeof(kSSL3ClientHello))) {
1884 return false;
1885 }
1886
1887 static const uint8_t kTLS1ClientHello[] = {
Matt Braithwaite9c8c4182016-08-24 14:36:54 -07001888 0x16,
1889 0x03, 0x01,
1890 0x00, 0x5e,
1891 0x01,
1892 0x00, 0x00, 0x5a,
1893 0x03, 0x01,
1894 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1895 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1896 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1897 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1898 0x00,
1899 0x00, 0x12,
1900 0xc0, 0x09,
1901 0xc0, 0x13,
1902 0x00, 0x33,
1903 0xc0, 0x0a,
1904 0xc0, 0x14,
1905 0x00, 0x39,
1906 0x00, 0x2f,
1907 0x00, 0x35,
1908 0x00, 0x0a,
David Benjaminafc64de2016-07-19 17:12:41 +02001909 0x01, 0x00, 0x00, 0x1f, 0xff, 0x01, 0x00, 0x01, 0x00, 0x00, 0x17, 0x00,
1910 0x00, 0x00, 0x23, 0x00, 0x00, 0x00, 0x0b, 0x00, 0x02, 0x01, 0x00, 0x00,
1911 0x0a, 0x00, 0x08, 0x00, 0x06, 0x00, 0x1d, 0x00, 0x17, 0x00, 0x18,
1912 };
1913 if (!ClientHelloMatches(TLS1_VERSION, kTLS1ClientHello,
1914 sizeof(kTLS1ClientHello))) {
1915 return false;
1916 }
1917
1918 static const uint8_t kTLS11ClientHello[] = {
Matt Braithwaite9c8c4182016-08-24 14:36:54 -07001919 0x16,
1920 0x03, 0x01,
1921 0x00, 0x5e,
1922 0x01,
1923 0x00, 0x00, 0x5a,
1924 0x03, 0x02,
1925 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1926 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1927 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1928 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1929 0x00,
1930 0x00, 0x12,
1931 0xc0, 0x09,
1932 0xc0, 0x13,
1933 0x00, 0x33,
1934 0xc0, 0x0a,
1935 0xc0, 0x14,
1936 0x00, 0x39,
1937 0x00, 0x2f,
1938 0x00, 0x35,
1939 0x00, 0x0a,
David Benjaminafc64de2016-07-19 17:12:41 +02001940 0x01, 0x00, 0x00, 0x1f, 0xff, 0x01, 0x00, 0x01, 0x00, 0x00, 0x17, 0x00,
1941 0x00, 0x00, 0x23, 0x00, 0x00, 0x00, 0x0b, 0x00, 0x02, 0x01, 0x00, 0x00,
1942 0x0a, 0x00, 0x08, 0x00, 0x06, 0x00, 0x1d, 0x00, 0x17, 0x00, 0x18,
1943 };
1944 if (!ClientHelloMatches(TLS1_1_VERSION, kTLS11ClientHello,
1945 sizeof(kTLS11ClientHello))) {
1946 return false;
1947 }
1948
1949 static const uint8_t kTLS12ClientHello[] = {
David Benjamin3ef76972016-10-17 17:59:54 -04001950 0x16, 0x03, 0x01, 0x00, 0x9e, 0x01, 0x00, 0x00, 0x9a, 0x03, 0x03, 0x00,
David Benjamin57e929f2016-08-30 00:30:38 -04001951 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1952 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1953 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x3a, 0xcc, 0xa9,
1954 0xcc, 0xa8, 0xcc, 0x14, 0xcc, 0x13, 0xc0, 0x2b, 0xc0, 0x2f, 0x00, 0x9e,
1955 0xc0, 0x2c, 0xc0, 0x30, 0x00, 0x9f, 0xc0, 0x09, 0xc0, 0x23, 0xc0, 0x13,
1956 0xc0, 0x27, 0x00, 0x33, 0x00, 0x67, 0xc0, 0x0a, 0xc0, 0x24, 0xc0, 0x14,
1957 0xc0, 0x28, 0x00, 0x39, 0x00, 0x6b, 0x00, 0x9c, 0x00, 0x9d, 0x00, 0x2f,
David Benjamin3ef76972016-10-17 17:59:54 -04001958 0x00, 0x3c, 0x00, 0x35, 0x00, 0x3d, 0x00, 0x0a, 0x01, 0x00, 0x00, 0x37,
David Benjamin57e929f2016-08-30 00:30:38 -04001959 0xff, 0x01, 0x00, 0x01, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x23, 0x00,
David Benjamin3a322f52016-10-26 12:45:35 -04001960 0x00, 0x00, 0x0d, 0x00, 0x14, 0x00, 0x12, 0x04, 0x03, 0x08, 0x04, 0x04,
1961 0x01, 0x05, 0x03, 0x08, 0x05, 0x05, 0x01, 0x08, 0x06, 0x06, 0x01, 0x02,
David Benjamin3ef76972016-10-17 17:59:54 -04001962 0x01, 0x00, 0x0b, 0x00, 0x02, 0x01, 0x00, 0x00, 0x0a, 0x00, 0x08, 0x00,
1963 0x06, 0x00, 0x1d, 0x00, 0x17, 0x00, 0x18,
David Benjaminafc64de2016-07-19 17:12:41 +02001964 };
1965 if (!ClientHelloMatches(TLS1_2_VERSION, kTLS12ClientHello,
1966 sizeof(kTLS12ClientHello))) {
1967 return false;
1968 }
1969
1970 // TODO(davidben): Add a change detector for TLS 1.3 once the spec and our
1971 // implementation has settled enough that it won't change.
1972
1973 return true;
1974}
1975
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001976static bssl::UniquePtr<SSL_SESSION> g_last_session;
David Benjamina20e5352016-08-02 19:09:41 -04001977
1978static int SaveLastSession(SSL *ssl, SSL_SESSION *session) {
1979 // Save the most recent session.
1980 g_last_session.reset(session);
1981 return 1;
1982}
1983
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001984static bssl::UniquePtr<SSL_SESSION> CreateClientSession(SSL_CTX *client_ctx,
David Benjamina20e5352016-08-02 19:09:41 -04001985 SSL_CTX *server_ctx) {
1986 g_last_session = nullptr;
1987 SSL_CTX_sess_set_new_cb(client_ctx, SaveLastSession);
1988
1989 // Connect client and server to get a session.
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001990 bssl::UniquePtr<SSL> client, server;
David Benjamina20e5352016-08-02 19:09:41 -04001991 if (!ConnectClientAndServer(&client, &server, client_ctx, server_ctx,
1992 nullptr /* no session */)) {
1993 fprintf(stderr, "Failed to connect client and server.\n");
1994 return nullptr;
1995 }
1996
1997 // Run the read loop to account for post-handshake tickets in TLS 1.3.
1998 SSL_read(client.get(), nullptr, 0);
1999
2000 SSL_CTX_sess_set_new_cb(client_ctx, nullptr);
2001
2002 if (!g_last_session) {
2003 fprintf(stderr, "Client did not receive a session.\n");
2004 return nullptr;
2005 }
2006 return std::move(g_last_session);
2007}
2008
2009static bool ExpectSessionReused(SSL_CTX *client_ctx, SSL_CTX *server_ctx,
2010 SSL_SESSION *session,
2011 bool reused) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002012 bssl::UniquePtr<SSL> client, server;
David Benjamina20e5352016-08-02 19:09:41 -04002013 if (!ConnectClientAndServer(&client, &server, client_ctx,
2014 server_ctx, session)) {
2015 fprintf(stderr, "Failed to connect client and server.\n");
2016 return false;
2017 }
2018
2019 if (SSL_session_reused(client.get()) != SSL_session_reused(server.get())) {
2020 fprintf(stderr, "Client and server were inconsistent.\n");
2021 return false;
2022 }
2023
2024 bool was_reused = !!SSL_session_reused(client.get());
2025 if (was_reused != reused) {
2026 fprintf(stderr, "Session was%s reused, but we expected the opposite.\n",
2027 was_reused ? "" : " not");
2028 return false;
2029 }
2030
2031 return true;
2032}
2033
David Benjamin3c51d9b2016-11-01 17:50:42 -04002034static bssl::UniquePtr<SSL_SESSION> ExpectSessionRenewed(SSL_CTX *client_ctx,
2035 SSL_CTX *server_ctx,
2036 SSL_SESSION *session) {
2037 g_last_session = nullptr;
2038 SSL_CTX_sess_set_new_cb(client_ctx, SaveLastSession);
2039
2040 bssl::UniquePtr<SSL> client, server;
2041 if (!ConnectClientAndServer(&client, &server, client_ctx,
2042 server_ctx, session)) {
2043 fprintf(stderr, "Failed to connect client and server.\n");
2044 return nullptr;
2045 }
2046
2047 if (SSL_session_reused(client.get()) != SSL_session_reused(server.get())) {
2048 fprintf(stderr, "Client and server were inconsistent.\n");
2049 return nullptr;
2050 }
2051
2052 if (!SSL_session_reused(client.get())) {
2053 fprintf(stderr, "Session was not reused.\n");
2054 return nullptr;
2055 }
2056
2057 // Run the read loop to account for post-handshake tickets in TLS 1.3.
2058 SSL_read(client.get(), nullptr, 0);
2059
2060 SSL_CTX_sess_set_new_cb(client_ctx, nullptr);
2061
2062 if (!g_last_session) {
2063 fprintf(stderr, "Client did not receive a renewed session.\n");
2064 return nullptr;
2065 }
2066 return std::move(g_last_session);
2067}
2068
David Benjamina933c382016-10-28 00:10:03 -04002069static int SwitchSessionIDContextSNI(SSL *ssl, int *out_alert, void *arg) {
2070 static const uint8_t kContext[] = {3};
2071
2072 if (!SSL_set_session_id_context(ssl, kContext, sizeof(kContext))) {
2073 return SSL_TLSEXT_ERR_ALERT_FATAL;
2074 }
2075
2076 return SSL_TLSEXT_ERR_OK;
2077}
2078
David Benjamin731058e2016-12-03 23:15:13 -05002079static int SwitchSessionIDContextEarly(const SSL_CLIENT_HELLO *client_hello) {
David Benjamina933c382016-10-28 00:10:03 -04002080 static const uint8_t kContext[] = {3};
2081
David Benjamin731058e2016-12-03 23:15:13 -05002082 if (!SSL_set_session_id_context(client_hello->ssl, kContext,
2083 sizeof(kContext))) {
David Benjamina933c382016-10-28 00:10:03 -04002084 return -1;
2085 }
2086
2087 return 1;
2088}
2089
David Benjamin0fef3052016-11-18 15:11:10 +09002090static bool TestSessionIDContext(bool is_dtls, const SSL_METHOD *method,
2091 uint16_t version) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002092 bssl::UniquePtr<X509> cert = GetTestCertificate();
2093 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
David Benjamina20e5352016-08-02 19:09:41 -04002094 if (!cert || !key) {
2095 return false;
2096 }
2097
2098 static const uint8_t kContext1[] = {1};
2099 static const uint8_t kContext2[] = {2};
2100
David Benjamin0fef3052016-11-18 15:11:10 +09002101 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(method));
2102 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(method));
2103 if (!server_ctx || !client_ctx ||
2104 !SSL_CTX_use_certificate(server_ctx.get(), cert.get()) ||
2105 !SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()) ||
2106 !SSL_CTX_set_session_id_context(server_ctx.get(), kContext1,
2107 sizeof(kContext1)) ||
2108 !SSL_CTX_set_min_proto_version(client_ctx.get(), version) ||
2109 !SSL_CTX_set_max_proto_version(client_ctx.get(), version) ||
2110 !SSL_CTX_set_min_proto_version(server_ctx.get(), version) ||
2111 !SSL_CTX_set_max_proto_version(server_ctx.get(), version)) {
2112 return false;
2113 }
David Benjamina20e5352016-08-02 19:09:41 -04002114
David Benjamin0fef3052016-11-18 15:11:10 +09002115 SSL_CTX_set_session_cache_mode(client_ctx.get(), SSL_SESS_CACHE_BOTH);
2116 SSL_CTX_set_session_cache_mode(server_ctx.get(), SSL_SESS_CACHE_BOTH);
David Benjamina20e5352016-08-02 19:09:41 -04002117
David Benjamin0fef3052016-11-18 15:11:10 +09002118 bssl::UniquePtr<SSL_SESSION> session =
2119 CreateClientSession(client_ctx.get(), server_ctx.get());
2120 if (!session) {
2121 fprintf(stderr, "Error getting session.\n");
2122 return false;
2123 }
David Benjamina20e5352016-08-02 19:09:41 -04002124
David Benjamin0fef3052016-11-18 15:11:10 +09002125 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(), session.get(),
2126 true /* expect session reused */)) {
2127 fprintf(stderr, "Error resuming session.\n");
2128 return false;
2129 }
David Benjamina20e5352016-08-02 19:09:41 -04002130
David Benjamin0fef3052016-11-18 15:11:10 +09002131 // Change the session ID context.
2132 if (!SSL_CTX_set_session_id_context(server_ctx.get(), kContext2,
2133 sizeof(kContext2))) {
2134 return false;
2135 }
David Benjamina20e5352016-08-02 19:09:41 -04002136
David Benjamin0fef3052016-11-18 15:11:10 +09002137 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(), session.get(),
2138 false /* expect session not reused */)) {
2139 fprintf(stderr, "Error connecting with a different context.\n");
2140 return false;
2141 }
David Benjamina933c382016-10-28 00:10:03 -04002142
David Benjamin0fef3052016-11-18 15:11:10 +09002143 // Change the session ID context back and install an SNI callback to switch
2144 // it.
2145 if (!SSL_CTX_set_session_id_context(server_ctx.get(), kContext1,
2146 sizeof(kContext1))) {
2147 return false;
2148 }
David Benjamina933c382016-10-28 00:10:03 -04002149
David Benjamin0fef3052016-11-18 15:11:10 +09002150 SSL_CTX_set_tlsext_servername_callback(server_ctx.get(),
2151 SwitchSessionIDContextSNI);
David Benjamina933c382016-10-28 00:10:03 -04002152
David Benjamin0fef3052016-11-18 15:11:10 +09002153 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(), session.get(),
2154 false /* expect session not reused */)) {
2155 fprintf(stderr, "Error connecting with a context switch on SNI callback.\n");
2156 return false;
2157 }
David Benjamina933c382016-10-28 00:10:03 -04002158
David Benjamin0fef3052016-11-18 15:11:10 +09002159 // Switch the session ID context with the early callback instead.
2160 SSL_CTX_set_tlsext_servername_callback(server_ctx.get(), nullptr);
2161 SSL_CTX_set_select_certificate_cb(server_ctx.get(),
2162 SwitchSessionIDContextEarly);
David Benjamina933c382016-10-28 00:10:03 -04002163
David Benjamin0fef3052016-11-18 15:11:10 +09002164 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(), session.get(),
2165 false /* expect session not reused */)) {
2166 fprintf(stderr,
2167 "Error connecting with a context switch on early callback.\n");
2168 return false;
David Benjamina20e5352016-08-02 19:09:41 -04002169 }
2170
2171 return true;
2172}
2173
David Benjamin721e8b72016-08-03 13:13:17 -04002174static timeval g_current_time;
2175
2176static void CurrentTimeCallback(const SSL *ssl, timeval *out_clock) {
2177 *out_clock = g_current_time;
2178}
2179
David Benjamin3c51d9b2016-11-01 17:50:42 -04002180static int RenewTicketCallback(SSL *ssl, uint8_t *key_name, uint8_t *iv,
2181 EVP_CIPHER_CTX *ctx, HMAC_CTX *hmac_ctx,
2182 int encrypt) {
2183 static const uint8_t kZeros[16] = {0};
2184
2185 if (encrypt) {
David Benjamin17cf2cb2016-12-13 01:07:13 -05002186 OPENSSL_memcpy(key_name, kZeros, sizeof(kZeros));
David Benjamin3c51d9b2016-11-01 17:50:42 -04002187 RAND_bytes(iv, 16);
David Benjamin17cf2cb2016-12-13 01:07:13 -05002188 } else if (OPENSSL_memcmp(key_name, kZeros, 16) != 0) {
David Benjamin3c51d9b2016-11-01 17:50:42 -04002189 return 0;
2190 }
2191
2192 if (!HMAC_Init_ex(hmac_ctx, kZeros, sizeof(kZeros), EVP_sha256(), NULL) ||
2193 !EVP_CipherInit_ex(ctx, EVP_aes_128_cbc(), NULL, kZeros, iv, encrypt)) {
2194 return -1;
2195 }
2196
2197 // Returning two from the callback in decrypt mode renews the
2198 // session in TLS 1.2 and below.
2199 return encrypt ? 1 : 2;
2200}
2201
David Benjamin123db572016-11-03 16:59:25 -04002202static bool GetServerTicketTime(long *out, const SSL_SESSION *session) {
David Benjamin123db572016-11-03 16:59:25 -04002203 if (session->tlsext_ticklen < 16 + 16 + SHA256_DIGEST_LENGTH) {
2204 return false;
2205 }
2206
David Benjamin123db572016-11-03 16:59:25 -04002207 const uint8_t *ciphertext = session->tlsext_tick + 16 + 16;
2208 size_t len = session->tlsext_ticklen - 16 - 16 - SHA256_DIGEST_LENGTH;
2209 std::unique_ptr<uint8_t[]> plaintext(new uint8_t[len]);
2210
David Benjamin9b63f292016-11-15 00:44:05 -05002211#if defined(BORINGSSL_UNSAFE_FUZZER_MODE)
2212 // Fuzzer-mode tickets are unencrypted.
David Benjamin17cf2cb2016-12-13 01:07:13 -05002213 OPENSSL_memcpy(plaintext.get(), ciphertext, len);
David Benjamin9b63f292016-11-15 00:44:05 -05002214#else
2215 static const uint8_t kZeros[16] = {0};
2216 const uint8_t *iv = session->tlsext_tick + 16;
David Benjamin123db572016-11-03 16:59:25 -04002217 bssl::ScopedEVP_CIPHER_CTX ctx;
2218 int len1, len2;
2219 if (!EVP_DecryptInit_ex(ctx.get(), EVP_aes_128_cbc(), nullptr, kZeros, iv) ||
2220 !EVP_DecryptUpdate(ctx.get(), plaintext.get(), &len1, ciphertext, len) ||
2221 !EVP_DecryptFinal_ex(ctx.get(), plaintext.get() + len1, &len2)) {
2222 return false;
2223 }
2224
2225 len = static_cast<size_t>(len1 + len2);
David Benjamin9b63f292016-11-15 00:44:05 -05002226#endif
David Benjamin123db572016-11-03 16:59:25 -04002227
2228 bssl::UniquePtr<SSL_SESSION> server_session(
2229 SSL_SESSION_from_bytes(plaintext.get(), len));
2230 if (!server_session) {
2231 return false;
2232 }
2233
2234 *out = server_session->time;
2235 return true;
2236}
2237
David Benjamin0fef3052016-11-18 15:11:10 +09002238static bool TestSessionTimeout(bool is_dtls, const SSL_METHOD *method,
2239 uint16_t version) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002240 bssl::UniquePtr<X509> cert = GetTestCertificate();
2241 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
David Benjamin721e8b72016-08-03 13:13:17 -04002242 if (!cert || !key) {
2243 return false;
2244 }
2245
David Benjamin0fef3052016-11-18 15:11:10 +09002246 for (bool server_test : std::vector<bool>{false, true}) {
2247 static const int kStartTime = 1000;
2248 g_current_time.tv_sec = kStartTime;
David Benjamin1b22f852016-10-27 16:36:32 -04002249
David Benjamin0fef3052016-11-18 15:11:10 +09002250 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(method));
2251 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(method));
2252 if (!server_ctx || !client_ctx ||
2253 !SSL_CTX_use_certificate(server_ctx.get(), cert.get()) ||
2254 !SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()) ||
2255 !SSL_CTX_set_min_proto_version(client_ctx.get(), version) ||
2256 !SSL_CTX_set_max_proto_version(client_ctx.get(), version) ||
2257 !SSL_CTX_set_min_proto_version(server_ctx.get(), version) ||
2258 !SSL_CTX_set_max_proto_version(server_ctx.get(), version)) {
2259 return false;
2260 }
2261
2262 SSL_CTX_set_session_cache_mode(client_ctx.get(), SSL_SESS_CACHE_BOTH);
2263 SSL_CTX_set_session_cache_mode(server_ctx.get(), SSL_SESS_CACHE_BOTH);
2264
2265 // Both client and server must enforce session timeouts.
2266 if (server_test) {
2267 SSL_CTX_set_current_time_cb(server_ctx.get(), CurrentTimeCallback);
2268 } else {
2269 SSL_CTX_set_current_time_cb(client_ctx.get(), CurrentTimeCallback);
2270 }
2271
2272 // Configure a ticket callback which renews tickets.
2273 SSL_CTX_set_tlsext_ticket_key_cb(server_ctx.get(), RenewTicketCallback);
2274
2275 bssl::UniquePtr<SSL_SESSION> session =
2276 CreateClientSession(client_ctx.get(), server_ctx.get());
2277 if (!session) {
2278 fprintf(stderr, "Error getting session.\n");
2279 return false;
2280 }
2281
2282 // Advance the clock just behind the timeout.
2283 g_current_time.tv_sec += SSL_DEFAULT_SESSION_TIMEOUT - 1;
2284
2285 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(), session.get(),
2286 true /* expect session reused */)) {
2287 fprintf(stderr, "Error resuming session.\n");
2288 return false;
2289 }
2290
2291 // Advance the clock one more second.
2292 g_current_time.tv_sec++;
2293
2294 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(), session.get(),
2295 false /* expect session not reused */)) {
2296 fprintf(stderr, "Error resuming session.\n");
2297 return false;
2298 }
2299
2300 // Rewind the clock to before the session was minted.
2301 g_current_time.tv_sec = kStartTime - 1;
2302
2303 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(), session.get(),
2304 false /* expect session not reused */)) {
2305 fprintf(stderr, "Error resuming session.\n");
2306 return false;
2307 }
2308
2309 // SSL 3.0 cannot renew sessions.
2310 if (version == SSL3_VERSION) {
2311 continue;
2312 }
2313
2314 // Renew the session 10 seconds before expiration.
2315 g_current_time.tv_sec = kStartTime + SSL_DEFAULT_SESSION_TIMEOUT - 10;
2316 bssl::UniquePtr<SSL_SESSION> new_session =
2317 ExpectSessionRenewed(client_ctx.get(), server_ctx.get(), session.get());
2318 if (!new_session) {
2319 fprintf(stderr, "Error renewing session.\n");
2320 return false;
2321 }
2322
2323 // This new session is not the same object as before.
2324 if (session.get() == new_session.get()) {
2325 fprintf(stderr, "New and old sessions alias.\n");
2326 return false;
2327 }
2328
2329 // Check the sessions have timestamps measured from issuance.
2330 long session_time = 0;
2331 if (server_test) {
2332 if (!GetServerTicketTime(&session_time, new_session.get())) {
2333 fprintf(stderr, "Failed to decode session ticket.\n");
David Benjaminb2e2e322016-11-01 17:32:54 -04002334 return false;
2335 }
David Benjamin0fef3052016-11-18 15:11:10 +09002336 } else {
2337 session_time = new_session->time;
2338 }
David Benjamin721e8b72016-08-03 13:13:17 -04002339
David Benjamin0fef3052016-11-18 15:11:10 +09002340 if (session_time != g_current_time.tv_sec) {
2341 fprintf(stderr, "New session is not measured from issuance.\n");
2342 return false;
2343 }
David Benjamin721e8b72016-08-03 13:13:17 -04002344
David Benjamin0fef3052016-11-18 15:11:10 +09002345 // The new session is usable just before the old expiration.
2346 g_current_time.tv_sec = kStartTime + SSL_DEFAULT_SESSION_TIMEOUT - 1;
2347 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(),
2348 new_session.get(),
2349 true /* expect session reused */)) {
2350 fprintf(stderr, "Error resuming renewed session.\n");
2351 return false;
2352 }
David Benjamin721e8b72016-08-03 13:13:17 -04002353
David Benjamin0fef3052016-11-18 15:11:10 +09002354 // Renewal does not extend the lifetime, so it is not usable beyond the
2355 // old expiration.
2356 g_current_time.tv_sec = kStartTime + SSL_DEFAULT_SESSION_TIMEOUT + 1;
2357 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(),
2358 new_session.get(),
2359 false /* expect session not reused */)) {
2360 fprintf(stderr, "Renewed session's lifetime is too long.\n");
2361 return false;
David Benjamin1b22f852016-10-27 16:36:32 -04002362 }
David Benjamin721e8b72016-08-03 13:13:17 -04002363 }
2364
2365 return true;
2366}
2367
Alessandro Ghedinibf483642016-11-22 18:56:46 +00002368static int SetSessionTimeoutCallback(SSL *ssl, void *arg) {
2369 long timeout = *(long *) arg;
2370 SSL_set_session_timeout(ssl, timeout);
2371 return 1;
2372}
2373
2374static bool TestSessionTimeoutCertCallback(bool is_dtls,
2375 const SSL_METHOD *method,
2376 uint16_t version) {
2377 static const int kStartTime = 1000;
2378 g_current_time.tv_sec = kStartTime;
2379
2380 bssl::UniquePtr<X509> cert = GetTestCertificate();
2381 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
2382 if (!cert || !key) {
2383 return false;
2384 }
2385
2386 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(method));
2387 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(method));
2388 if (!server_ctx || !client_ctx ||
2389 !SSL_CTX_use_certificate(server_ctx.get(), cert.get()) ||
2390 !SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()) ||
2391 !SSL_CTX_set_min_proto_version(client_ctx.get(), version) ||
2392 !SSL_CTX_set_max_proto_version(client_ctx.get(), version) ||
2393 !SSL_CTX_set_min_proto_version(server_ctx.get(), version) ||
2394 !SSL_CTX_set_max_proto_version(server_ctx.get(), version)) {
2395 return false;
2396 }
2397
2398 SSL_CTX_set_session_cache_mode(client_ctx.get(), SSL_SESS_CACHE_BOTH);
2399 SSL_CTX_set_session_cache_mode(server_ctx.get(), SSL_SESS_CACHE_BOTH);
2400
2401 SSL_CTX_set_current_time_cb(server_ctx.get(), CurrentTimeCallback);
2402
2403 long timeout = 25;
2404 SSL_CTX_set_cert_cb(server_ctx.get(), SetSessionTimeoutCallback, &timeout);
2405
2406 bssl::UniquePtr<SSL_SESSION> session =
2407 CreateClientSession(client_ctx.get(), server_ctx.get());
2408 if (!session) {
2409 fprintf(stderr, "Error getting session.\n");
2410 return false;
2411 }
2412
2413 // Advance the clock just behind the timeout.
2414 g_current_time.tv_sec += timeout - 1;
2415
2416 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(), session.get(),
2417 true /* expect session reused */)) {
2418 fprintf(stderr, "Error resuming session.\n");
2419 return false;
2420 }
2421
2422 // Advance the clock one more second.
2423 g_current_time.tv_sec++;
2424
2425 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(), session.get(),
2426 false /* expect session not reused */)) {
2427 fprintf(stderr, "Error resuming session.\n");
2428 return false;
2429 }
2430
2431 // Set session timeout to 0 to disable resumption.
2432 timeout = 0;
2433 g_current_time.tv_sec = kStartTime;
2434
2435 bssl::UniquePtr<SSL_SESSION> not_resumable_session =
2436 CreateClientSession(client_ctx.get(), server_ctx.get());
2437 if (!not_resumable_session) {
2438 fprintf(stderr, "Error getting session.\n");
2439 return false;
2440 }
2441
2442 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(),
2443 not_resumable_session.get(),
2444 false /* expect session not reused */)) {
2445 fprintf(stderr, "Error resuming session with timeout of 0.\n");
2446 return false;
2447 }
2448
2449 // Set both context and connection (via callback) default session timeout.
2450 // The connection one is the one that ends up being used.
2451 timeout = 25;
2452 g_current_time.tv_sec = kStartTime;
2453
2454 SSL_CTX_set_timeout(server_ctx.get(), timeout - 10);
2455
2456 bssl::UniquePtr<SSL_SESSION> ctx_and_cb_session =
2457 CreateClientSession(client_ctx.get(), server_ctx.get());
2458 if (!ctx_and_cb_session) {
2459 fprintf(stderr, "Error getting session.\n");
2460 return false;
2461 }
2462
2463 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(),
2464 ctx_and_cb_session.get(),
2465 true /* expect session reused */)) {
2466 fprintf(stderr, "Error resuming session with timeout of 0.\n");
2467 return false;
2468 }
2469
2470 // Advance the clock just behind the timeout.
2471 g_current_time.tv_sec += timeout - 1;
2472
2473 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(),
2474 ctx_and_cb_session.get(),
2475 true /* expect session reused */)) {
2476 fprintf(stderr, "Error resuming session.\n");
2477 return false;
2478 }
2479
2480 // Advance the clock one more second.
2481 g_current_time.tv_sec++;
2482
2483 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(),
2484 ctx_and_cb_session.get(),
2485 false /* expect session not reused */)) {
2486 fprintf(stderr, "Error resuming session.\n");
2487 return false;
2488 }
2489
2490 return true;
2491}
2492
David Benjamin0fc37ef2016-08-17 15:29:46 -04002493static int SwitchContext(SSL *ssl, int *out_alert, void *arg) {
2494 SSL_CTX *ctx = reinterpret_cast<SSL_CTX*>(arg);
2495 SSL_set_SSL_CTX(ssl, ctx);
2496 return SSL_TLSEXT_ERR_OK;
2497}
2498
David Benjamin0fef3052016-11-18 15:11:10 +09002499static bool TestSNICallback(bool is_dtls, const SSL_METHOD *method,
2500 uint16_t version) {
2501 // SSL 3.0 lacks extensions.
2502 if (version == SSL3_VERSION) {
2503 return true;
2504 }
2505
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002506 bssl::UniquePtr<X509> cert = GetTestCertificate();
2507 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
2508 bssl::UniquePtr<X509> cert2 = GetECDSATestCertificate();
2509 bssl::UniquePtr<EVP_PKEY> key2 = GetECDSATestKey();
David Benjamin0fc37ef2016-08-17 15:29:46 -04002510 if (!cert || !key || !cert2 || !key2) {
2511 return false;
2512 }
2513
David Benjamin0fef3052016-11-18 15:11:10 +09002514 // Test that switching the |SSL_CTX| at the SNI callback behaves correctly.
2515 static const uint16_t kECDSAWithSHA256 = SSL_SIGN_ECDSA_SECP256R1_SHA256;
David Benjamin0fc37ef2016-08-17 15:29:46 -04002516
David Benjamin0fef3052016-11-18 15:11:10 +09002517 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(method));
2518 bssl::UniquePtr<SSL_CTX> server_ctx2(SSL_CTX_new(method));
2519 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(method));
2520 if (!server_ctx || !server_ctx2 || !client_ctx ||
2521 !SSL_CTX_use_certificate(server_ctx.get(), cert.get()) ||
2522 !SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()) ||
2523 !SSL_CTX_use_certificate(server_ctx2.get(), cert2.get()) ||
2524 !SSL_CTX_use_PrivateKey(server_ctx2.get(), key2.get()) ||
2525 // Historically signing preferences would be lost in some cases with the
2526 // SNI callback, which triggers the TLS 1.2 SHA-1 default. To ensure
2527 // this doesn't happen when |version| is TLS 1.2, configure the private
2528 // key to only sign SHA-256.
2529 !SSL_CTX_set_signing_algorithm_prefs(server_ctx2.get(), &kECDSAWithSHA256,
2530 1) ||
2531 !SSL_CTX_set_min_proto_version(client_ctx.get(), version) ||
2532 !SSL_CTX_set_max_proto_version(client_ctx.get(), version) ||
2533 !SSL_CTX_set_min_proto_version(server_ctx.get(), version) ||
2534 !SSL_CTX_set_max_proto_version(server_ctx.get(), version) ||
2535 !SSL_CTX_set_min_proto_version(server_ctx2.get(), version) ||
2536 !SSL_CTX_set_max_proto_version(server_ctx2.get(), version)) {
2537 return false;
2538 }
David Benjamin0fc37ef2016-08-17 15:29:46 -04002539
David Benjamin0fef3052016-11-18 15:11:10 +09002540 SSL_CTX_set_tlsext_servername_callback(server_ctx.get(), SwitchContext);
2541 SSL_CTX_set_tlsext_servername_arg(server_ctx.get(), server_ctx2.get());
David Benjamin0fc37ef2016-08-17 15:29:46 -04002542
David Benjamin0fef3052016-11-18 15:11:10 +09002543 bssl::UniquePtr<SSL> client, server;
2544 if (!ConnectClientAndServer(&client, &server, client_ctx.get(),
2545 server_ctx.get(), nullptr)) {
2546 fprintf(stderr, "Handshake failed.\n");
2547 return false;
2548 }
David Benjamin0fc37ef2016-08-17 15:29:46 -04002549
David Benjamin0fef3052016-11-18 15:11:10 +09002550 // The client should have received |cert2|.
2551 bssl::UniquePtr<X509> peer(SSL_get_peer_certificate(client.get()));
2552 if (!peer || X509_cmp(peer.get(), cert2.get()) != 0) {
2553 fprintf(stderr, "Incorrect certificate received.\n");
2554 return false;
David Benjamin0fc37ef2016-08-17 15:29:46 -04002555 }
2556
2557 return true;
2558}
2559
David Benjamin731058e2016-12-03 23:15:13 -05002560static int SetMaxVersion(const SSL_CLIENT_HELLO *client_hello) {
2561 if (!SSL_set_max_proto_version(client_hello->ssl, TLS1_2_VERSION)) {
David Benjamin2dc02042016-09-19 19:57:37 -04002562 return -1;
2563 }
2564
David Benjamin99620572016-08-30 00:35:36 -04002565 return 1;
2566}
2567
2568// TestEarlyCallbackVersionSwitch tests that the early callback can swap the
2569// maximum version.
2570static bool TestEarlyCallbackVersionSwitch() {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002571 bssl::UniquePtr<X509> cert = GetTestCertificate();
2572 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
2573 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(TLS_method()));
2574 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLS_method()));
David Benjamin99620572016-08-30 00:35:36 -04002575 if (!cert || !key || !server_ctx || !client_ctx ||
2576 !SSL_CTX_use_certificate(server_ctx.get(), cert.get()) ||
David Benjamin2dc02042016-09-19 19:57:37 -04002577 !SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()) ||
David Benjamine4706902016-09-20 15:12:23 -04002578 !SSL_CTX_set_max_proto_version(client_ctx.get(), TLS1_3_VERSION) ||
2579 !SSL_CTX_set_max_proto_version(server_ctx.get(), TLS1_3_VERSION)) {
David Benjamin99620572016-08-30 00:35:36 -04002580 return false;
2581 }
2582
David Benjamin99620572016-08-30 00:35:36 -04002583 SSL_CTX_set_select_certificate_cb(server_ctx.get(), SetMaxVersion);
2584
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002585 bssl::UniquePtr<SSL> client, server;
David Benjamin99620572016-08-30 00:35:36 -04002586 if (!ConnectClientAndServer(&client, &server, client_ctx.get(),
2587 server_ctx.get(), nullptr)) {
2588 return false;
2589 }
2590
2591 if (SSL_version(client.get()) != TLS1_2_VERSION) {
2592 fprintf(stderr, "Early callback failed to switch the maximum version.\n");
2593 return false;
2594 }
2595
2596 return true;
2597}
2598
David Benjamin2dc02042016-09-19 19:57:37 -04002599static bool TestSetVersion() {
2600 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
2601 if (!ctx) {
2602 return false;
2603 }
2604
David Benjamine4706902016-09-20 15:12:23 -04002605 if (!SSL_CTX_set_max_proto_version(ctx.get(), TLS1_VERSION) ||
2606 !SSL_CTX_set_max_proto_version(ctx.get(), TLS1_1_VERSION) ||
2607 !SSL_CTX_set_min_proto_version(ctx.get(), TLS1_VERSION) ||
2608 !SSL_CTX_set_min_proto_version(ctx.get(), TLS1_1_VERSION)) {
David Benjamin2dc02042016-09-19 19:57:37 -04002609 fprintf(stderr, "Could not set valid TLS version.\n");
2610 return false;
2611 }
2612
David Benjamine4706902016-09-20 15:12:23 -04002613 if (SSL_CTX_set_max_proto_version(ctx.get(), DTLS1_VERSION) ||
2614 SSL_CTX_set_max_proto_version(ctx.get(), 0x0200) ||
2615 SSL_CTX_set_max_proto_version(ctx.get(), 0x1234) ||
2616 SSL_CTX_set_min_proto_version(ctx.get(), DTLS1_VERSION) ||
2617 SSL_CTX_set_min_proto_version(ctx.get(), 0x0200) ||
2618 SSL_CTX_set_min_proto_version(ctx.get(), 0x1234)) {
David Benjamin2dc02042016-09-19 19:57:37 -04002619 fprintf(stderr, "Unexpectedly set invalid TLS version.\n");
2620 return false;
2621 }
2622
David Benjamine34bcc92016-09-21 16:53:09 -04002623 if (!SSL_CTX_set_max_proto_version(ctx.get(), 0) ||
2624 !SSL_CTX_set_min_proto_version(ctx.get(), 0)) {
2625 fprintf(stderr, "Could not set default TLS version.\n");
2626 return false;
2627 }
2628
2629 if (ctx->min_version != SSL3_VERSION ||
2630 ctx->max_version != TLS1_2_VERSION) {
2631 fprintf(stderr, "Default TLS versions were incorrect (%04x and %04x).\n",
2632 ctx->min_version, ctx->max_version);
2633 return false;
2634 }
2635
David Benjamin2dc02042016-09-19 19:57:37 -04002636 ctx.reset(SSL_CTX_new(DTLS_method()));
2637 if (!ctx) {
2638 return false;
2639 }
2640
David Benjamine4706902016-09-20 15:12:23 -04002641 if (!SSL_CTX_set_max_proto_version(ctx.get(), DTLS1_VERSION) ||
2642 !SSL_CTX_set_max_proto_version(ctx.get(), DTLS1_2_VERSION) ||
2643 !SSL_CTX_set_min_proto_version(ctx.get(), DTLS1_VERSION) ||
2644 !SSL_CTX_set_min_proto_version(ctx.get(), DTLS1_2_VERSION)) {
David Benjamin2dc02042016-09-19 19:57:37 -04002645 fprintf(stderr, "Could not set valid DTLS version.\n");
2646 return false;
2647 }
2648
David Benjamine4706902016-09-20 15:12:23 -04002649 if (SSL_CTX_set_max_proto_version(ctx.get(), TLS1_VERSION) ||
2650 SSL_CTX_set_max_proto_version(ctx.get(), 0xfefe /* DTLS 1.1 */) ||
2651 SSL_CTX_set_max_proto_version(ctx.get(), 0xfffe /* DTLS 0.1 */) ||
2652 SSL_CTX_set_max_proto_version(ctx.get(), 0x1234) ||
2653 SSL_CTX_set_min_proto_version(ctx.get(), TLS1_VERSION) ||
2654 SSL_CTX_set_min_proto_version(ctx.get(), 0xfefe /* DTLS 1.1 */) ||
2655 SSL_CTX_set_min_proto_version(ctx.get(), 0xfffe /* DTLS 0.1 */) ||
2656 SSL_CTX_set_min_proto_version(ctx.get(), 0x1234)) {
David Benjamin2dc02042016-09-19 19:57:37 -04002657 fprintf(stderr, "Unexpectedly set invalid DTLS version.\n");
2658 return false;
2659 }
2660
David Benjamine34bcc92016-09-21 16:53:09 -04002661 if (!SSL_CTX_set_max_proto_version(ctx.get(), 0) ||
2662 !SSL_CTX_set_min_proto_version(ctx.get(), 0)) {
2663 fprintf(stderr, "Could not set default DTLS version.\n");
2664 return false;
2665 }
2666
2667 if (ctx->min_version != TLS1_1_VERSION ||
2668 ctx->max_version != TLS1_2_VERSION) {
2669 fprintf(stderr, "Default DTLS versions were incorrect (%04x and %04x).\n",
2670 ctx->min_version, ctx->max_version);
2671 return false;
2672 }
2673
David Benjamin2dc02042016-09-19 19:57:37 -04002674 return true;
2675}
2676
David Benjamin458334a2016-12-15 13:53:25 -05002677static const char *GetVersionName(uint16_t version) {
2678 switch (version) {
2679 case SSL3_VERSION:
2680 return "SSLv3";
2681 case TLS1_VERSION:
2682 return "TLSv1";
2683 case TLS1_1_VERSION:
2684 return "TLSv1.1";
2685 case TLS1_2_VERSION:
2686 return "TLSv1.2";
2687 case TLS1_3_VERSION:
2688 return "TLSv1.3";
2689 case DTLS1_VERSION:
2690 return "DTLSv1";
2691 case DTLS1_2_VERSION:
2692 return "DTLSv1.2";
2693 default:
2694 return "???";
2695 }
2696}
2697
David Benjamin0fef3052016-11-18 15:11:10 +09002698static bool TestVersion(bool is_dtls, const SSL_METHOD *method,
2699 uint16_t version) {
David Benjamincb18ac22016-09-27 14:09:15 -04002700 bssl::UniquePtr<X509> cert = GetTestCertificate();
2701 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
2702 if (!cert || !key) {
2703 return false;
2704 }
2705
David Benjamin0fef3052016-11-18 15:11:10 +09002706 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(method));
2707 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(method));
2708 bssl::UniquePtr<SSL> client, server;
2709 if (!server_ctx || !client_ctx ||
2710 !SSL_CTX_use_certificate(server_ctx.get(), cert.get()) ||
2711 !SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()) ||
2712 !SSL_CTX_set_min_proto_version(client_ctx.get(), version) ||
2713 !SSL_CTX_set_max_proto_version(client_ctx.get(), version) ||
2714 !SSL_CTX_set_min_proto_version(server_ctx.get(), version) ||
2715 !SSL_CTX_set_max_proto_version(server_ctx.get(), version) ||
2716 !ConnectClientAndServer(&client, &server, client_ctx.get(),
2717 server_ctx.get(), nullptr /* no session */)) {
2718 fprintf(stderr, "Failed to connect.\n");
2719 return false;
2720 }
David Benjamincb18ac22016-09-27 14:09:15 -04002721
David Benjamin0fef3052016-11-18 15:11:10 +09002722 if (SSL_version(client.get()) != version ||
2723 SSL_version(server.get()) != version) {
2724 fprintf(stderr, "Version mismatch. Got %04x and %04x, wanted %04x.\n",
2725 SSL_version(client.get()), SSL_version(server.get()), version);
2726 return false;
David Benjamincb18ac22016-09-27 14:09:15 -04002727 }
2728
David Benjamin458334a2016-12-15 13:53:25 -05002729 // Test the version name is reported as expected.
2730 const char *version_name = GetVersionName(version);
2731 if (strcmp(version_name, SSL_get_version(client.get())) != 0 ||
2732 strcmp(version_name, SSL_get_version(server.get())) != 0) {
2733 fprintf(stderr, "Version name mismatch. Got '%s' and '%s', wanted '%s'.\n",
2734 SSL_get_version(client.get()), SSL_get_version(server.get()),
2735 version_name);
2736 return false;
2737 }
2738
2739 // Test SSL_SESSION reports the same name.
2740 const char *client_name =
2741 SSL_SESSION_get_version(SSL_get_session(client.get()));
2742 const char *server_name =
2743 SSL_SESSION_get_version(SSL_get_session(server.get()));
2744 if (strcmp(version_name, client_name) != 0 ||
2745 strcmp(version_name, server_name) != 0) {
2746 fprintf(stderr,
2747 "Session version name mismatch. Got '%s' and '%s', wanted '%s'.\n",
2748 client_name, server_name, version_name);
2749 return false;
2750 }
2751
David Benjamincb18ac22016-09-27 14:09:15 -04002752 return true;
2753}
2754
David Benjamin9ef31f02016-10-31 18:01:13 -04002755// Tests that that |SSL_get_pending_cipher| is available during the ALPN
2756// selection callback.
David Benjamin0fef3052016-11-18 15:11:10 +09002757static bool TestALPNCipherAvailable(bool is_dtls, const SSL_METHOD *method,
2758 uint16_t version) {
2759 // SSL 3.0 lacks extensions.
2760 if (version == SSL3_VERSION) {
2761 return true;
2762 }
2763
David Benjamin9ef31f02016-10-31 18:01:13 -04002764 static const uint8_t kALPNProtos[] = {0x03, 'f', 'o', 'o'};
2765
2766 bssl::UniquePtr<X509> cert = GetTestCertificate();
2767 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
2768 if (!cert || !key) {
2769 return false;
2770 }
2771
David Benjamin0fef3052016-11-18 15:11:10 +09002772 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(method));
2773 if (!ctx || !SSL_CTX_use_certificate(ctx.get(), cert.get()) ||
2774 !SSL_CTX_use_PrivateKey(ctx.get(), key.get()) ||
2775 !SSL_CTX_set_min_proto_version(ctx.get(), version) ||
2776 !SSL_CTX_set_max_proto_version(ctx.get(), version) ||
2777 SSL_CTX_set_alpn_protos(ctx.get(), kALPNProtos, sizeof(kALPNProtos)) !=
2778 0) {
2779 return false;
2780 }
2781
2782 // The ALPN callback does not fail the handshake on error, so have the
2783 // callback write a boolean.
2784 std::pair<uint16_t, bool> callback_state(version, false);
2785 SSL_CTX_set_alpn_select_cb(
2786 ctx.get(),
2787 [](SSL *ssl, const uint8_t **out, uint8_t *out_len, const uint8_t *in,
2788 unsigned in_len, void *arg) -> int {
2789 auto state = reinterpret_cast<std::pair<uint16_t, bool> *>(arg);
2790 if (SSL_get_pending_cipher(ssl) != nullptr &&
2791 SSL_version(ssl) == state->first) {
2792 state->second = true;
2793 }
2794 return SSL_TLSEXT_ERR_NOACK;
2795 },
2796 &callback_state);
2797
2798 bssl::UniquePtr<SSL> client, server;
2799 if (!ConnectClientAndServer(&client, &server, ctx.get(), ctx.get(),
2800 nullptr /* no session */)) {
2801 return false;
2802 }
2803
2804 if (!callback_state.second) {
2805 fprintf(stderr, "The pending cipher was not known in the ALPN callback.\n");
2806 return false;
2807 }
2808
2809 return true;
2810}
2811
David Benjaminb79cc842016-12-07 15:57:14 -05002812static bool TestSSLClearSessionResumption(bool is_dtls,
2813 const SSL_METHOD *method,
2814 uint16_t version) {
2815 // Skip this for TLS 1.3. TLS 1.3's ticket mechanism is incompatible with this
2816 // API pattern.
2817 if (version == TLS1_3_VERSION) {
2818 return true;
2819 }
2820
2821 bssl::UniquePtr<X509> cert = GetTestCertificate();
2822 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
2823 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(method));
2824 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(method));
2825 if (!cert || !key || !server_ctx || !client_ctx ||
2826 !SSL_CTX_use_certificate(server_ctx.get(), cert.get()) ||
2827 !SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()) ||
2828 !SSL_CTX_set_min_proto_version(client_ctx.get(), version) ||
2829 !SSL_CTX_set_max_proto_version(client_ctx.get(), version) ||
2830 !SSL_CTX_set_min_proto_version(server_ctx.get(), version) ||
2831 !SSL_CTX_set_max_proto_version(server_ctx.get(), version)) {
2832 return false;
2833 }
2834
2835 // Connect a client and a server.
2836 bssl::UniquePtr<SSL> client, server;
2837 if (!ConnectClientAndServer(&client, &server, client_ctx.get(),
2838 server_ctx.get(), nullptr /* no session */)) {
2839 return false;
2840 }
2841
2842 if (SSL_session_reused(client.get()) ||
2843 SSL_session_reused(server.get())) {
2844 fprintf(stderr, "Session unexpectedly reused.\n");
2845 return false;
2846 }
2847
2848 // Reset everything.
2849 if (!SSL_clear(client.get()) ||
2850 !SSL_clear(server.get())) {
2851 fprintf(stderr, "SSL_clear failed.\n");
2852 return false;
2853 }
2854
2855 // Attempt to connect a second time.
2856 if (!CompleteHandshakes(client.get(), server.get())) {
2857 fprintf(stderr, "Could not reuse SSL objects.\n");
2858 return false;
2859 }
2860
2861 // |SSL_clear| should implicitly offer the previous session to the server.
2862 if (!SSL_session_reused(client.get()) ||
2863 !SSL_session_reused(server.get())) {
2864 fprintf(stderr, "Session was not reused in second try.\n");
2865 return false;
2866 }
2867
2868 return true;
2869}
2870
David Benjamin1444c3a2016-12-20 17:23:11 -05002871static bool ChainsEqual(STACK_OF(X509) *chain,
2872 const std::vector<X509 *> &expected) {
2873 if (sk_X509_num(chain) != expected.size()) {
2874 return false;
2875 }
2876
2877 for (size_t i = 0; i < expected.size(); i++) {
2878 if (X509_cmp(sk_X509_value(chain, i), expected[i]) != 0) {
2879 return false;
2880 }
2881 }
2882
2883 return true;
2884}
2885
2886static bool TestAutoChain(bool is_dtls, const SSL_METHOD *method,
2887 uint16_t version) {
2888 if (version == TLS1_3_VERSION) {
2889 // TODO(davidben): Auto-chaining does not currently work in TLS 1.3.
2890 return true;
2891 }
2892
2893 bssl::UniquePtr<X509> cert = GetChainTestCertificate();
2894 bssl::UniquePtr<X509> intermediate = GetChainTestIntermediate();
2895 bssl::UniquePtr<EVP_PKEY> key = GetChainTestKey();
2896 if (!cert || !intermediate || !key) {
2897 return false;
2898 }
2899
2900 // Configure both client and server to accept any certificate. Add
2901 // |intermediate| to the cert store.
2902 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(method));
2903 if (!ctx ||
2904 !SSL_CTX_use_certificate(ctx.get(), cert.get()) ||
2905 !SSL_CTX_use_PrivateKey(ctx.get(), key.get()) ||
2906 !SSL_CTX_set_min_proto_version(ctx.get(), version) ||
2907 !SSL_CTX_set_max_proto_version(ctx.get(), version) ||
2908 !X509_STORE_add_cert(SSL_CTX_get_cert_store(ctx.get()),
2909 intermediate.get())) {
2910 return false;
2911 }
2912 SSL_CTX_set_verify(
2913 ctx.get(), SSL_VERIFY_PEER | SSL_VERIFY_FAIL_IF_NO_PEER_CERT, nullptr);
2914 SSL_CTX_set_cert_verify_callback(ctx.get(), VerifySucceed, NULL);
2915
2916 // By default, the client and server should each only send the leaf.
2917 bssl::UniquePtr<SSL> client, server;
2918 if (!ConnectClientAndServer(&client, &server, ctx.get(), ctx.get(),
2919 nullptr /* no session */)) {
2920 return false;
2921 }
2922
2923 if (!ChainsEqual(SSL_get_peer_full_cert_chain(client.get()), {cert.get()})) {
2924 fprintf(stderr, "Client-received chain did not match.\n");
2925 return false;
2926 }
2927
2928 if (!ChainsEqual(SSL_get_peer_full_cert_chain(server.get()), {cert.get()})) {
2929 fprintf(stderr, "Server-received chain did not match.\n");
2930 return false;
2931 }
2932
2933 // If auto-chaining is enabled, then the intermediate is sent.
2934 SSL_CTX_clear_mode(ctx.get(), SSL_MODE_NO_AUTO_CHAIN);
2935 if (!ConnectClientAndServer(&client, &server, ctx.get(), ctx.get(),
2936 nullptr /* no session */)) {
2937 return false;
2938 }
2939
2940 if (!ChainsEqual(SSL_get_peer_full_cert_chain(client.get()),
2941 {cert.get(), intermediate.get()})) {
2942 fprintf(stderr, "Client-received chain did not match (auto-chaining).\n");
2943 return false;
2944 }
2945
2946 if (!ChainsEqual(SSL_get_peer_full_cert_chain(server.get()),
2947 {cert.get(), intermediate.get()})) {
2948 fprintf(stderr, "Server-received chain did not match (auto-chaining).\n");
2949 return false;
2950 }
2951
2952 // Auto-chaining does not override explicitly-configured intermediates.
2953 if (!SSL_CTX_add1_chain_cert(ctx.get(), cert.get()) ||
2954 !ConnectClientAndServer(&client, &server, ctx.get(), ctx.get(),
2955 nullptr /* no session */)) {
2956 return false;
2957 }
2958
2959 if (!ChainsEqual(SSL_get_peer_full_cert_chain(client.get()),
2960 {cert.get(), cert.get()})) {
2961 fprintf(stderr,
2962 "Client-received chain did not match (auto-chaining, explicit "
2963 "intermediate).\n");
2964 return false;
2965 }
2966
2967 if (!ChainsEqual(SSL_get_peer_full_cert_chain(server.get()),
2968 {cert.get(), cert.get()})) {
2969 fprintf(stderr,
2970 "Server-received chain did not match (auto-chaining, explicit "
2971 "intermediate).\n");
2972 return false;
2973 }
2974
2975 return true;
2976}
2977
David Benjamin0fef3052016-11-18 15:11:10 +09002978static bool ForEachVersion(bool (*test_func)(bool is_dtls,
2979 const SSL_METHOD *method,
2980 uint16_t version)) {
2981 static uint16_t kTLSVersions[] = {
2982 SSL3_VERSION, TLS1_VERSION, TLS1_1_VERSION,
2983 TLS1_2_VERSION, TLS1_3_VERSION,
2984 };
2985
2986 static uint16_t kDTLSVersions[] = {
2987 DTLS1_VERSION, DTLS1_2_VERSION,
2988 };
2989
David Benjamin9ef31f02016-10-31 18:01:13 -04002990 for (uint16_t version : kTLSVersions) {
David Benjamin0fef3052016-11-18 15:11:10 +09002991 if (!test_func(false, TLS_method(), version)) {
2992 fprintf(stderr, "Test failed at TLS version %04x.\n", version);
David Benjamin9ef31f02016-10-31 18:01:13 -04002993 return false;
2994 }
David Benjamin0fef3052016-11-18 15:11:10 +09002995 }
David Benjamin9ef31f02016-10-31 18:01:13 -04002996
David Benjamin0fef3052016-11-18 15:11:10 +09002997 for (uint16_t version : kDTLSVersions) {
2998 if (!test_func(true, DTLS_method(), version)) {
2999 fprintf(stderr, "Test failed at DTLS version %04x.\n", version);
David Benjamin9ef31f02016-10-31 18:01:13 -04003000 return false;
3001 }
3002 }
3003
3004 return true;
3005}
3006
David Benjamin1d128f32015-09-08 17:41:40 -04003007int main() {
David Benjamin7a1eefd2015-10-17 23:39:22 -04003008 CRYPTO_library_init();
David Benjaminbb0a17c2014-09-20 15:35:39 -04003009
Adam Langley10f97f32016-07-12 08:09:33 -07003010 if (!TestCipherRules() ||
Alessandro Ghedini5fd18072016-09-28 21:04:25 +01003011 !TestCurveRules() ||
Adam Langley10f97f32016-07-12 08:09:33 -07003012 !TestSSL_SESSIONEncoding(kOpenSSLSession) ||
3013 !TestSSL_SESSIONEncoding(kCustomSession) ||
3014 !TestSSL_SESSIONEncoding(kBoringSSLSession) ||
3015 !TestBadSSL_SESSIONEncoding(kBadSessionExtraField) ||
3016 !TestBadSSL_SESSIONEncoding(kBadSessionVersion) ||
3017 !TestBadSSL_SESSIONEncoding(kBadSessionTrailingData) ||
David Benjamin10e664b2016-06-20 22:20:47 -04003018 // TODO(svaldez): Update this when TLS 1.3 is enabled by default.
Adam Langley10f97f32016-07-12 08:09:33 -07003019 !TestDefaultVersion(SSL3_VERSION, TLS1_2_VERSION, &TLS_method) ||
3020 !TestDefaultVersion(SSL3_VERSION, SSL3_VERSION, &SSLv3_method) ||
3021 !TestDefaultVersion(TLS1_VERSION, TLS1_VERSION, &TLSv1_method) ||
3022 !TestDefaultVersion(TLS1_1_VERSION, TLS1_1_VERSION, &TLSv1_1_method) ||
3023 !TestDefaultVersion(TLS1_2_VERSION, TLS1_2_VERSION, &TLSv1_2_method) ||
3024 !TestDefaultVersion(TLS1_1_VERSION, TLS1_2_VERSION, &DTLS_method) ||
3025 !TestDefaultVersion(TLS1_1_VERSION, TLS1_1_VERSION, &DTLSv1_method) ||
3026 !TestDefaultVersion(TLS1_2_VERSION, TLS1_2_VERSION, &DTLSv1_2_method) ||
3027 !TestCipherGetRFCName() ||
Steven Valdeza833c352016-11-01 13:39:36 -04003028 // Test the padding extension at TLS 1.2.
3029 !TestPaddingExtension(TLS1_2_VERSION, TLS1_2_VERSION) ||
3030 // Test the padding extension at TLS 1.3 with a TLS 1.2 session, so there
3031 // will be no PSK binder after the padding extension.
3032 !TestPaddingExtension(TLS1_3_VERSION, TLS1_2_VERSION) ||
3033 // Test the padding extension at TLS 1.3 with a TLS 1.3 session, so there
3034 // will be a PSK binder after the padding extension.
3035 !TestPaddingExtension(TLS1_3_VERSION, TLS1_3_DRAFT_VERSION) ||
Adam Langley10f97f32016-07-12 08:09:33 -07003036 !TestClientCAList() ||
3037 !TestInternalSessionCache() ||
David Benjamin0fef3052016-11-18 15:11:10 +09003038 !ForEachVersion(TestSequenceNumber) ||
David Benjamin68f37b72016-11-18 15:14:42 +09003039 !ForEachVersion(TestOneSidedShutdown) ||
Steven Valdez87eab492016-06-27 16:34:59 -04003040 !TestSessionDuplication() ||
David Benjamin25490f22016-07-14 00:22:54 -04003041 !TestSetFD() ||
David Benjamin4501bd52016-08-01 13:39:41 -04003042 !TestSetBIO() ||
David Benjamin0fef3052016-11-18 15:11:10 +09003043 !ForEachVersion(TestGetPeerCertificate) ||
3044 !ForEachVersion(TestRetainOnlySHA256OfCerts) ||
David Benjamina20e5352016-08-02 19:09:41 -04003045 !TestClientHello() ||
David Benjamin0fef3052016-11-18 15:11:10 +09003046 !ForEachVersion(TestSessionIDContext) ||
3047 !ForEachVersion(TestSessionTimeout) ||
Alessandro Ghedinibf483642016-11-22 18:56:46 +00003048 !ForEachVersion(TestSessionTimeoutCertCallback) ||
David Benjamin0fef3052016-11-18 15:11:10 +09003049 !ForEachVersion(TestSNICallback) ||
David Benjamin2dc02042016-09-19 19:57:37 -04003050 !TestEarlyCallbackVersionSwitch() ||
David Benjamincb18ac22016-09-27 14:09:15 -04003051 !TestSetVersion() ||
David Benjamin0fef3052016-11-18 15:11:10 +09003052 !ForEachVersion(TestVersion) ||
David Benjaminb79cc842016-12-07 15:57:14 -05003053 !ForEachVersion(TestALPNCipherAvailable) ||
David Benjamin1444c3a2016-12-20 17:23:11 -05003054 !ForEachVersion(TestSSLClearSessionResumption) ||
3055 !ForEachVersion(TestAutoChain)) {
Brian Smith83a82982015-04-09 16:21:10 -10003056 ERR_print_errors_fp(stderr);
David Benjaminbb0a17c2014-09-20 15:35:39 -04003057 return 1;
3058 }
3059
David Benjamin2e521212014-07-16 14:37:51 -04003060 printf("PASS\n");
3061 return 0;
3062}