blob: 6b150e8c6071903ed94aff5112dfaa45e89f68c4 [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 Benjamin96628432017-01-19 19:05:47 -050024#include <gtest/gtest.h>
25
David Benjamin751e8892014-10-19 00:59:36 -040026#include <openssl/base64.h>
27#include <openssl/bio.h>
David Benjamin3c51d9b2016-11-01 17:50:42 -040028#include <openssl/cipher.h>
David Benjamin7a1eefd2015-10-17 23:39:22 -040029#include <openssl/crypto.h>
David Benjaminbb0a17c2014-09-20 15:35:39 -040030#include <openssl/err.h>
David Benjamin3c51d9b2016-11-01 17:50:42 -040031#include <openssl/hmac.h>
David Benjaminde942382016-02-11 12:02:01 -050032#include <openssl/pem.h>
David Benjamin25490f22016-07-14 00:22:54 -040033#include <openssl/sha.h>
David Benjaminbb0a17c2014-09-20 15:35:39 -040034#include <openssl/ssl.h>
David Benjamin3c51d9b2016-11-01 17:50:42 -040035#include <openssl/rand.h>
David Benjaminde942382016-02-11 12:02:01 -050036#include <openssl/x509.h>
David Benjaminbb0a17c2014-09-20 15:35:39 -040037
Steven Valdez87eab492016-06-27 16:34:59 -040038#include "internal.h"
Steven Valdezcb966542016-08-17 16:56:14 -040039#include "../crypto/internal.h"
Sigbjorn Vik2b23d242015-06-29 15:07:26 +020040#include "../crypto/test/test_util.h"
41
David Benjamin721e8b72016-08-03 13:13:17 -040042#if defined(OPENSSL_WINDOWS)
43/* Windows defines struct timeval in winsock2.h. */
44OPENSSL_MSVC_PRAGMA(warning(push, 3))
45#include <winsock2.h>
46OPENSSL_MSVC_PRAGMA(warning(pop))
47#else
48#include <sys/time.h>
49#endif
50
David Benjamin1d77e562015-03-22 17:22:08 -040051
52struct ExpectedCipher {
53 unsigned long id;
David Benjaminbb0a17c2014-09-20 15:35:39 -040054 int in_group_flag;
David Benjamin1d77e562015-03-22 17:22:08 -040055};
David Benjaminbb0a17c2014-09-20 15:35:39 -040056
David Benjamin1d77e562015-03-22 17:22:08 -040057struct CipherTest {
58 // The rule string to apply.
David Benjaminbb0a17c2014-09-20 15:35:39 -040059 const char *rule;
David Benjaminfb974e62015-12-16 19:34:22 -050060 // The list of expected ciphers, in order.
61 std::vector<ExpectedCipher> expected;
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -080062 // True if this cipher list should fail in strict mode.
63 bool strict_fail;
David Benjamin1d77e562015-03-22 17:22:08 -040064};
David Benjaminbb0a17c2014-09-20 15:35:39 -040065
Alessandro Ghedini5fd18072016-09-28 21:04:25 +010066struct CurveTest {
67 // The rule string to apply.
68 const char *rule;
69 // The list of expected curves, in order.
70 std::vector<uint16_t> expected;
71};
72
David Benjaminfb974e62015-12-16 19:34:22 -050073static const CipherTest kCipherTests[] = {
74 // Selecting individual ciphers should work.
75 {
76 "ECDHE-ECDSA-CHACHA20-POLY1305:"
77 "ECDHE-RSA-CHACHA20-POLY1305:"
78 "ECDHE-ECDSA-AES128-GCM-SHA256:"
79 "ECDHE-RSA-AES128-GCM-SHA256",
80 {
81 {TLS1_CK_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256, 0},
David Benjaminfb974e62015-12-16 19:34:22 -050082 {TLS1_CK_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256, 0},
David Benjaminfb974e62015-12-16 19:34:22 -050083 {TLS1_CK_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, 0},
84 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 0},
85 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -080086 false,
David Benjaminfb974e62015-12-16 19:34:22 -050087 },
88 // + reorders selected ciphers to the end, keeping their relative order.
89 {
90 "ECDHE-ECDSA-CHACHA20-POLY1305:"
91 "ECDHE-RSA-CHACHA20-POLY1305:"
92 "ECDHE-ECDSA-AES128-GCM-SHA256:"
93 "ECDHE-RSA-AES128-GCM-SHA256:"
94 "+aRSA",
95 {
96 {TLS1_CK_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256, 0},
David Benjaminfb974e62015-12-16 19:34:22 -050097 {TLS1_CK_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, 0},
98 {TLS1_CK_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256, 0},
David Benjaminfb974e62015-12-16 19:34:22 -050099 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 0},
100 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800101 false,
David Benjaminfb974e62015-12-16 19:34:22 -0500102 },
103 // ! banishes ciphers from future selections.
104 {
105 "!aRSA:"
106 "ECDHE-ECDSA-CHACHA20-POLY1305:"
107 "ECDHE-RSA-CHACHA20-POLY1305:"
108 "ECDHE-ECDSA-AES128-GCM-SHA256:"
109 "ECDHE-RSA-AES128-GCM-SHA256",
110 {
111 {TLS1_CK_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256, 0},
David Benjaminfb974e62015-12-16 19:34:22 -0500112 {TLS1_CK_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, 0},
113 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800114 false,
David Benjaminfb974e62015-12-16 19:34:22 -0500115 },
116 // Multiple masks can be ANDed in a single rule.
117 {
118 "kRSA+AESGCM+AES128",
119 {
120 {TLS1_CK_RSA_WITH_AES_128_GCM_SHA256, 0},
121 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800122 false,
David Benjaminfb974e62015-12-16 19:34:22 -0500123 },
124 // - removes selected ciphers, but preserves their order for future
125 // selections. Select AES_128_GCM, but order the key exchanges RSA, DHE_RSA,
126 // ECDHE_RSA.
127 {
128 "ALL:-kECDHE:-kDHE:-kRSA:-ALL:"
129 "AESGCM+AES128+aRSA",
130 {
131 {TLS1_CK_RSA_WITH_AES_128_GCM_SHA256, 0},
132 {TLS1_CK_DHE_RSA_WITH_AES_128_GCM_SHA256, 0},
133 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 0},
134 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800135 false,
David Benjaminfb974e62015-12-16 19:34:22 -0500136 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800137 // Unknown selectors are no-ops, except in strict mode.
David Benjaminfb974e62015-12-16 19:34:22 -0500138 {
139 "ECDHE-ECDSA-CHACHA20-POLY1305:"
140 "ECDHE-RSA-CHACHA20-POLY1305:"
141 "ECDHE-ECDSA-AES128-GCM-SHA256:"
142 "ECDHE-RSA-AES128-GCM-SHA256:"
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800143 "BOGUS1",
David Benjaminfb974e62015-12-16 19:34:22 -0500144 {
145 {TLS1_CK_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256, 0},
David Benjaminfb974e62015-12-16 19:34:22 -0500146 {TLS1_CK_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256, 0},
David Benjaminfb974e62015-12-16 19:34:22 -0500147 {TLS1_CK_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, 0},
148 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 0},
149 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800150 true,
151 },
152 // Unknown selectors are no-ops, except in strict mode.
153 {
154 "ECDHE-ECDSA-CHACHA20-POLY1305:"
155 "ECDHE-RSA-CHACHA20-POLY1305:"
156 "ECDHE-ECDSA-AES128-GCM-SHA256:"
157 "ECDHE-RSA-AES128-GCM-SHA256:"
158 "-BOGUS2:+BOGUS3:!BOGUS4",
159 {
160 {TLS1_CK_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256, 0},
161 {TLS1_CK_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256, 0},
162 {TLS1_CK_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, 0},
163 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 0},
164 },
165 true,
David Benjaminfb974e62015-12-16 19:34:22 -0500166 },
167 // Square brackets specify equi-preference groups.
168 {
169 "[ECDHE-ECDSA-CHACHA20-POLY1305|ECDHE-ECDSA-AES128-GCM-SHA256]:"
170 "[ECDHE-RSA-CHACHA20-POLY1305]:"
171 "ECDHE-RSA-AES128-GCM-SHA256",
172 {
173 {TLS1_CK_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256, 1},
David Benjaminfb974e62015-12-16 19:34:22 -0500174 {TLS1_CK_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, 0},
Adam Langley2e839242017-01-19 15:12:44 -0800175 {TLS1_CK_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256, 0},
David Benjaminfb974e62015-12-16 19:34:22 -0500176 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 0},
177 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800178 false,
David Benjaminfb974e62015-12-16 19:34:22 -0500179 },
180 // @STRENGTH performs a stable strength-sort of the selected ciphers and
181 // only the selected ciphers.
182 {
183 // To simplify things, banish all but {ECDHE_RSA,RSA} x
Matthew Braithwaite8aaa9e12016-09-07 15:09:58 -0700184 // {CHACHA20,AES_256_CBC,AES_128_CBC} x SHA1.
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800185 "!kEDH:!AESGCM:!3DES:!SHA256:!SHA384:"
David Benjaminfb974e62015-12-16 19:34:22 -0500186 // Order some ciphers backwards by strength.
Matthew Braithwaite8aaa9e12016-09-07 15:09:58 -0700187 "ALL:-CHACHA20:-AES256:-AES128:-ALL:"
David Benjaminfb974e62015-12-16 19:34:22 -0500188 // Select ECDHE ones and sort them by strength. Ties should resolve
189 // based on the order above.
190 "kECDHE:@STRENGTH:-ALL:"
191 // Now bring back everything uses RSA. ECDHE_RSA should be first, sorted
192 // by strength. Then RSA, backwards by strength.
193 "aRSA",
194 {
195 {TLS1_CK_ECDHE_RSA_WITH_AES_256_CBC_SHA, 0},
196 {TLS1_CK_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256, 0},
David Benjaminfb974e62015-12-16 19:34:22 -0500197 {TLS1_CK_ECDHE_RSA_WITH_AES_128_CBC_SHA, 0},
David Benjaminfb974e62015-12-16 19:34:22 -0500198 {TLS1_CK_RSA_WITH_AES_128_SHA, 0},
199 {TLS1_CK_RSA_WITH_AES_256_SHA, 0},
200 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800201 false,
David Benjaminfb974e62015-12-16 19:34:22 -0500202 },
203 // Exact ciphers may not be used in multi-part rules; they are treated
204 // as unknown aliases.
205 {
206 "ECDHE-ECDSA-AES128-GCM-SHA256:"
207 "ECDHE-RSA-AES128-GCM-SHA256:"
208 "!ECDHE-RSA-AES128-GCM-SHA256+RSA:"
209 "!ECDSA+ECDHE-ECDSA-AES128-GCM-SHA256",
210 {
211 {TLS1_CK_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, 0},
212 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 0},
213 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800214 true,
David Benjaminfb974e62015-12-16 19:34:22 -0500215 },
216 // SSLv3 matches everything that existed before TLS 1.2.
217 {
218 "AES128-SHA:AES128-SHA256:!SSLv3",
219 {
220 {TLS1_CK_RSA_WITH_AES_128_SHA256, 0},
221 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800222 false,
David Benjaminfb974e62015-12-16 19:34:22 -0500223 },
224 // TLSv1.2 matches everything added in TLS 1.2.
225 {
226 "AES128-SHA:AES128-SHA256:!TLSv1.2",
227 {
228 {TLS1_CK_RSA_WITH_AES_128_SHA, 0},
229 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800230 false,
David Benjaminfb974e62015-12-16 19:34:22 -0500231 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800232 // The two directives have no intersection. But each component is valid, so
233 // even in strict mode it is accepted.
David Benjaminfb974e62015-12-16 19:34:22 -0500234 {
235 "AES128-SHA:AES128-SHA256:!TLSv1.2+SSLv3",
236 {
237 {TLS1_CK_RSA_WITH_AES_128_SHA, 0},
238 {TLS1_CK_RSA_WITH_AES_128_SHA256, 0},
239 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800240 false,
David Benjaminfb974e62015-12-16 19:34:22 -0500241 },
David Benjaminbb0a17c2014-09-20 15:35:39 -0400242};
243
244static const char *kBadRules[] = {
David Benjamin1d77e562015-03-22 17:22:08 -0400245 // Invalid brackets.
David Benjaminbb0a17c2014-09-20 15:35:39 -0400246 "[ECDHE-RSA-CHACHA20-POLY1305|ECDHE-RSA-AES128-GCM-SHA256",
247 "RSA]",
248 "[[RSA]]",
David Benjamin1d77e562015-03-22 17:22:08 -0400249 // Operators inside brackets.
David Benjaminbb0a17c2014-09-20 15:35:39 -0400250 "[+RSA]",
David Benjamin1d77e562015-03-22 17:22:08 -0400251 // Unknown directive.
David Benjaminbb0a17c2014-09-20 15:35:39 -0400252 "@BOGUS",
David Benjamin1d77e562015-03-22 17:22:08 -0400253 // Empty cipher lists error at SSL_CTX_set_cipher_list.
David Benjaminbb0a17c2014-09-20 15:35:39 -0400254 "",
255 "BOGUS",
David Benjamin32fbdf22015-04-07 01:14:06 -0400256 // COMPLEMENTOFDEFAULT is empty.
257 "COMPLEMENTOFDEFAULT",
David Benjamin1d77e562015-03-22 17:22:08 -0400258 // Invalid command.
David Benjaminbb0a17c2014-09-20 15:35:39 -0400259 "?BAR",
David Benjamin1d77e562015-03-22 17:22:08 -0400260 // Special operators are not allowed if groups are used.
David Benjamin37d92462014-09-20 17:54:24 -0400261 "[ECDHE-RSA-CHACHA20-POLY1305|ECDHE-RSA-AES128-GCM-SHA256]:+FOO",
262 "[ECDHE-RSA-CHACHA20-POLY1305|ECDHE-RSA-AES128-GCM-SHA256]:!FOO",
263 "[ECDHE-RSA-CHACHA20-POLY1305|ECDHE-RSA-AES128-GCM-SHA256]:-FOO",
264 "[ECDHE-RSA-CHACHA20-POLY1305|ECDHE-RSA-AES128-GCM-SHA256]:@STRENGTH",
Adam Langleyf99f2442016-10-02 09:53:38 -0700265 // Opcode supplied, but missing selector.
266 "+",
David Benjaminbb0a17c2014-09-20 15:35:39 -0400267};
268
Matt Braithwaiteaf096752015-09-02 19:48:16 -0700269static const char *kMustNotIncludeNull[] = {
270 "ALL",
271 "DEFAULT",
David Benjamind6e9eec2015-11-18 09:48:55 -0500272 "HIGH",
Matt Braithwaiteaf096752015-09-02 19:48:16 -0700273 "FIPS",
274 "SHA",
275 "SHA1",
276 "RSA",
277 "SSLv3",
278 "TLSv1",
279 "TLSv1.2",
Matt Braithwaiteaf096752015-09-02 19:48:16 -0700280};
281
Alessandro Ghedini5fd18072016-09-28 21:04:25 +0100282static const CurveTest kCurveTests[] = {
283 {
284 "P-256",
285 { SSL_CURVE_SECP256R1 },
286 },
287 {
288 "P-256:P-384:P-521:X25519",
289 {
290 SSL_CURVE_SECP256R1,
291 SSL_CURVE_SECP384R1,
292 SSL_CURVE_SECP521R1,
293 SSL_CURVE_X25519,
294 },
295 },
296};
297
298static const char *kBadCurvesLists[] = {
299 "",
300 ":",
301 "::",
302 "P-256::X25519",
303 "RSA:P-256",
304 "P-256:RSA",
305 "X25519:P-256:",
306 ":X25519:P-256",
307};
308
David Benjamin1d77e562015-03-22 17:22:08 -0400309static void PrintCipherPreferenceList(ssl_cipher_preference_list_st *list) {
310 bool in_group = false;
311 for (size_t i = 0; i < sk_SSL_CIPHER_num(list->ciphers); i++) {
David Benjaminbb0a17c2014-09-20 15:35:39 -0400312 const SSL_CIPHER *cipher = sk_SSL_CIPHER_value(list->ciphers, i);
313 if (!in_group && list->in_group_flags[i]) {
314 fprintf(stderr, "\t[\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400315 in_group = true;
David Benjaminbb0a17c2014-09-20 15:35:39 -0400316 }
317 fprintf(stderr, "\t");
318 if (in_group) {
319 fprintf(stderr, " ");
320 }
321 fprintf(stderr, "%s\n", SSL_CIPHER_get_name(cipher));
322 if (in_group && !list->in_group_flags[i]) {
323 fprintf(stderr, "\t]\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400324 in_group = false;
David Benjaminbb0a17c2014-09-20 15:35:39 -0400325 }
326 }
327}
328
David Benjaminfb974e62015-12-16 19:34:22 -0500329static bool TestCipherRule(const CipherTest &t) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700330 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
David Benjamin1d77e562015-03-22 17:22:08 -0400331 if (!ctx) {
332 return false;
David Benjamin65226252015-02-05 16:49:47 -0500333 }
334
David Benjaminfb974e62015-12-16 19:34:22 -0500335 if (!SSL_CTX_set_cipher_list(ctx.get(), t.rule)) {
336 fprintf(stderr, "Error testing cipher rule '%s'\n", t.rule);
David Benjamin1d77e562015-03-22 17:22:08 -0400337 return false;
David Benjaminbb0a17c2014-09-20 15:35:39 -0400338 }
339
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800340 if (!SSL_CTX_set_strict_cipher_list(ctx.get(), t.rule) != t.strict_fail) {
341 fprintf(stderr, "Unexpected strict failure result testing cipher rule '%s':"
342 " expected %d\n", t.rule, t.strict_fail);
343 return false;
344 }
345
David Benjamin1d77e562015-03-22 17:22:08 -0400346 // Compare the two lists.
David Benjaminfb974e62015-12-16 19:34:22 -0500347 if (sk_SSL_CIPHER_num(ctx->cipher_list->ciphers) != t.expected.size()) {
348 fprintf(stderr, "Error: cipher rule '%s' evaluated to:\n", t.rule);
349 PrintCipherPreferenceList(ctx->cipher_list);
350 return false;
351 }
352
353 for (size_t i = 0; i < t.expected.size(); i++) {
David Benjaminbb0a17c2014-09-20 15:35:39 -0400354 const SSL_CIPHER *cipher =
355 sk_SSL_CIPHER_value(ctx->cipher_list->ciphers, i);
David Benjaminfb974e62015-12-16 19:34:22 -0500356 if (t.expected[i].id != SSL_CIPHER_get_id(cipher) ||
357 t.expected[i].in_group_flag != ctx->cipher_list->in_group_flags[i]) {
358 fprintf(stderr, "Error: cipher rule '%s' evaluated to:\n", t.rule);
David Benjamin1d77e562015-03-22 17:22:08 -0400359 PrintCipherPreferenceList(ctx->cipher_list);
360 return false;
David Benjaminbb0a17c2014-09-20 15:35:39 -0400361 }
362 }
363
David Benjamin1d77e562015-03-22 17:22:08 -0400364 return true;
David Benjaminbb0a17c2014-09-20 15:35:39 -0400365}
366
Matt Braithwaiteaf096752015-09-02 19:48:16 -0700367static bool TestRuleDoesNotIncludeNull(const char *rule) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700368 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(SSLv23_server_method()));
Matt Braithwaiteaf096752015-09-02 19:48:16 -0700369 if (!ctx) {
370 return false;
371 }
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800372 if (!SSL_CTX_set_strict_cipher_list(ctx.get(), rule)) {
Matt Braithwaiteaf096752015-09-02 19:48:16 -0700373 fprintf(stderr, "Error: cipher rule '%s' failed\n", rule);
374 return false;
375 }
376 for (size_t i = 0; i < sk_SSL_CIPHER_num(ctx->cipher_list->ciphers); i++) {
377 if (SSL_CIPHER_is_NULL(sk_SSL_CIPHER_value(ctx->cipher_list->ciphers, i))) {
378 fprintf(stderr, "Error: cipher rule '%s' includes NULL\n",rule);
379 return false;
380 }
381 }
382 return true;
383}
384
David Benjamin1d77e562015-03-22 17:22:08 -0400385static bool TestCipherRules() {
David Benjaminfb974e62015-12-16 19:34:22 -0500386 for (const CipherTest &test : kCipherTests) {
387 if (!TestCipherRule(test)) {
David Benjamin1d77e562015-03-22 17:22:08 -0400388 return false;
David Benjaminbb0a17c2014-09-20 15:35:39 -0400389 }
390 }
391
David Benjaminfb974e62015-12-16 19:34:22 -0500392 for (const char *rule : kBadRules) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700393 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(SSLv23_server_method()));
David Benjamin1d77e562015-03-22 17:22:08 -0400394 if (!ctx) {
395 return false;
David Benjamin65226252015-02-05 16:49:47 -0500396 }
David Benjaminfb974e62015-12-16 19:34:22 -0500397 if (SSL_CTX_set_cipher_list(ctx.get(), rule)) {
398 fprintf(stderr, "Cipher rule '%s' unexpectedly succeeded\n", rule);
David Benjamin1d77e562015-03-22 17:22:08 -0400399 return false;
David Benjaminbb0a17c2014-09-20 15:35:39 -0400400 }
401 ERR_clear_error();
David Benjaminbb0a17c2014-09-20 15:35:39 -0400402 }
403
David Benjaminfb974e62015-12-16 19:34:22 -0500404 for (const char *rule : kMustNotIncludeNull) {
405 if (!TestRuleDoesNotIncludeNull(rule)) {
Matt Braithwaiteaf096752015-09-02 19:48:16 -0700406 return false;
407 }
408 }
409
David Benjamin1d77e562015-03-22 17:22:08 -0400410 return true;
David Benjaminbb0a17c2014-09-20 15:35:39 -0400411}
David Benjamin2e521212014-07-16 14:37:51 -0400412
Alessandro Ghedini5fd18072016-09-28 21:04:25 +0100413static bool TestCurveRule(const CurveTest &t) {
414 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
415 if (!ctx) {
416 return false;
417 }
418
419 if (!SSL_CTX_set1_curves_list(ctx.get(), t.rule)) {
420 fprintf(stderr, "Error testing curves list '%s'\n", t.rule);
421 return false;
422 }
423
424 // Compare the two lists.
425 if (ctx->supported_group_list_len != t.expected.size()) {
426 fprintf(stderr, "Error testing curves list '%s': length\n", t.rule);
427 return false;
428 }
429
430 for (size_t i = 0; i < t.expected.size(); i++) {
431 if (t.expected[i] != ctx->supported_group_list[i]) {
432 fprintf(stderr, "Error testing curves list '%s': mismatch\n", t.rule);
433 return false;
434 }
435 }
436
437 return true;
438}
439
440static bool TestCurveRules() {
441 for (const CurveTest &test : kCurveTests) {
442 if (!TestCurveRule(test)) {
443 return false;
444 }
445 }
446
447 for (const char *rule : kBadCurvesLists) {
448 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(SSLv23_server_method()));
449 if (!ctx) {
450 return false;
451 }
452 if (SSL_CTX_set1_curves_list(ctx.get(), rule)) {
453 fprintf(stderr, "Curves list '%s' unexpectedly succeeded\n", rule);
454 return false;
455 }
456 ERR_clear_error();
457 }
458
459 return true;
460}
461
Adam Langley364f7a62016-12-12 10:51:00 -0800462// kOpenSSLSession is a serialized SSL_SESSION.
Adam Langley10f97f32016-07-12 08:09:33 -0700463static const char kOpenSSLSession[] =
Adam Langley364f7a62016-12-12 10:51:00 -0800464 "MIIFqgIBAQICAwMEAsAvBCAG5Q1ndq4Yfmbeo1zwLkNRKmCXGdNgWvGT3cskV0yQ"
Adam Langley10f97f32016-07-12 08:09:33 -0700465 "kAQwJlrlzkAWBOWiLj/jJ76D7l+UXoizP2KI2C7I2FccqMmIfFmmkUy32nIJ0mZH"
466 "IWoJoQYCBFRDO46iBAICASyjggR6MIIEdjCCA16gAwIBAgIIK9dUvsPWSlUwDQYJ"
467 "KoZIhvcNAQEFBQAwSTELMAkGA1UEBhMCVVMxEzARBgNVBAoTCkdvb2dsZSBJbmMx"
468 "JTAjBgNVBAMTHEdvb2dsZSBJbnRlcm5ldCBBdXRob3JpdHkgRzIwHhcNMTQxMDA4"
469 "MTIwNzU3WhcNMTUwMTA2MDAwMDAwWjBoMQswCQYDVQQGEwJVUzETMBEGA1UECAwK"
470 "Q2FsaWZvcm5pYTEWMBQGA1UEBwwNTW91bnRhaW4gVmlldzETMBEGA1UECgwKR29v"
471 "Z2xlIEluYzEXMBUGA1UEAwwOd3d3Lmdvb2dsZS5jb20wggEiMA0GCSqGSIb3DQEB"
472 "AQUAA4IBDwAwggEKAoIBAQCcKeLrplAC+Lofy8t/wDwtB6eu72CVp0cJ4V3lknN6"
473 "huH9ct6FFk70oRIh/VBNBBz900jYy+7111Jm1b8iqOTQ9aT5C7SEhNcQFJvqzH3e"
474 "MPkb6ZSWGm1yGF7MCQTGQXF20Sk/O16FSjAynU/b3oJmOctcycWYkY0ytS/k3LBu"
475 "Id45PJaoMqjB0WypqvNeJHC3q5JjCB4RP7Nfx5jjHSrCMhw8lUMW4EaDxjaR9KDh"
476 "PLgjsk+LDIySRSRDaCQGhEOWLJZVLzLo4N6/UlctCHEllpBUSvEOyFga52qroGjg"
477 "rf3WOQ925MFwzd6AK+Ich0gDRg8sQfdLH5OuP1cfLfU1AgMBAAGjggFBMIIBPTAd"
478 "BgNVHSUEFjAUBggrBgEFBQcDAQYIKwYBBQUHAwIwGQYDVR0RBBIwEIIOd3d3Lmdv"
479 "b2dsZS5jb20waAYIKwYBBQUHAQEEXDBaMCsGCCsGAQUFBzAChh9odHRwOi8vcGtp"
480 "Lmdvb2dsZS5jb20vR0lBRzIuY3J0MCsGCCsGAQUFBzABhh9odHRwOi8vY2xpZW50"
481 "czEuZ29vZ2xlLmNvbS9vY3NwMB0GA1UdDgQWBBQ7a+CcxsZByOpc+xpYFcIbnUMZ"
482 "hTAMBgNVHRMBAf8EAjAAMB8GA1UdIwQYMBaAFErdBhYbvPZotXb1gba7Yhq6WoEv"
483 "MBcGA1UdIAQQMA4wDAYKKwYBBAHWeQIFATAwBgNVHR8EKTAnMCWgI6Ahhh9odHRw"
484 "Oi8vcGtpLmdvb2dsZS5jb20vR0lBRzIuY3JsMA0GCSqGSIb3DQEBBQUAA4IBAQCa"
485 "OXCBdoqUy5bxyq+Wrh1zsyyCFim1PH5VU2+yvDSWrgDY8ibRGJmfff3r4Lud5kal"
486 "dKs9k8YlKD3ITG7P0YT/Rk8hLgfEuLcq5cc0xqmE42xJ+Eo2uzq9rYorc5emMCxf"
487 "5L0TJOXZqHQpOEcuptZQ4OjdYMfSxk5UzueUhA3ogZKRcRkdB3WeWRp+nYRhx4St"
488 "o2rt2A0MKmY9165GHUqMK9YaaXHDXqBu7Sefr1uSoAP9gyIJKeihMivsGqJ1TD6Z"
489 "cc6LMe+dN2P8cZEQHtD1y296ul4Mivqk3jatUVL8/hCwgch9A8O4PGZq9WqBfEWm"
490 "IyHh1dPtbg1lOXdYCWtjpAIEAKUDAgEUqQUCAwGJwKqBpwSBpBwUQvoeOk0Kg36S"
491 "YTcLEkXqKwOBfF9vE4KX0NxeLwjcDTpsuh3qXEaZ992r1N38VDcyS6P7I6HBYN9B"
492 "sNHM362zZnY27GpTw+Kwd751CLoXFPoaMOe57dbBpXoro6Pd3BTbf/Tzr88K06yE"
493 "OTDKPNj3+inbMaVigtK4PLyPq+Topyzvx9USFgRvyuoxn0Hgb+R0A3j6SLRuyOdA"
Adam Langley364f7a62016-12-12 10:51:00 -0800494 "i4gv7Y5oliyntgMBAQA=";
Adam Langley10f97f32016-07-12 08:09:33 -0700495
496// kCustomSession is a custom serialized SSL_SESSION generated by
497// filling in missing fields from |kOpenSSLSession|. This includes
498// providing |peer_sha256|, so |peer| is not serialized.
499static const char kCustomSession[] =
500 "MIIBdgIBAQICAwMEAsAvBCAG5Q1ndq4Yfmbeo1zwLkNRKmCXGdNgWvGT3cskV0yQ"
501 "kAQwJlrlzkAWBOWiLj/jJ76D7l+UXoizP2KI2C7I2FccqMmIfFmmkUy32nIJ0mZH"
502 "IWoJoQYCBFRDO46iBAICASykAwQBAqUDAgEUphAEDnd3dy5nb29nbGUuY29tqAcE"
503 "BXdvcmxkqQUCAwGJwKqBpwSBpBwUQvoeOk0Kg36SYTcLEkXqKwOBfF9vE4KX0Nxe"
504 "LwjcDTpsuh3qXEaZ992r1N38VDcyS6P7I6HBYN9BsNHM362zZnY27GpTw+Kwd751"
505 "CLoXFPoaMOe57dbBpXoro6Pd3BTbf/Tzr88K06yEOTDKPNj3+inbMaVigtK4PLyP"
506 "q+Topyzvx9USFgRvyuoxn0Hgb+R0A3j6SLRuyOdAi4gv7Y5oliynrSIEIAYGBgYG"
507 "BgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGrgMEAQevAwQBBLADBAEF";
508
509// kBoringSSLSession is a serialized SSL_SESSION generated from bssl client.
510static const char kBoringSSLSession[] =
511 "MIIRwQIBAQICAwMEAsAvBCDdoGxGK26mR+8lM0uq6+k9xYuxPnwAjpcF9n0Yli9R"
512 "kQQwbyshfWhdi5XQ1++7n2L1qqrcVlmHBPpr6yknT/u4pUrpQB5FZ7vqvNn8MdHf"
513 "9rWgoQYCBFXgs7uiBAICHCCjggR6MIIEdjCCA16gAwIBAgIIf+yfD7Y6UicwDQYJ"
514 "KoZIhvcNAQELBQAwSTELMAkGA1UEBhMCVVMxEzARBgNVBAoTCkdvb2dsZSBJbmMx"
515 "JTAjBgNVBAMTHEdvb2dsZSBJbnRlcm5ldCBBdXRob3JpdHkgRzIwHhcNMTUwODEy"
516 "MTQ1MzE1WhcNMTUxMTEwMDAwMDAwWjBoMQswCQYDVQQGEwJVUzETMBEGA1UECAwK"
517 "Q2FsaWZvcm5pYTEWMBQGA1UEBwwNTW91bnRhaW4gVmlldzETMBEGA1UECgwKR29v"
518 "Z2xlIEluYzEXMBUGA1UEAwwOd3d3Lmdvb2dsZS5jb20wggEiMA0GCSqGSIb3DQEB"
519 "AQUAA4IBDwAwggEKAoIBAQC0MeG5YGQ0t+IeJeoneP/PrhEaieibeKYkbKVLNZpo"
520 "PLuBinvhkXZo3DC133NpCBpy6ZktBwamqyixAyuk/NU6OjgXqwwxfQ7di1AInLIU"
521 "792c7hFyNXSUCG7At8Ifi3YwBX9Ba6u/1d6rWTGZJrdCq3QU11RkKYyTq2KT5mce"
522 "Tv9iGKqSkSTlp8puy/9SZ/3DbU3U+BuqCFqeSlz7zjwFmk35acdCilpJlVDDN5C/"
523 "RCh8/UKc8PaL+cxlt531qoTENvYrflBno14YEZlCBZsPiFeUSILpKEj3Ccwhy0eL"
524 "EucWQ72YZU8mUzXBoXGn0zA0crFl5ci/2sTBBGZsylNBAgMBAAGjggFBMIIBPTAd"
525 "BgNVHSUEFjAUBggrBgEFBQcDAQYIKwYBBQUHAwIwGQYDVR0RBBIwEIIOd3d3Lmdv"
526 "b2dsZS5jb20waAYIKwYBBQUHAQEEXDBaMCsGCCsGAQUFBzAChh9odHRwOi8vcGtp"
527 "Lmdvb2dsZS5jb20vR0lBRzIuY3J0MCsGCCsGAQUFBzABhh9odHRwOi8vY2xpZW50"
528 "czEuZ29vZ2xlLmNvbS9vY3NwMB0GA1UdDgQWBBS/bzHxcE73Q4j3slC4BLbMtLjG"
529 "GjAMBgNVHRMBAf8EAjAAMB8GA1UdIwQYMBaAFErdBhYbvPZotXb1gba7Yhq6WoEv"
530 "MBcGA1UdIAQQMA4wDAYKKwYBBAHWeQIFATAwBgNVHR8EKTAnMCWgI6Ahhh9odHRw"
531 "Oi8vcGtpLmdvb2dsZS5jb20vR0lBRzIuY3JsMA0GCSqGSIb3DQEBCwUAA4IBAQAb"
532 "qdWPZEHk0X7iKPCTHL6S3w6q1eR67goxZGFSM1lk1hjwyu7XcLJuvALVV9uY3ovE"
533 "kQZSHwT+pyOPWQhsSjO+1GyjvCvK/CAwiUmBX+bQRGaqHsRcio7xSbdVcajQ3bXd"
534 "X+s0WdbOpn6MStKAiBVloPlSxEI8pxY6x/BBCnTIk/+DMB17uZlOjG3vbAnkDkP+"
535 "n0OTucD9sHV7EVj9XUxi51nOfNBCN/s7lpUjDS/NJ4k3iwOtbCPswiot8vLO779a"
536 "f07vR03r349Iz/KTzk95rlFtX0IU+KYNxFNsanIXZ+C9FYGRXkwhHcvFb4qMUB1y"
537 "TTlM80jBMOwyjZXmjRAhpAIEAKUDAgEUqQUCAwGJwKqBpwSBpOgebbmn9NRUtMWH"
538 "+eJpqA5JLMFSMCChOsvKey3toBaCNGU7HfAEiiXNuuAdCBoK262BjQc2YYfqFzqH"
539 "zuppopXCvhohx7j/tnCNZIMgLYt/O9SXK2RYI5z8FhCCHvB4CbD5G0LGl5EFP27s"
540 "Jb6S3aTTYPkQe8yZSlxevg6NDwmTogLO9F7UUkaYmVcMQhzssEE2ZRYNwSOU6KjE"
541 "0Yj+8fAiBtbQriIEIN2L8ZlpaVrdN5KFNdvcmOxJu81P8q53X55xQyGTnGWwsgMC"
542 "ARezggvvMIIEdjCCA16gAwIBAgIIf+yfD7Y6UicwDQYJKoZIhvcNAQELBQAwSTEL"
543 "MAkGA1UEBhMCVVMxEzARBgNVBAoTCkdvb2dsZSBJbmMxJTAjBgNVBAMTHEdvb2ds"
544 "ZSBJbnRlcm5ldCBBdXRob3JpdHkgRzIwHhcNMTUwODEyMTQ1MzE1WhcNMTUxMTEw"
545 "MDAwMDAwWjBoMQswCQYDVQQGEwJVUzETMBEGA1UECAwKQ2FsaWZvcm5pYTEWMBQG"
546 "A1UEBwwNTW91bnRhaW4gVmlldzETMBEGA1UECgwKR29vZ2xlIEluYzEXMBUGA1UE"
547 "AwwOd3d3Lmdvb2dsZS5jb20wggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIB"
548 "AQC0MeG5YGQ0t+IeJeoneP/PrhEaieibeKYkbKVLNZpoPLuBinvhkXZo3DC133Np"
549 "CBpy6ZktBwamqyixAyuk/NU6OjgXqwwxfQ7di1AInLIU792c7hFyNXSUCG7At8If"
550 "i3YwBX9Ba6u/1d6rWTGZJrdCq3QU11RkKYyTq2KT5mceTv9iGKqSkSTlp8puy/9S"
551 "Z/3DbU3U+BuqCFqeSlz7zjwFmk35acdCilpJlVDDN5C/RCh8/UKc8PaL+cxlt531"
552 "qoTENvYrflBno14YEZlCBZsPiFeUSILpKEj3Ccwhy0eLEucWQ72YZU8mUzXBoXGn"
553 "0zA0crFl5ci/2sTBBGZsylNBAgMBAAGjggFBMIIBPTAdBgNVHSUEFjAUBggrBgEF"
554 "BQcDAQYIKwYBBQUHAwIwGQYDVR0RBBIwEIIOd3d3Lmdvb2dsZS5jb20waAYIKwYB"
555 "BQUHAQEEXDBaMCsGCCsGAQUFBzAChh9odHRwOi8vcGtpLmdvb2dsZS5jb20vR0lB"
556 "RzIuY3J0MCsGCCsGAQUFBzABhh9odHRwOi8vY2xpZW50czEuZ29vZ2xlLmNvbS9v"
557 "Y3NwMB0GA1UdDgQWBBS/bzHxcE73Q4j3slC4BLbMtLjGGjAMBgNVHRMBAf8EAjAA"
558 "MB8GA1UdIwQYMBaAFErdBhYbvPZotXb1gba7Yhq6WoEvMBcGA1UdIAQQMA4wDAYK"
559 "KwYBBAHWeQIFATAwBgNVHR8EKTAnMCWgI6Ahhh9odHRwOi8vcGtpLmdvb2dsZS5j"
560 "b20vR0lBRzIuY3JsMA0GCSqGSIb3DQEBCwUAA4IBAQAbqdWPZEHk0X7iKPCTHL6S"
561 "3w6q1eR67goxZGFSM1lk1hjwyu7XcLJuvALVV9uY3ovEkQZSHwT+pyOPWQhsSjO+"
562 "1GyjvCvK/CAwiUmBX+bQRGaqHsRcio7xSbdVcajQ3bXdX+s0WdbOpn6MStKAiBVl"
563 "oPlSxEI8pxY6x/BBCnTIk/+DMB17uZlOjG3vbAnkDkP+n0OTucD9sHV7EVj9XUxi"
564 "51nOfNBCN/s7lpUjDS/NJ4k3iwOtbCPswiot8vLO779af07vR03r349Iz/KTzk95"
565 "rlFtX0IU+KYNxFNsanIXZ+C9FYGRXkwhHcvFb4qMUB1yTTlM80jBMOwyjZXmjRAh"
566 "MIID8DCCAtigAwIBAgIDAjqDMA0GCSqGSIb3DQEBCwUAMEIxCzAJBgNVBAYTAlVT"
567 "MRYwFAYDVQQKEw1HZW9UcnVzdCBJbmMuMRswGQYDVQQDExJHZW9UcnVzdCBHbG9i"
568 "YWwgQ0EwHhcNMTMwNDA1MTUxNTU2WhcNMTYxMjMxMjM1OTU5WjBJMQswCQYDVQQG"
569 "EwJVUzETMBEGA1UEChMKR29vZ2xlIEluYzElMCMGA1UEAxMcR29vZ2xlIEludGVy"
570 "bmV0IEF1dGhvcml0eSBHMjCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEB"
571 "AJwqBHdc2FCROgajguDYUEi8iT/xGXAaiEZ+4I/F8YnOIe5a/mENtzJEiaB0C1NP"
572 "VaTOgmKV7utZX8bhBYASxF6UP7xbSDj0U/ck5vuR6RXEz/RTDfRK/J9U3n2+oGtv"
573 "h8DQUB8oMANA2ghzUWx//zo8pzcGjr1LEQTrfSTe5vn8MXH7lNVg8y5Kr0LSy+rE"
574 "ahqyzFPdFUuLH8gZYR/Nnag+YyuENWllhMgZxUYi+FOVvuOAShDGKuy6lyARxzmZ"
575 "EASg8GF6lSWMTlJ14rbtCMoU/M4iarNOz0YDl5cDfsCx3nuvRTPPuj5xt970JSXC"
576 "DTWJnZ37DhF5iR43xa+OcmkCAwEAAaOB5zCB5DAfBgNVHSMEGDAWgBTAephojYn7"
577 "qwVkDBF9qn1luMrMTjAdBgNVHQ4EFgQUSt0GFhu89mi1dvWBtrtiGrpagS8wDgYD"
578 "VR0PAQH/BAQDAgEGMC4GCCsGAQUFBwEBBCIwIDAeBggrBgEFBQcwAYYSaHR0cDov"
579 "L2cuc3ltY2QuY29tMBIGA1UdEwEB/wQIMAYBAf8CAQAwNQYDVR0fBC4wLDAqoCig"
580 "JoYkaHR0cDovL2cuc3ltY2IuY29tL2NybHMvZ3RnbG9iYWwuY3JsMBcGA1UdIAQQ"
581 "MA4wDAYKKwYBBAHWeQIFATANBgkqhkiG9w0BAQsFAAOCAQEAqvqpIM1qZ4PtXtR+"
582 "3h3Ef+AlBgDFJPupyC1tft6dgmUsgWM0Zj7pUsIItMsv91+ZOmqcUHqFBYx90SpI"
583 "hNMJbHzCzTWf84LuUt5oX+QAihcglvcpjZpNy6jehsgNb1aHA30DP9z6eX0hGfnI"
584 "Oi9RdozHQZJxjyXON/hKTAAj78Q1EK7gI4BzfE00LshukNYQHpmEcxpw8u1VDu4X"
585 "Bupn7jLrLN1nBz/2i8Jw3lsA5rsb0zYaImxssDVCbJAJPZPpZAkiDoUGn8JzIdPm"
586 "X4DkjYUiOnMDsWCOrmji9D6X52ASCWg23jrW4kOVWzeBkoEfu43XrVJkFleW2V40"
587 "fsg12DCCA30wggLmoAMCAQICAxK75jANBgkqhkiG9w0BAQUFADBOMQswCQYDVQQG"
588 "EwJVUzEQMA4GA1UEChMHRXF1aWZheDEtMCsGA1UECxMkRXF1aWZheCBTZWN1cmUg"
589 "Q2VydGlmaWNhdGUgQXV0aG9yaXR5MB4XDTAyMDUyMTA0MDAwMFoXDTE4MDgyMTA0"
590 "MDAwMFowQjELMAkGA1UEBhMCVVMxFjAUBgNVBAoTDUdlb1RydXN0IEluYy4xGzAZ"
591 "BgNVBAMTEkdlb1RydXN0IEdsb2JhbCBDQTCCASIwDQYJKoZIhvcNAQEBBQADggEP"
592 "ADCCAQoCggEBANrMGGMw/fQXIxpWflvfPGw45HG3eJHUvKHYTPioQ7YD6U0hBwiI"
593 "2lgvZjkpvQV4i5046AW3an5xpObEYKaw74DkiSgPniXW7YPzraaRx5jJQhg1FJ2t"
594 "mEaSLk/K8YdDwRaVVy1Q74ktgHpXrfLuX2vSAI25FPgUFTXZwEaje3LIkb/JVSvN"
595 "0Jc+nCZkzN/Ogxlxyk7m1NV7qRnNVd7I7NJeOFPlXE+MLf5QIzb8ZubLjqQ5GQC3"
596 "lQI5kQsO/jgu0R0FmvZNPm8PBx2vLB6PYDni+jZTEznUXiYr2z2oFL0y6xgDKFIE"
597 "ceWrMz3hOLsHNoRinHnqFjD0X8Ar6HFr5PkCAwEAAaOB8DCB7TAfBgNVHSMEGDAW"
598 "gBRI5mj5K9KylddH2CMgEE8zmJCf1DAdBgNVHQ4EFgQUwHqYaI2J+6sFZAwRfap9"
599 "ZbjKzE4wDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMCAQYwOgYDVR0fBDMw"
600 "MTAvoC2gK4YpaHR0cDovL2NybC5nZW90cnVzdC5jb20vY3Jscy9zZWN1cmVjYS5j"
601 "cmwwTgYDVR0gBEcwRTBDBgRVHSAAMDswOQYIKwYBBQUHAgEWLWh0dHBzOi8vd3d3"
602 "Lmdlb3RydXN0LmNvbS9yZXNvdXJjZXMvcmVwb3NpdG9yeTANBgkqhkiG9w0BAQUF"
603 "AAOBgQB24RJuTksWEoYwBrKBCM/wCMfHcX5m7sLt1Dsf//DwyE7WQziwuTB9GNBV"
604 "g6JqyzYRnOhIZqNtf7gT1Ef+i1pcc/yu2RsyGTirlzQUqpbS66McFAhJtrvlke+D"
605 "NusdVm/K2rxzY5Dkf3s+Iss9B+1fOHSc4wNQTqGvmO5h8oQ/Eg==";
606
607// kBadSessionExtraField is a custom serialized SSL_SESSION generated by replacing
608// the final (optional) element of |kCustomSession| with tag number 30.
609static const char kBadSessionExtraField[] =
610 "MIIBdgIBAQICAwMEAsAvBCAG5Q1ndq4Yfmbeo1zwLkNRKmCXGdNgWvGT3cskV0yQ"
611 "kAQwJlrlzkAWBOWiLj/jJ76D7l+UXoizP2KI2C7I2FccqMmIfFmmkUy32nIJ0mZH"
612 "IWoJoQYCBFRDO46iBAICASykAwQBAqUDAgEUphAEDnd3dy5nb29nbGUuY29tqAcE"
613 "BXdvcmxkqQUCAwGJwKqBpwSBpBwUQvoeOk0Kg36SYTcLEkXqKwOBfF9vE4KX0Nxe"
614 "LwjcDTpsuh3qXEaZ992r1N38VDcyS6P7I6HBYN9BsNHM362zZnY27GpTw+Kwd751"
615 "CLoXFPoaMOe57dbBpXoro6Pd3BTbf/Tzr88K06yEOTDKPNj3+inbMaVigtK4PLyP"
616 "q+Topyzvx9USFgRvyuoxn0Hgb+R0A3j6SLRuyOdAi4gv7Y5oliynrSIEIAYGBgYG"
617 "BgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGrgMEAQevAwQBBL4DBAEF";
618
619// kBadSessionVersion is a custom serialized SSL_SESSION generated by replacing
620// the version of |kCustomSession| with 2.
621static const char kBadSessionVersion[] =
622 "MIIBdgIBAgICAwMEAsAvBCAG5Q1ndq4Yfmbeo1zwLkNRKmCXGdNgWvGT3cskV0yQ"
623 "kAQwJlrlzkAWBOWiLj/jJ76D7l+UXoizP2KI2C7I2FccqMmIfFmmkUy32nIJ0mZH"
624 "IWoJoQYCBFRDO46iBAICASykAwQBAqUDAgEUphAEDnd3dy5nb29nbGUuY29tqAcE"
625 "BXdvcmxkqQUCAwGJwKqBpwSBpBwUQvoeOk0Kg36SYTcLEkXqKwOBfF9vE4KX0Nxe"
626 "LwjcDTpsuh3qXEaZ992r1N38VDcyS6P7I6HBYN9BsNHM362zZnY27GpTw+Kwd751"
627 "CLoXFPoaMOe57dbBpXoro6Pd3BTbf/Tzr88K06yEOTDKPNj3+inbMaVigtK4PLyP"
628 "q+Topyzvx9USFgRvyuoxn0Hgb+R0A3j6SLRuyOdAi4gv7Y5oliynrSIEIAYGBgYG"
629 "BgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGrgMEAQevAwQBBLADBAEF";
630
631// kBadSessionTrailingData is a custom serialized SSL_SESSION with trailing data
632// appended.
633static const char kBadSessionTrailingData[] =
634 "MIIBdgIBAQICAwMEAsAvBCAG5Q1ndq4Yfmbeo1zwLkNRKmCXGdNgWvGT3cskV0yQ"
635 "kAQwJlrlzkAWBOWiLj/jJ76D7l+UXoizP2KI2C7I2FccqMmIfFmmkUy32nIJ0mZH"
636 "IWoJoQYCBFRDO46iBAICASykAwQBAqUDAgEUphAEDnd3dy5nb29nbGUuY29tqAcE"
637 "BXdvcmxkqQUCAwGJwKqBpwSBpBwUQvoeOk0Kg36SYTcLEkXqKwOBfF9vE4KX0Nxe"
638 "LwjcDTpsuh3qXEaZ992r1N38VDcyS6P7I6HBYN9BsNHM362zZnY27GpTw+Kwd751"
639 "CLoXFPoaMOe57dbBpXoro6Pd3BTbf/Tzr88K06yEOTDKPNj3+inbMaVigtK4PLyP"
640 "q+Topyzvx9USFgRvyuoxn0Hgb+R0A3j6SLRuyOdAi4gv7Y5oliynrSIEIAYGBgYG"
641 "BgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGrgMEAQevAwQBBLADBAEFAAAA";
642
David Benjamin1d77e562015-03-22 17:22:08 -0400643static bool DecodeBase64(std::vector<uint8_t> *out, const char *in) {
David Benjamin751e8892014-10-19 00:59:36 -0400644 size_t len;
David Benjamin751e8892014-10-19 00:59:36 -0400645 if (!EVP_DecodedLength(&len, strlen(in))) {
646 fprintf(stderr, "EVP_DecodedLength failed\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400647 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400648 }
649
David Benjamin1d77e562015-03-22 17:22:08 -0400650 out->resize(len);
David Benjaminef14b2d2015-11-11 14:01:27 -0800651 if (!EVP_DecodeBase64(out->data(), &len, len, (const uint8_t *)in,
David Benjamin751e8892014-10-19 00:59:36 -0400652 strlen(in))) {
653 fprintf(stderr, "EVP_DecodeBase64 failed\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400654 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400655 }
David Benjamin1d77e562015-03-22 17:22:08 -0400656 out->resize(len);
657 return true;
David Benjamin751e8892014-10-19 00:59:36 -0400658}
659
David Benjamin1d77e562015-03-22 17:22:08 -0400660static bool TestSSL_SESSIONEncoding(const char *input_b64) {
David Benjamin751e8892014-10-19 00:59:36 -0400661 const uint8_t *cptr;
662 uint8_t *ptr;
David Benjamin751e8892014-10-19 00:59:36 -0400663
David Benjamin1d77e562015-03-22 17:22:08 -0400664 // Decode the input.
665 std::vector<uint8_t> input;
666 if (!DecodeBase64(&input, input_b64)) {
667 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400668 }
669
David Benjamin1d77e562015-03-22 17:22:08 -0400670 // Verify the SSL_SESSION decodes.
Adam Langley46db7af2017-02-01 15:49:37 -0800671 bssl::UniquePtr<SSL_CTX> ssl_ctx(SSL_CTX_new(TLS_method()));
672 if (!ssl_ctx) {
673 return false;
674 }
675 bssl::UniquePtr<SSL_SESSION> session(
676 SSL_SESSION_from_bytes(input.data(), input.size(), ssl_ctx.get()));
David Benjaminfd67aa82015-06-15 19:41:48 -0400677 if (!session) {
678 fprintf(stderr, "SSL_SESSION_from_bytes failed\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400679 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400680 }
681
David Benjamin1d77e562015-03-22 17:22:08 -0400682 // Verify the SSL_SESSION encoding round-trips.
683 size_t encoded_len;
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700684 bssl::UniquePtr<uint8_t> encoded;
David Benjamin1d77e562015-03-22 17:22:08 -0400685 uint8_t *encoded_raw;
686 if (!SSL_SESSION_to_bytes(session.get(), &encoded_raw, &encoded_len)) {
David Benjamin3cac4502014-10-21 01:46:30 -0400687 fprintf(stderr, "SSL_SESSION_to_bytes failed\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400688 return false;
David Benjamin3cac4502014-10-21 01:46:30 -0400689 }
David Benjamin1d77e562015-03-22 17:22:08 -0400690 encoded.reset(encoded_raw);
691 if (encoded_len != input.size() ||
David Benjamin17cf2cb2016-12-13 01:07:13 -0500692 OPENSSL_memcmp(input.data(), encoded.get(), input.size()) != 0) {
David Benjamin3cac4502014-10-21 01:46:30 -0400693 fprintf(stderr, "SSL_SESSION_to_bytes did not round-trip\n");
Sigbjorn Vik2b23d242015-06-29 15:07:26 +0200694 hexdump(stderr, "Before: ", input.data(), input.size());
695 hexdump(stderr, "After: ", encoded_raw, encoded_len);
David Benjamin1d77e562015-03-22 17:22:08 -0400696 return false;
David Benjamin3cac4502014-10-21 01:46:30 -0400697 }
David Benjamin3cac4502014-10-21 01:46:30 -0400698
David Benjaminfd67aa82015-06-15 19:41:48 -0400699 // Verify the SSL_SESSION also decodes with the legacy API.
David Benjaminef14b2d2015-11-11 14:01:27 -0800700 cptr = input.data();
David Benjaminfd67aa82015-06-15 19:41:48 -0400701 session.reset(d2i_SSL_SESSION(NULL, &cptr, input.size()));
David Benjaminef14b2d2015-11-11 14:01:27 -0800702 if (!session || cptr != input.data() + input.size()) {
David Benjaminfd67aa82015-06-15 19:41:48 -0400703 fprintf(stderr, "d2i_SSL_SESSION failed\n");
704 return false;
705 }
706
David Benjamin1d77e562015-03-22 17:22:08 -0400707 // Verify the SSL_SESSION encoding round-trips via the legacy API.
708 int len = i2d_SSL_SESSION(session.get(), NULL);
709 if (len < 0 || (size_t)len != input.size()) {
David Benjamin751e8892014-10-19 00:59:36 -0400710 fprintf(stderr, "i2d_SSL_SESSION(NULL) returned invalid length\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400711 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400712 }
713
David Benjamin1d77e562015-03-22 17:22:08 -0400714 encoded.reset((uint8_t *)OPENSSL_malloc(input.size()));
715 if (!encoded) {
David Benjamin751e8892014-10-19 00:59:36 -0400716 fprintf(stderr, "malloc failed\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400717 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400718 }
David Benjamin1d77e562015-03-22 17:22:08 -0400719
720 ptr = encoded.get();
721 len = i2d_SSL_SESSION(session.get(), &ptr);
722 if (len < 0 || (size_t)len != input.size()) {
David Benjamin751e8892014-10-19 00:59:36 -0400723 fprintf(stderr, "i2d_SSL_SESSION returned invalid length\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400724 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400725 }
David Benjamin1d77e562015-03-22 17:22:08 -0400726 if (ptr != encoded.get() + input.size()) {
David Benjamin751e8892014-10-19 00:59:36 -0400727 fprintf(stderr, "i2d_SSL_SESSION did not advance ptr correctly\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400728 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400729 }
David Benjamin17cf2cb2016-12-13 01:07:13 -0500730 if (OPENSSL_memcmp(input.data(), encoded.get(), input.size()) != 0) {
David Benjamin751e8892014-10-19 00:59:36 -0400731 fprintf(stderr, "i2d_SSL_SESSION did not round-trip\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400732 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400733 }
734
David Benjamin1d77e562015-03-22 17:22:08 -0400735 return true;
David Benjamin751e8892014-10-19 00:59:36 -0400736}
737
David Benjaminf297e022015-05-28 19:55:29 -0400738static bool TestBadSSL_SESSIONEncoding(const char *input_b64) {
739 std::vector<uint8_t> input;
740 if (!DecodeBase64(&input, input_b64)) {
741 return false;
742 }
743
744 // Verify that the SSL_SESSION fails to decode.
Adam Langley46db7af2017-02-01 15:49:37 -0800745 bssl::UniquePtr<SSL_CTX> ssl_ctx(SSL_CTX_new(TLS_method()));
746 if (!ssl_ctx) {
747 return false;
748 }
749 bssl::UniquePtr<SSL_SESSION> session(
750 SSL_SESSION_from_bytes(input.data(), input.size(), ssl_ctx.get()));
David Benjaminf297e022015-05-28 19:55:29 -0400751 if (session) {
David Benjaminfd67aa82015-06-15 19:41:48 -0400752 fprintf(stderr, "SSL_SESSION_from_bytes unexpectedly succeeded\n");
David Benjaminf297e022015-05-28 19:55:29 -0400753 return false;
754 }
755 ERR_clear_error();
756 return true;
757}
758
David Benjamin10e664b2016-06-20 22:20:47 -0400759static bool TestDefaultVersion(uint16_t min_version, uint16_t max_version,
David Benjamin1d77e562015-03-22 17:22:08 -0400760 const SSL_METHOD *(*method)(void)) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700761 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(method()));
David Benjamin1d77e562015-03-22 17:22:08 -0400762 if (!ctx) {
763 return false;
David Benjamin82c9e902014-12-12 15:55:27 -0500764 }
David Benjaminb6a0a512016-06-21 10:33:21 -0400765 if (ctx->min_version != min_version || ctx->max_version != max_version) {
766 fprintf(stderr, "Got min %04x, max %04x; wanted min %04x, max %04x\n",
767 ctx->min_version, ctx->max_version, min_version, max_version);
768 return false;
769 }
770 return true;
David Benjamin82c9e902014-12-12 15:55:27 -0500771}
772
David Benjamin1d77e562015-03-22 17:22:08 -0400773static bool CipherGetRFCName(std::string *out, uint16_t value) {
David Benjamin2bdb35c2015-02-21 11:03:06 -0500774 const SSL_CIPHER *cipher = SSL_get_cipher_by_value(value);
775 if (cipher == NULL) {
David Benjamin1d77e562015-03-22 17:22:08 -0400776 return false;
David Benjamin65226252015-02-05 16:49:47 -0500777 }
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700778 bssl::UniquePtr<char> rfc_name(SSL_CIPHER_get_rfc_name(cipher));
David Benjamin3fa65f02015-05-15 19:11:57 -0400779 if (!rfc_name) {
780 return false;
781 }
David Benjamin67be0482015-04-20 16:19:00 -0400782 out->assign(rfc_name.get());
David Benjamin1d77e562015-03-22 17:22:08 -0400783 return true;
David Benjamin65226252015-02-05 16:49:47 -0500784}
785
786typedef struct {
David Benjamin2bdb35c2015-02-21 11:03:06 -0500787 int id;
David Benjamin65226252015-02-05 16:49:47 -0500788 const char *rfc_name;
789} CIPHER_RFC_NAME_TEST;
790
791static const CIPHER_RFC_NAME_TEST kCipherRFCNameTests[] = {
Steven Valdez803c77a2016-09-06 14:13:43 -0400792 {SSL3_CK_RSA_DES_192_CBC3_SHA, "TLS_RSA_WITH_3DES_EDE_CBC_SHA"},
793 {TLS1_CK_RSA_WITH_AES_128_SHA, "TLS_RSA_WITH_AES_128_CBC_SHA"},
794 {TLS1_CK_DHE_RSA_WITH_AES_256_SHA, "TLS_DHE_RSA_WITH_AES_256_CBC_SHA"},
795 {TLS1_CK_DHE_RSA_WITH_AES_256_SHA256,
796 "TLS_DHE_RSA_WITH_AES_256_CBC_SHA256"},
797 {TLS1_CK_ECDHE_RSA_WITH_AES_128_SHA256,
798 "TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256"},
799 {TLS1_CK_ECDHE_RSA_WITH_AES_256_SHA384,
800 "TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384"},
801 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256,
802 "TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256"},
803 {TLS1_CK_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256,
804 "TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256"},
805 {TLS1_CK_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384,
806 "TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384"},
807 {TLS1_CK_ECDHE_PSK_WITH_AES_128_CBC_SHA,
808 "TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA"},
809 {TLS1_CK_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256,
810 "TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256"},
811 {TLS1_CK_AES_256_GCM_SHA384, "TLS_AES_256_GCM_SHA384"},
812 {TLS1_CK_AES_128_GCM_SHA256, "TLS_AES_128_GCM_SHA256"},
813 {TLS1_CK_CHACHA20_POLY1305_SHA256, "TLS_CHACHA20_POLY1305_SHA256"},
David Benjamin65226252015-02-05 16:49:47 -0500814};
815
David Benjamin1d77e562015-03-22 17:22:08 -0400816static bool TestCipherGetRFCName(void) {
817 for (size_t i = 0;
Steven Valdezcb966542016-08-17 16:56:14 -0400818 i < OPENSSL_ARRAY_SIZE(kCipherRFCNameTests); i++) {
David Benjamin65226252015-02-05 16:49:47 -0500819 const CIPHER_RFC_NAME_TEST *test = &kCipherRFCNameTests[i];
David Benjamin1d77e562015-03-22 17:22:08 -0400820 std::string rfc_name;
821 if (!CipherGetRFCName(&rfc_name, test->id & 0xffff)) {
822 fprintf(stderr, "SSL_CIPHER_get_rfc_name failed\n");
823 return false;
David Benjamin65226252015-02-05 16:49:47 -0500824 }
David Benjamin1d77e562015-03-22 17:22:08 -0400825 if (rfc_name != test->rfc_name) {
David Benjamin65226252015-02-05 16:49:47 -0500826 fprintf(stderr, "SSL_CIPHER_get_rfc_name: got '%s', wanted '%s'\n",
David Benjamin1d77e562015-03-22 17:22:08 -0400827 rfc_name.c_str(), test->rfc_name);
828 return false;
David Benjamin65226252015-02-05 16:49:47 -0500829 }
David Benjamin65226252015-02-05 16:49:47 -0500830 }
David Benjamin1d77e562015-03-22 17:22:08 -0400831 return true;
David Benjamin65226252015-02-05 16:49:47 -0500832}
833
Steven Valdeza833c352016-11-01 13:39:36 -0400834// CreateSessionWithTicket returns a sample |SSL_SESSION| with the specified
835// version and ticket length or nullptr on failure.
836static bssl::UniquePtr<SSL_SESSION> CreateSessionWithTicket(uint16_t version,
837 size_t ticket_len) {
David Benjamin422fe082015-07-21 22:03:43 -0400838 std::vector<uint8_t> der;
839 if (!DecodeBase64(&der, kOpenSSLSession)) {
840 return nullptr;
841 }
Adam Langley46db7af2017-02-01 15:49:37 -0800842
843 bssl::UniquePtr<SSL_CTX> ssl_ctx(SSL_CTX_new(TLS_method()));
844 if (!ssl_ctx) {
845 return nullptr;
846 }
Steven Valdeza833c352016-11-01 13:39:36 -0400847 bssl::UniquePtr<SSL_SESSION> session(
Adam Langley46db7af2017-02-01 15:49:37 -0800848 SSL_SESSION_from_bytes(der.data(), der.size(), ssl_ctx.get()));
David Benjamin422fe082015-07-21 22:03:43 -0400849 if (!session) {
850 return nullptr;
851 }
852
Steven Valdeza833c352016-11-01 13:39:36 -0400853 session->ssl_version = version;
854
David Benjamin422fe082015-07-21 22:03:43 -0400855 // Swap out the ticket for a garbage one.
856 OPENSSL_free(session->tlsext_tick);
857 session->tlsext_tick = reinterpret_cast<uint8_t*>(OPENSSL_malloc(ticket_len));
858 if (session->tlsext_tick == nullptr) {
859 return nullptr;
860 }
David Benjamin17cf2cb2016-12-13 01:07:13 -0500861 OPENSSL_memset(session->tlsext_tick, 'a', ticket_len);
David Benjamin422fe082015-07-21 22:03:43 -0400862 session->tlsext_ticklen = ticket_len;
David Benjamin1269ddd2015-10-18 15:18:55 -0400863
864 // Fix up the timeout.
David Benjamin9b63f292016-11-15 00:44:05 -0500865#if defined(BORINGSSL_UNSAFE_DETERMINISTIC_MODE)
866 session->time = 1234;
867#else
David Benjamin1269ddd2015-10-18 15:18:55 -0400868 session->time = time(NULL);
David Benjamin9b63f292016-11-15 00:44:05 -0500869#endif
David Benjamin422fe082015-07-21 22:03:43 -0400870 return session;
871}
872
David Benjaminafc64de2016-07-19 17:12:41 +0200873static bool GetClientHello(SSL *ssl, std::vector<uint8_t> *out) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700874 bssl::UniquePtr<BIO> bio(BIO_new(BIO_s_mem()));
David Benjaminafc64de2016-07-19 17:12:41 +0200875 if (!bio) {
876 return false;
877 }
878 // Do not configure a reading BIO, but record what's written to a memory BIO.
David Benjamin96a16cd2016-08-11 12:14:47 -0400879 BIO_up_ref(bio.get());
880 SSL_set_bio(ssl, nullptr /* rbio */, bio.get());
David Benjaminafc64de2016-07-19 17:12:41 +0200881 int ret = SSL_connect(ssl);
882 if (ret > 0) {
883 // SSL_connect should fail without a BIO to write to.
884 return false;
885 }
886 ERR_clear_error();
887
888 const uint8_t *client_hello;
889 size_t client_hello_len;
890 if (!BIO_mem_contents(bio.get(), &client_hello, &client_hello_len)) {
891 return false;
892 }
893 *out = std::vector<uint8_t>(client_hello, client_hello + client_hello_len);
894 return true;
895}
896
Steven Valdeza833c352016-11-01 13:39:36 -0400897// GetClientHelloLen creates a client SSL connection with the specified version
898// and ticket length. It returns the length of the ClientHello, not including
899// the record header, on success and zero on error.
900static size_t GetClientHelloLen(uint16_t max_version, uint16_t session_version,
901 size_t ticket_len) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700902 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
Steven Valdeza833c352016-11-01 13:39:36 -0400903 bssl::UniquePtr<SSL_SESSION> session =
904 CreateSessionWithTicket(session_version, ticket_len);
David Benjamin422fe082015-07-21 22:03:43 -0400905 if (!ctx || !session) {
906 return 0;
907 }
Steven Valdeza833c352016-11-01 13:39:36 -0400908
909 // Set a one-element cipher list so the baseline ClientHello is unpadded.
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700910 bssl::UniquePtr<SSL> ssl(SSL_new(ctx.get()));
Steven Valdez2c62fe92016-10-14 12:08:12 -0400911 if (!ssl || !SSL_set_session(ssl.get(), session.get()) ||
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800912 !SSL_set_strict_cipher_list(ssl.get(), "ECDHE-RSA-AES128-GCM-SHA256") ||
Steven Valdeza833c352016-11-01 13:39:36 -0400913 !SSL_set_max_proto_version(ssl.get(), max_version)) {
David Benjamin422fe082015-07-21 22:03:43 -0400914 return 0;
915 }
Steven Valdeza833c352016-11-01 13:39:36 -0400916
David Benjaminafc64de2016-07-19 17:12:41 +0200917 std::vector<uint8_t> client_hello;
918 if (!GetClientHello(ssl.get(), &client_hello) ||
919 client_hello.size() <= SSL3_RT_HEADER_LENGTH) {
David Benjamin422fe082015-07-21 22:03:43 -0400920 return 0;
921 }
Steven Valdeza833c352016-11-01 13:39:36 -0400922
David Benjaminafc64de2016-07-19 17:12:41 +0200923 return client_hello.size() - SSL3_RT_HEADER_LENGTH;
David Benjamin422fe082015-07-21 22:03:43 -0400924}
925
926struct PaddingTest {
927 size_t input_len, padded_len;
928};
929
930static const PaddingTest kPaddingTests[] = {
931 // ClientHellos of length below 0x100 do not require padding.
932 {0xfe, 0xfe},
933 {0xff, 0xff},
934 // ClientHellos of length 0x100 through 0x1fb are padded up to 0x200.
935 {0x100, 0x200},
936 {0x123, 0x200},
937 {0x1fb, 0x200},
938 // ClientHellos of length 0x1fc through 0x1ff get padded beyond 0x200. The
939 // padding extension takes a minimum of four bytes plus one required content
940 // byte. (To work around yet more server bugs, we avoid empty final
941 // extensions.)
942 {0x1fc, 0x201},
943 {0x1fd, 0x202},
944 {0x1fe, 0x203},
945 {0x1ff, 0x204},
946 // Finally, larger ClientHellos need no padding.
947 {0x200, 0x200},
948 {0x201, 0x201},
949};
950
Steven Valdeza833c352016-11-01 13:39:36 -0400951static bool TestPaddingExtension(uint16_t max_version,
952 uint16_t session_version) {
David Benjamin422fe082015-07-21 22:03:43 -0400953 // Sample a baseline length.
Steven Valdeza833c352016-11-01 13:39:36 -0400954 size_t base_len = GetClientHelloLen(max_version, session_version, 1);
David Benjamin422fe082015-07-21 22:03:43 -0400955 if (base_len == 0) {
956 return false;
957 }
958
959 for (const PaddingTest &test : kPaddingTests) {
960 if (base_len > test.input_len) {
Steven Valdeza833c352016-11-01 13:39:36 -0400961 fprintf(stderr,
962 "Baseline ClientHello too long (max_version = %04x, "
963 "session_version = %04x).\n",
964 max_version, session_version);
David Benjamin422fe082015-07-21 22:03:43 -0400965 return false;
966 }
967
Steven Valdeza833c352016-11-01 13:39:36 -0400968 size_t padded_len = GetClientHelloLen(max_version, session_version,
969 1 + test.input_len - base_len);
David Benjamin422fe082015-07-21 22:03:43 -0400970 if (padded_len != test.padded_len) {
Steven Valdeza833c352016-11-01 13:39:36 -0400971 fprintf(stderr,
972 "%u-byte ClientHello padded to %u bytes, not %u (max_version = "
973 "%04x, session_version = %04x).\n",
David Benjamin422fe082015-07-21 22:03:43 -0400974 static_cast<unsigned>(test.input_len),
975 static_cast<unsigned>(padded_len),
Steven Valdeza833c352016-11-01 13:39:36 -0400976 static_cast<unsigned>(test.padded_len), max_version,
977 session_version);
David Benjamin422fe082015-07-21 22:03:43 -0400978 return false;
979 }
980 }
Steven Valdeza833c352016-11-01 13:39:36 -0400981
David Benjamin422fe082015-07-21 22:03:43 -0400982 return true;
983}
984
David Benjamin1d128f32015-09-08 17:41:40 -0400985// Test that |SSL_get_client_CA_list| echoes back the configured parameter even
986// before configuring as a server.
David Benjaminf0d8e222017-02-04 10:58:26 -0500987TEST(SSLTest, ClientCAList) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700988 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
David Benjaminf0d8e222017-02-04 10:58:26 -0500989 ASSERT_TRUE(ctx);
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700990 bssl::UniquePtr<SSL> ssl(SSL_new(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -0500991 ASSERT_TRUE(ssl);
David Benjamin1d128f32015-09-08 17:41:40 -0400992
Adam Langley34b4c822017-02-02 10:57:17 -0800993 bssl::UniquePtr<X509_NAME> name(X509_NAME_new());
994 ASSERT_TRUE(name);
David Benjamin1d128f32015-09-08 17:41:40 -0400995
Adam Langley34b4c822017-02-02 10:57:17 -0800996 bssl::UniquePtr<X509_NAME> name_dup(X509_NAME_dup(name.get()));
997 ASSERT_TRUE(name_dup);
998
999 bssl::UniquePtr<STACK_OF(X509_NAME)> stack(sk_X509_NAME_new_null());
1000 ASSERT_TRUE(stack);
1001
1002 ASSERT_TRUE(sk_X509_NAME_push(stack.get(), name_dup.get()));
1003 name_dup.release();
1004
1005 // |SSL_set_client_CA_list| takes ownership.
1006 SSL_set_client_CA_list(ssl.get(), stack.release());
1007
1008 STACK_OF(X509_NAME) *result = SSL_get_client_CA_list(ssl.get());
1009 ASSERT_TRUE(result);
1010 ASSERT_EQ(1u, sk_X509_NAME_num(result));
1011 EXPECT_EQ(0, X509_NAME_cmp(sk_X509_NAME_value(result, 0), name.get()));
David Benjamin1d128f32015-09-08 17:41:40 -04001012}
1013
David Benjamin0f653952015-10-18 14:28:01 -04001014static void AppendSession(SSL_SESSION *session, void *arg) {
1015 std::vector<SSL_SESSION*> *out =
1016 reinterpret_cast<std::vector<SSL_SESSION*>*>(arg);
1017 out->push_back(session);
1018}
1019
1020// ExpectCache returns true if |ctx|'s session cache consists of |expected|, in
1021// order.
1022static bool ExpectCache(SSL_CTX *ctx,
1023 const std::vector<SSL_SESSION*> &expected) {
1024 // Check the linked list.
1025 SSL_SESSION *ptr = ctx->session_cache_head;
1026 for (SSL_SESSION *session : expected) {
1027 if (ptr != session) {
1028 return false;
1029 }
1030 // TODO(davidben): This is an absurd way to denote the end of the list.
1031 if (ptr->next ==
1032 reinterpret_cast<SSL_SESSION *>(&ctx->session_cache_tail)) {
1033 ptr = nullptr;
1034 } else {
1035 ptr = ptr->next;
1036 }
1037 }
1038 if (ptr != nullptr) {
1039 return false;
1040 }
1041
1042 // Check the hash table.
1043 std::vector<SSL_SESSION*> actual, expected_copy;
1044 lh_SSL_SESSION_doall_arg(SSL_CTX_sessions(ctx), AppendSession, &actual);
1045 expected_copy = expected;
1046
1047 std::sort(actual.begin(), actual.end());
1048 std::sort(expected_copy.begin(), expected_copy.end());
1049
1050 return actual == expected_copy;
1051}
1052
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001053static bssl::UniquePtr<SSL_SESSION> CreateTestSession(uint32_t number) {
Adam Langley46db7af2017-02-01 15:49:37 -08001054 bssl::UniquePtr<SSL_CTX> ssl_ctx(SSL_CTX_new(TLS_method()));
1055 if (!ssl_ctx) {
1056 return nullptr;
1057 }
1058 bssl::UniquePtr<SSL_SESSION> ret(SSL_SESSION_new(ssl_ctx.get()));
David Benjamin0f653952015-10-18 14:28:01 -04001059 if (!ret) {
1060 return nullptr;
1061 }
1062
1063 ret->session_id_length = SSL3_SSL_SESSION_ID_LENGTH;
David Benjamin17cf2cb2016-12-13 01:07:13 -05001064 OPENSSL_memset(ret->session_id, 0, ret->session_id_length);
1065 OPENSSL_memcpy(ret->session_id, &number, sizeof(number));
David Benjamin0f653952015-10-18 14:28:01 -04001066 return ret;
1067}
1068
David Benjamin0f653952015-10-18 14:28:01 -04001069// Test that the internal session cache behaves as expected.
1070static bool TestInternalSessionCache() {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001071 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
David Benjamin0f653952015-10-18 14:28:01 -04001072 if (!ctx) {
1073 return false;
1074 }
1075
1076 // Prepare 10 test sessions.
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001077 std::vector<bssl::UniquePtr<SSL_SESSION>> sessions;
David Benjamin0f653952015-10-18 14:28:01 -04001078 for (int i = 0; i < 10; i++) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001079 bssl::UniquePtr<SSL_SESSION> session = CreateTestSession(i);
David Benjamin0f653952015-10-18 14:28:01 -04001080 if (!session) {
1081 return false;
1082 }
David Benjamin4f6acaf2015-11-21 03:00:50 -05001083 sessions.push_back(std::move(session));
David Benjamin0f653952015-10-18 14:28:01 -04001084 }
1085
1086 SSL_CTX_sess_set_cache_size(ctx.get(), 5);
1087
1088 // Insert all the test sessions.
David Benjamin4f6acaf2015-11-21 03:00:50 -05001089 for (const auto &session : sessions) {
1090 if (!SSL_CTX_add_session(ctx.get(), session.get())) {
David Benjamin0f653952015-10-18 14:28:01 -04001091 return false;
1092 }
1093 }
1094
1095 // Only the last five should be in the list.
David Benjamin4f6acaf2015-11-21 03:00:50 -05001096 std::vector<SSL_SESSION*> expected = {
1097 sessions[9].get(),
1098 sessions[8].get(),
1099 sessions[7].get(),
1100 sessions[6].get(),
1101 sessions[5].get(),
1102 };
David Benjamin0f653952015-10-18 14:28:01 -04001103 if (!ExpectCache(ctx.get(), expected)) {
1104 return false;
1105 }
1106
1107 // Inserting an element already in the cache should fail.
David Benjamin4f6acaf2015-11-21 03:00:50 -05001108 if (SSL_CTX_add_session(ctx.get(), sessions[7].get()) ||
David Benjamin0f653952015-10-18 14:28:01 -04001109 !ExpectCache(ctx.get(), expected)) {
1110 return false;
1111 }
1112
1113 // Although collisions should be impossible (256-bit session IDs), the cache
1114 // must handle them gracefully.
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001115 bssl::UniquePtr<SSL_SESSION> collision(CreateTestSession(7));
David Benjamin0f653952015-10-18 14:28:01 -04001116 if (!collision || !SSL_CTX_add_session(ctx.get(), collision.get())) {
1117 return false;
1118 }
David Benjamin4f6acaf2015-11-21 03:00:50 -05001119 expected = {
1120 collision.get(),
1121 sessions[9].get(),
1122 sessions[8].get(),
1123 sessions[6].get(),
1124 sessions[5].get(),
1125 };
David Benjamin0f653952015-10-18 14:28:01 -04001126 if (!ExpectCache(ctx.get(), expected)) {
1127 return false;
1128 }
1129
1130 // Removing sessions behaves correctly.
David Benjamin4f6acaf2015-11-21 03:00:50 -05001131 if (!SSL_CTX_remove_session(ctx.get(), sessions[6].get())) {
David Benjamin0f653952015-10-18 14:28:01 -04001132 return false;
1133 }
David Benjamin4f6acaf2015-11-21 03:00:50 -05001134 expected = {
1135 collision.get(),
1136 sessions[9].get(),
1137 sessions[8].get(),
1138 sessions[5].get(),
1139 };
David Benjamin0f653952015-10-18 14:28:01 -04001140 if (!ExpectCache(ctx.get(), expected)) {
1141 return false;
1142 }
1143
1144 // Removing sessions requires an exact match.
David Benjamin4f6acaf2015-11-21 03:00:50 -05001145 if (SSL_CTX_remove_session(ctx.get(), sessions[0].get()) ||
1146 SSL_CTX_remove_session(ctx.get(), sessions[7].get()) ||
David Benjamin0f653952015-10-18 14:28:01 -04001147 !ExpectCache(ctx.get(), expected)) {
1148 return false;
1149 }
1150
1151 return true;
1152}
1153
David Benjaminde942382016-02-11 12:02:01 -05001154static uint16_t EpochFromSequence(uint64_t seq) {
1155 return static_cast<uint16_t>(seq >> 48);
1156}
1157
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001158static bssl::UniquePtr<X509> GetTestCertificate() {
David Benjaminde942382016-02-11 12:02:01 -05001159 static const char kCertPEM[] =
1160 "-----BEGIN CERTIFICATE-----\n"
1161 "MIICWDCCAcGgAwIBAgIJAPuwTC6rEJsMMA0GCSqGSIb3DQEBBQUAMEUxCzAJBgNV\n"
1162 "BAYTAkFVMRMwEQYDVQQIDApTb21lLVN0YXRlMSEwHwYDVQQKDBhJbnRlcm5ldCBX\n"
1163 "aWRnaXRzIFB0eSBMdGQwHhcNMTQwNDIzMjA1MDQwWhcNMTcwNDIyMjA1MDQwWjBF\n"
1164 "MQswCQYDVQQGEwJBVTETMBEGA1UECAwKU29tZS1TdGF0ZTEhMB8GA1UECgwYSW50\n"
1165 "ZXJuZXQgV2lkZ2l0cyBQdHkgTHRkMIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKB\n"
1166 "gQDYK8imMuRi/03z0K1Zi0WnvfFHvwlYeyK9Na6XJYaUoIDAtB92kWdGMdAQhLci\n"
1167 "HnAjkXLI6W15OoV3gA/ElRZ1xUpxTMhjP6PyY5wqT5r6y8FxbiiFKKAnHmUcrgfV\n"
1168 "W28tQ+0rkLGMryRtrukXOgXBv7gcrmU7G1jC2a7WqmeI8QIDAQABo1AwTjAdBgNV\n"
1169 "HQ4EFgQUi3XVrMsIvg4fZbf6Vr5sp3Xaha8wHwYDVR0jBBgwFoAUi3XVrMsIvg4f\n"
1170 "Zbf6Vr5sp3Xaha8wDAYDVR0TBAUwAwEB/zANBgkqhkiG9w0BAQUFAAOBgQA76Hht\n"
1171 "ldY9avcTGSwbwoiuIqv0jTL1fHFnzy3RHMLDh+Lpvolc5DSrSJHCP5WuK0eeJXhr\n"
1172 "T5oQpHL9z/cCDLAKCKRa4uV0fhEdOWBqyR9p8y5jJtye72t6CuFUV5iqcpF4BH4f\n"
1173 "j2VNHwsSrJwkD4QUGlUtH7vwnQmyCFxZMmWAJg==\n"
1174 "-----END CERTIFICATE-----\n";
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001175 bssl::UniquePtr<BIO> bio(BIO_new_mem_buf(kCertPEM, strlen(kCertPEM)));
David Benjamin1444c3a2016-12-20 17:23:11 -05001176 return bssl::UniquePtr<X509>(
1177 PEM_read_bio_X509(bio.get(), nullptr, nullptr, nullptr));
David Benjaminde942382016-02-11 12:02:01 -05001178}
1179
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001180static bssl::UniquePtr<EVP_PKEY> GetTestKey() {
David Benjaminde942382016-02-11 12:02:01 -05001181 static const char kKeyPEM[] =
1182 "-----BEGIN RSA PRIVATE KEY-----\n"
1183 "MIICXgIBAAKBgQDYK8imMuRi/03z0K1Zi0WnvfFHvwlYeyK9Na6XJYaUoIDAtB92\n"
1184 "kWdGMdAQhLciHnAjkXLI6W15OoV3gA/ElRZ1xUpxTMhjP6PyY5wqT5r6y8FxbiiF\n"
1185 "KKAnHmUcrgfVW28tQ+0rkLGMryRtrukXOgXBv7gcrmU7G1jC2a7WqmeI8QIDAQAB\n"
1186 "AoGBAIBy09Fd4DOq/Ijp8HeKuCMKTHqTW1xGHshLQ6jwVV2vWZIn9aIgmDsvkjCe\n"
1187 "i6ssZvnbjVcwzSoByhjN8ZCf/i15HECWDFFh6gt0P5z0MnChwzZmvatV/FXCT0j+\n"
1188 "WmGNB/gkehKjGXLLcjTb6dRYVJSCZhVuOLLcbWIV10gggJQBAkEA8S8sGe4ezyyZ\n"
1189 "m4e9r95g6s43kPqtj5rewTsUxt+2n4eVodD+ZUlCULWVNAFLkYRTBCASlSrm9Xhj\n"
1190 "QpmWAHJUkQJBAOVzQdFUaewLtdOJoPCtpYoY1zd22eae8TQEmpGOR11L6kbxLQsk\n"
1191 "aMly/DOnOaa82tqAGTdqDEZgSNmCeKKknmECQAvpnY8GUOVAubGR6c+W90iBuQLj\n"
1192 "LtFp/9ihd2w/PoDwrHZaoUYVcT4VSfJQog/k7kjE4MYXYWL8eEKg3WTWQNECQQDk\n"
1193 "104Wi91Umd1PzF0ijd2jXOERJU1wEKe6XLkYYNHWQAe5l4J4MWj9OdxFXAxIuuR/\n"
1194 "tfDwbqkta4xcux67//khAkEAvvRXLHTaa6VFzTaiiO8SaFsHV3lQyXOtMrBpB5jd\n"
1195 "moZWgjHvB2W9Ckn7sDqsPB+U2tyX0joDdQEyuiMECDY8oQ==\n"
1196 "-----END RSA PRIVATE KEY-----\n";
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001197 bssl::UniquePtr<BIO> bio(BIO_new_mem_buf(kKeyPEM, strlen(kKeyPEM)));
1198 return bssl::UniquePtr<EVP_PKEY>(
David Benjaminde942382016-02-11 12:02:01 -05001199 PEM_read_bio_PrivateKey(bio.get(), nullptr, nullptr, nullptr));
1200}
1201
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001202static bssl::UniquePtr<X509> GetECDSATestCertificate() {
David Benjamin0fc37ef2016-08-17 15:29:46 -04001203 static const char kCertPEM[] =
1204 "-----BEGIN CERTIFICATE-----\n"
1205 "MIIBzzCCAXagAwIBAgIJANlMBNpJfb/rMAkGByqGSM49BAEwRTELMAkGA1UEBhMC\n"
1206 "QVUxEzARBgNVBAgMClNvbWUtU3RhdGUxITAfBgNVBAoMGEludGVybmV0IFdpZGdp\n"
1207 "dHMgUHR5IEx0ZDAeFw0xNDA0MjMyMzIxNTdaFw0xNDA1MjMyMzIxNTdaMEUxCzAJ\n"
1208 "BgNVBAYTAkFVMRMwEQYDVQQIDApTb21lLVN0YXRlMSEwHwYDVQQKDBhJbnRlcm5l\n"
1209 "dCBXaWRnaXRzIFB0eSBMdGQwWTATBgcqhkjOPQIBBggqhkjOPQMBBwNCAATmK2ni\n"
1210 "v2Wfl74vHg2UikzVl2u3qR4NRvvdqakendy6WgHn1peoChj5w8SjHlbifINI2xYa\n"
1211 "HPUdfvGULUvPciLBo1AwTjAdBgNVHQ4EFgQUq4TSrKuV8IJOFngHVVdf5CaNgtEw\n"
1212 "HwYDVR0jBBgwFoAUq4TSrKuV8IJOFngHVVdf5CaNgtEwDAYDVR0TBAUwAwEB/zAJ\n"
1213 "BgcqhkjOPQQBA0gAMEUCIQDyoDVeUTo2w4J5m+4nUIWOcAZ0lVfSKXQA9L4Vh13E\n"
1214 "BwIgfB55FGohg/B6dGh5XxSZmmi08cueFV7mHzJSYV51yRQ=\n"
1215 "-----END CERTIFICATE-----\n";
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001216 bssl::UniquePtr<BIO> bio(BIO_new_mem_buf(kCertPEM, strlen(kCertPEM)));
1217 return bssl::UniquePtr<X509>(PEM_read_bio_X509(bio.get(), nullptr, nullptr, nullptr));
David Benjamin0fc37ef2016-08-17 15:29:46 -04001218}
1219
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001220static bssl::UniquePtr<EVP_PKEY> GetECDSATestKey() {
David Benjamin0fc37ef2016-08-17 15:29:46 -04001221 static const char kKeyPEM[] =
1222 "-----BEGIN PRIVATE KEY-----\n"
1223 "MIGHAgEAMBMGByqGSM49AgEGCCqGSM49AwEHBG0wawIBAQQgBw8IcnrUoEqc3VnJ\n"
1224 "TYlodwi1b8ldMHcO6NHJzgqLtGqhRANCAATmK2niv2Wfl74vHg2UikzVl2u3qR4N\n"
1225 "Rvvdqakendy6WgHn1peoChj5w8SjHlbifINI2xYaHPUdfvGULUvPciLB\n"
1226 "-----END PRIVATE KEY-----\n";
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001227 bssl::UniquePtr<BIO> bio(BIO_new_mem_buf(kKeyPEM, strlen(kKeyPEM)));
1228 return bssl::UniquePtr<EVP_PKEY>(
David Benjamin0fc37ef2016-08-17 15:29:46 -04001229 PEM_read_bio_PrivateKey(bio.get(), nullptr, nullptr, nullptr));
1230}
1231
Adam Langleyd04ca952017-02-28 11:26:51 -08001232static bssl::UniquePtr<CRYPTO_BUFFER> BufferFromPEM(const char *pem) {
1233 bssl::UniquePtr<BIO> bio(BIO_new_mem_buf(pem, strlen(pem)));
1234 char *name, *header;
1235 uint8_t *data;
1236 long data_len;
1237 if (!PEM_read_bio(bio.get(), &name, &header, &data,
1238 &data_len)) {
1239 return nullptr;
1240 }
1241 OPENSSL_free(name);
1242 OPENSSL_free(header);
1243
1244 auto ret = bssl::UniquePtr<CRYPTO_BUFFER>(
1245 CRYPTO_BUFFER_new(data, data_len, nullptr));
1246 OPENSSL_free(data);
1247 return ret;
1248}
1249
1250static bssl::UniquePtr<CRYPTO_BUFFER> GetChainTestCertificateBuffer() {
David Benjamin1444c3a2016-12-20 17:23:11 -05001251 static const char kCertPEM[] =
1252 "-----BEGIN CERTIFICATE-----\n"
1253 "MIIC0jCCAbqgAwIBAgICEAAwDQYJKoZIhvcNAQELBQAwDzENMAsGA1UEAwwEQiBD\n"
1254 "QTAeFw0xNjAyMjgyMDI3MDNaFw0yNjAyMjUyMDI3MDNaMBgxFjAUBgNVBAMMDUNs\n"
1255 "aWVudCBDZXJ0IEEwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDRvaz8\n"
1256 "CC/cshpCafJo4jLkHEoBqDLhdgFelJoAiQUyIqyWl2O7YHPnpJH+TgR7oelzNzt/\n"
1257 "kLRcH89M/TszB6zqyLTC4aqmvzKL0peD/jL2LWBucR0WXIvjA3zoRuF/x86+rYH3\n"
1258 "tHb+xs2PSs8EGL/Ev+ss+qTzTGEn26fuGNHkNw6tOwPpc+o8+wUtzf/kAthamo+c\n"
1259 "IDs2rQ+lP7+aLZTLeU/q4gcLutlzcK5imex5xy2jPkweq48kijK0kIzl1cPlA5d1\n"
1260 "z7C8jU50Pj9X9sQDJTN32j7UYRisJeeYQF8GaaN8SbrDI6zHgKzrRLyxDt/KQa9V\n"
1261 "iLeXANgZi+Xx9KgfAgMBAAGjLzAtMAwGA1UdEwEB/wQCMAAwHQYDVR0lBBYwFAYI\n"
1262 "KwYBBQUHAwEGCCsGAQUFBwMCMA0GCSqGSIb3DQEBCwUAA4IBAQBFEVbmYl+2RtNw\n"
1263 "rDftRDF1v2QUbcN2ouSnQDHxeDQdSgasLzT3ui8iYu0Rw2WWcZ0DV5e0ztGPhWq7\n"
1264 "AO0B120aFRMOY+4+bzu9Q2FFkQqc7/fKTvTDzIJI5wrMnFvUfzzvxh3OHWMYSs/w\n"
1265 "giq33hTKeHEq6Jyk3btCny0Ycecyc3yGXH10sizUfiHlhviCkDuESk8mFDwDDzqW\n"
1266 "ZF0IipzFbEDHoIxLlm3GQxpiLoEV4k8KYJp3R5KBLFyxM6UGPz8h72mIPCJp2RuK\n"
1267 "MYgF91UDvVzvnYm6TfseM2+ewKirC00GOrZ7rEcFvtxnKSqYf4ckqfNdSU1Y+RRC\n"
1268 "1ngWZ7Ih\n"
1269 "-----END CERTIFICATE-----\n";
Adam Langleyd04ca952017-02-28 11:26:51 -08001270 return BufferFromPEM(kCertPEM);
David Benjamin1444c3a2016-12-20 17:23:11 -05001271}
1272
Adam Langleyd04ca952017-02-28 11:26:51 -08001273static bssl::UniquePtr<X509> X509FromBuffer(
1274 bssl::UniquePtr<CRYPTO_BUFFER> buffer) {
1275 if (!buffer) {
1276 return nullptr;
1277 }
1278 const uint8_t *derp = CRYPTO_BUFFER_data(buffer.get());
1279 return bssl::UniquePtr<X509>(
1280 d2i_X509(NULL, &derp, CRYPTO_BUFFER_len(buffer.get())));
1281}
1282
1283static bssl::UniquePtr<X509> GetChainTestCertificate() {
1284 return X509FromBuffer(GetChainTestCertificateBuffer());
1285}
1286
1287static bssl::UniquePtr<CRYPTO_BUFFER> GetChainTestIntermediateBuffer() {
David Benjamin1444c3a2016-12-20 17:23:11 -05001288 static const char kCertPEM[] =
1289 "-----BEGIN CERTIFICATE-----\n"
1290 "MIICwjCCAaqgAwIBAgICEAEwDQYJKoZIhvcNAQELBQAwFDESMBAGA1UEAwwJQyBS\n"
1291 "b290IENBMB4XDTE2MDIyODIwMjcwM1oXDTI2MDIyNTIwMjcwM1owDzENMAsGA1UE\n"
1292 "AwwEQiBDQTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBALsSCYmDip2D\n"
1293 "GkjFxw7ykz26JSjELkl6ArlYjFJ3aT/SCh8qbS4gln7RH8CPBd78oFdfhIKQrwtZ\n"
1294 "3/q21ykD9BAS3qHe2YdcJfm8/kWAy5DvXk6NXU4qX334KofBAEpgdA/igEFq1P1l\n"
1295 "HAuIfZCpMRfT+i5WohVsGi8f/NgpRvVaMONLNfgw57mz1lbtFeBEISmX0kbsuJxF\n"
1296 "Qj/Bwhi5/0HAEXG8e7zN4cEx0yPRvmOATRdVb/8dW2pwOHRJq9R5M0NUkIsTSnL7\n"
1297 "6N/z8hRAHMsV3IudC5Yd7GXW1AGu9a+iKU+Q4xcZCoj0DC99tL4VKujrV1kAeqsM\n"
1298 "cz5/dKzi6+cCAwEAAaMjMCEwDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMC\n"
1299 "AQYwDQYJKoZIhvcNAQELBQADggEBAIIeZiEeNhWWQ8Y4D+AGDwqUUeG8NjCbKrXQ\n"
1300 "BlHg5wZ8xftFaiP1Dp/UAezmx2LNazdmuwrYB8lm3FVTyaPDTKEGIPS4wJKHgqH1\n"
1301 "QPDhqNm85ey7TEtI9oYjsNim/Rb+iGkIAMXaxt58SzxbjvP0kMr1JfJIZbic9vye\n"
1302 "NwIspMFIpP3FB8ywyu0T0hWtCQgL4J47nigCHpOu58deP88fS/Nyz/fyGVWOZ76b\n"
1303 "WhWwgM3P3X95fQ3d7oFPR/bVh0YV+Cf861INwplokXgXQ3/TCQ+HNXeAMWn3JLWv\n"
1304 "XFwk8owk9dq/kQGdndGgy3KTEW4ctPX5GNhf3LJ9Q7dLji4ReQ4=\n"
1305 "-----END CERTIFICATE-----\n";
Adam Langleyd04ca952017-02-28 11:26:51 -08001306 return BufferFromPEM(kCertPEM);
1307}
1308
1309static bssl::UniquePtr<X509> GetChainTestIntermediate() {
1310 return X509FromBuffer(GetChainTestIntermediateBuffer());
David Benjamin1444c3a2016-12-20 17:23:11 -05001311}
1312
1313static bssl::UniquePtr<EVP_PKEY> GetChainTestKey() {
1314 static const char kKeyPEM[] =
1315 "-----BEGIN PRIVATE KEY-----\n"
1316 "MIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQDRvaz8CC/cshpC\n"
1317 "afJo4jLkHEoBqDLhdgFelJoAiQUyIqyWl2O7YHPnpJH+TgR7oelzNzt/kLRcH89M\n"
1318 "/TszB6zqyLTC4aqmvzKL0peD/jL2LWBucR0WXIvjA3zoRuF/x86+rYH3tHb+xs2P\n"
1319 "Ss8EGL/Ev+ss+qTzTGEn26fuGNHkNw6tOwPpc+o8+wUtzf/kAthamo+cIDs2rQ+l\n"
1320 "P7+aLZTLeU/q4gcLutlzcK5imex5xy2jPkweq48kijK0kIzl1cPlA5d1z7C8jU50\n"
1321 "Pj9X9sQDJTN32j7UYRisJeeYQF8GaaN8SbrDI6zHgKzrRLyxDt/KQa9ViLeXANgZ\n"
1322 "i+Xx9KgfAgMBAAECggEBAK0VjSJzkyPaamcyTVSWjo7GdaBGcK60lk657RjR+lK0\n"
1323 "YJ7pkej4oM2hdsVZFsP8Cs4E33nXLa/0pDsRov/qrp0WQm2skwqGMC1I/bZ0WRPk\n"
1324 "wHaDrBBfESWnJDX/AGpVtlyOjPmgmK6J2usMPihQUDkKdAYrVWJePrMIxt1q6BMe\n"
1325 "iczs3qriMmtY3bUc4UyUwJ5fhDLjshHvfuIpYQyI6EXZM6dZksn9LylXJnigY6QJ\n"
1326 "HxOYO0BDwOsZ8yQ8J8afLk88i0GizEkgE1z3REtQUwgWfxr1WV/ud+T6/ZhSAgH9\n"
1327 "042mQvSFZnIUSEsmCvjhWuAunfxHKCTcAoYISWfzWpkCgYEA7gpf3HHU5Tn+CgUn\n"
1328 "1X5uGpG3DmcMgfeGgs2r2f/IIg/5Ac1dfYILiybL1tN9zbyLCJfcbFpWBc9hJL6f\n"
1329 "CPc5hUiwWFJqBJewxQkC1Ae/HakHbip+IZ+Jr0842O4BAArvixk4Lb7/N2Ct9sTE\n"
1330 "NJO6RtK9lbEZ5uK61DglHy8CS2UCgYEA4ZC1o36kPAMQBggajgnucb2yuUEelk0f\n"
1331 "AEr+GI32MGE+93xMr7rAhBoqLg4AITyIfEnOSQ5HwagnIHonBbv1LV/Gf9ursx8Z\n"
1332 "YOGbvT8zzzC+SU1bkDzdjAYnFQVGIjMtKOBJ3K07++ypwX1fr4QsQ8uKL8WSOWwt\n"
1333 "Z3Bym6XiZzMCgYADnhy+2OwHX85AkLt+PyGlPbmuelpyTzS4IDAQbBa6jcuW/2wA\n"
1334 "UE2km75VUXmD+u2R/9zVuLm99NzhFhSMqlUxdV1YukfqMfP5yp1EY6m/5aW7QuIP\n"
1335 "2MDa7TVL9rIFMiVZ09RKvbBbQxjhuzPQKL6X/PPspnhiTefQ+dl2k9xREQKBgHDS\n"
1336 "fMfGNEeAEKezrfSVqxphE9/tXms3L+ZpnCaT+yu/uEr5dTIAawKoQ6i9f/sf1/Sy\n"
1337 "xedsqR+IB+oKrzIDDWMgoJybN4pkZ8E5lzhVQIjFjKgFdWLzzqyW9z1gYfABQPlN\n"
1338 "FiS20WX0vgP1vcKAjdNrHzc9zyHBpgQzDmAj3NZZAoGBAI8vKCKdH7w3aL5CNkZQ\n"
1339 "2buIeWNA2HZazVwAGG5F2TU/LmXfRKnG6dX5bkU+AkBZh56jNZy//hfFSewJB4Kk\n"
1340 "buB7ERSdaNbO21zXt9FEA3+z0RfMd/Zv2vlIWOSB5nzl/7UKti3sribK6s9ZVLfi\n"
1341 "SxpiPQ8d/hmSGwn4ksrWUsJD\n"
1342 "-----END PRIVATE KEY-----\n";
1343 bssl::UniquePtr<BIO> bio(BIO_new_mem_buf(kKeyPEM, strlen(kKeyPEM)));
1344 return bssl::UniquePtr<EVP_PKEY>(
1345 PEM_read_bio_PrivateKey(bio.get(), nullptr, nullptr, nullptr));
1346}
1347
David Benjaminb79cc842016-12-07 15:57:14 -05001348static bool CompleteHandshakes(SSL *client, SSL *server) {
1349 // Drive both their handshakes to completion.
1350 for (;;) {
1351 int client_ret = SSL_do_handshake(client);
1352 int client_err = SSL_get_error(client, client_ret);
1353 if (client_err != SSL_ERROR_NONE &&
1354 client_err != SSL_ERROR_WANT_READ &&
Adam Langley4c341d02017-03-08 19:33:21 -08001355 client_err != SSL_ERROR_WANT_WRITE &&
1356 client_err != SSL_ERROR_PENDING_TICKET) {
David Benjaminb79cc842016-12-07 15:57:14 -05001357 fprintf(stderr, "Client error: %d\n", client_err);
1358 return false;
1359 }
1360
1361 int server_ret = SSL_do_handshake(server);
1362 int server_err = SSL_get_error(server, server_ret);
1363 if (server_err != SSL_ERROR_NONE &&
1364 server_err != SSL_ERROR_WANT_READ &&
Adam Langley4c341d02017-03-08 19:33:21 -08001365 server_err != SSL_ERROR_WANT_WRITE &&
1366 server_err != SSL_ERROR_PENDING_TICKET) {
David Benjaminb79cc842016-12-07 15:57:14 -05001367 fprintf(stderr, "Server error: %d\n", server_err);
1368 return false;
1369 }
1370
1371 if (client_ret == 1 && server_ret == 1) {
1372 break;
1373 }
1374 }
1375
1376 return true;
1377}
1378
1379static bool ConnectClientAndServer(bssl::UniquePtr<SSL> *out_client,
1380 bssl::UniquePtr<SSL> *out_server,
David Benjamina20e5352016-08-02 19:09:41 -04001381 SSL_CTX *client_ctx, SSL_CTX *server_ctx,
1382 SSL_SESSION *session) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001383 bssl::UniquePtr<SSL> client(SSL_new(client_ctx)), server(SSL_new(server_ctx));
David Benjaminde942382016-02-11 12:02:01 -05001384 if (!client || !server) {
1385 return false;
1386 }
1387 SSL_set_connect_state(client.get());
1388 SSL_set_accept_state(server.get());
1389
David Benjamina20e5352016-08-02 19:09:41 -04001390 SSL_set_session(client.get(), session);
1391
David Benjaminde942382016-02-11 12:02:01 -05001392 BIO *bio1, *bio2;
1393 if (!BIO_new_bio_pair(&bio1, 0, &bio2, 0)) {
1394 return false;
1395 }
1396 // SSL_set_bio takes ownership.
1397 SSL_set_bio(client.get(), bio1, bio1);
1398 SSL_set_bio(server.get(), bio2, bio2);
1399
David Benjaminb79cc842016-12-07 15:57:14 -05001400 if (!CompleteHandshakes(client.get(), server.get())) {
1401 return false;
David Benjaminde942382016-02-11 12:02:01 -05001402 }
1403
David Benjamin686bb192016-05-10 15:15:41 -04001404 *out_client = std::move(client);
1405 *out_server = std::move(server);
1406 return true;
1407}
1408
David Benjamin0fef3052016-11-18 15:11:10 +09001409static bool TestSequenceNumber(bool is_dtls, const SSL_METHOD *method,
1410 uint16_t version) {
1411 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(method));
1412 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(method));
1413 if (!server_ctx || !client_ctx ||
1414 !SSL_CTX_set_min_proto_version(client_ctx.get(), version) ||
1415 !SSL_CTX_set_max_proto_version(client_ctx.get(), version) ||
1416 !SSL_CTX_set_min_proto_version(server_ctx.get(), version) ||
1417 !SSL_CTX_set_max_proto_version(server_ctx.get(), version)) {
1418 return false;
1419 }
David Benjamin686bb192016-05-10 15:15:41 -04001420
David Benjamin0fef3052016-11-18 15:11:10 +09001421 bssl::UniquePtr<X509> cert = GetTestCertificate();
1422 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
1423 if (!cert || !key || !SSL_CTX_use_certificate(server_ctx.get(), cert.get()) ||
1424 !SSL_CTX_use_PrivateKey(server_ctx.get(), key.get())) {
1425 return false;
1426 }
David Benjamin686bb192016-05-10 15:15:41 -04001427
David Benjamin0fef3052016-11-18 15:11:10 +09001428 bssl::UniquePtr<SSL> client, server;
1429 if (!ConnectClientAndServer(&client, &server, client_ctx.get(),
1430 server_ctx.get(), nullptr /* no session */)) {
1431 return false;
1432 }
David Benjamin686bb192016-05-10 15:15:41 -04001433
David Benjamin0fef3052016-11-18 15:11:10 +09001434 // Drain any post-handshake messages to ensure there are no unread records
1435 // on either end.
1436 uint8_t byte = 0;
1437 if (SSL_read(client.get(), &byte, 1) > 0 ||
1438 SSL_read(server.get(), &byte, 1) > 0) {
1439 fprintf(stderr, "Received unexpected data.\n");
1440 return false;
1441 }
David Benjaminde942382016-02-11 12:02:01 -05001442
David Benjamin0fef3052016-11-18 15:11:10 +09001443 uint64_t client_read_seq = SSL_get_read_sequence(client.get());
1444 uint64_t client_write_seq = SSL_get_write_sequence(client.get());
1445 uint64_t server_read_seq = SSL_get_read_sequence(server.get());
1446 uint64_t server_write_seq = SSL_get_write_sequence(server.get());
Steven Valdez2c62fe92016-10-14 12:08:12 -04001447
David Benjamin0fef3052016-11-18 15:11:10 +09001448 if (is_dtls) {
1449 // Both client and server must be at epoch 1.
1450 if (EpochFromSequence(client_read_seq) != 1 ||
1451 EpochFromSequence(client_write_seq) != 1 ||
1452 EpochFromSequence(server_read_seq) != 1 ||
1453 EpochFromSequence(server_write_seq) != 1) {
1454 fprintf(stderr, "Bad epochs.\n");
1455 return false;
David Benjaminde942382016-02-11 12:02:01 -05001456 }
David Benjamin0fef3052016-11-18 15:11:10 +09001457
1458 // The next record to be written should exceed the largest received.
1459 if (client_write_seq <= server_read_seq ||
1460 server_write_seq <= client_read_seq) {
1461 fprintf(stderr, "Inconsistent sequence numbers.\n");
1462 return false;
1463 }
1464 } else {
1465 // The next record to be written should equal the next to be received.
1466 if (client_write_seq != server_read_seq ||
1467 server_write_seq != client_read_seq) {
1468 fprintf(stderr, "Inconsistent sequence numbers.\n");
1469 return false;
1470 }
1471 }
1472
1473 // Send a record from client to server.
1474 if (SSL_write(client.get(), &byte, 1) != 1 ||
1475 SSL_read(server.get(), &byte, 1) != 1) {
1476 fprintf(stderr, "Could not send byte.\n");
1477 return false;
1478 }
1479
1480 // The client write and server read sequence numbers should have
1481 // incremented.
1482 if (client_write_seq + 1 != SSL_get_write_sequence(client.get()) ||
1483 server_read_seq + 1 != SSL_get_read_sequence(server.get())) {
1484 fprintf(stderr, "Sequence numbers did not increment.\n");
1485 return false;
David Benjaminde942382016-02-11 12:02:01 -05001486 }
1487
1488 return true;
1489}
1490
David Benjamin68f37b72016-11-18 15:14:42 +09001491static bool TestOneSidedShutdown(bool is_dtls, const SSL_METHOD *method,
1492 uint16_t version) {
1493 // SSL_shutdown is a no-op in DTLS.
1494 if (is_dtls) {
1495 return true;
David Benjamin686bb192016-05-10 15:15:41 -04001496 }
1497
David Benjamin68f37b72016-11-18 15:14:42 +09001498 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(method));
1499 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(method));
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001500 bssl::UniquePtr<X509> cert = GetTestCertificate();
1501 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
David Benjamin68f37b72016-11-18 15:14:42 +09001502 if (!client_ctx || !server_ctx || !cert || !key ||
1503 !SSL_CTX_set_min_proto_version(server_ctx.get(), version) ||
1504 !SSL_CTX_set_max_proto_version(server_ctx.get(), version) ||
1505 !SSL_CTX_set_min_proto_version(client_ctx.get(), version) ||
1506 !SSL_CTX_set_max_proto_version(client_ctx.get(), version) ||
David Benjamin686bb192016-05-10 15:15:41 -04001507 !SSL_CTX_use_certificate(server_ctx.get(), cert.get()) ||
1508 !SSL_CTX_use_PrivateKey(server_ctx.get(), key.get())) {
1509 return false;
1510 }
1511
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001512 bssl::UniquePtr<SSL> client, server;
David Benjamin686bb192016-05-10 15:15:41 -04001513 if (!ConnectClientAndServer(&client, &server, client_ctx.get(),
David Benjamina20e5352016-08-02 19:09:41 -04001514 server_ctx.get(), nullptr /* no session */)) {
David Benjamin686bb192016-05-10 15:15:41 -04001515 return false;
1516 }
1517
1518 // Shut down half the connection. SSL_shutdown will return 0 to signal only
1519 // one side has shut down.
1520 if (SSL_shutdown(client.get()) != 0) {
1521 fprintf(stderr, "Could not shutdown.\n");
1522 return false;
1523 }
1524
1525 // Reading from the server should consume the EOF.
1526 uint8_t byte;
1527 if (SSL_read(server.get(), &byte, 1) != 0 ||
1528 SSL_get_error(server.get(), 0) != SSL_ERROR_ZERO_RETURN) {
1529 fprintf(stderr, "Connection was not shut down cleanly.\n");
1530 return false;
1531 }
1532
1533 // However, the server may continue to write data and then shut down the
1534 // connection.
1535 byte = 42;
1536 if (SSL_write(server.get(), &byte, 1) != 1 ||
1537 SSL_read(client.get(), &byte, 1) != 1 ||
1538 byte != 42) {
1539 fprintf(stderr, "Could not send byte.\n");
1540 return false;
1541 }
1542
1543 // The server may then shutdown the connection.
1544 if (SSL_shutdown(server.get()) != 1 ||
1545 SSL_shutdown(client.get()) != 1) {
1546 fprintf(stderr, "Could not complete shutdown.\n");
1547 return false;
1548 }
1549
1550 return true;
1551}
David Benjamin68f37b72016-11-18 15:14:42 +09001552
David Benjaminf0d8e222017-02-04 10:58:26 -05001553TEST(SSLTest, SessionDuplication) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001554 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLS_method()));
1555 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(TLS_method()));
David Benjaminf0d8e222017-02-04 10:58:26 -05001556 ASSERT_TRUE(client_ctx);
1557 ASSERT_TRUE(server_ctx);
Steven Valdez87eab492016-06-27 16:34:59 -04001558
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001559 bssl::UniquePtr<X509> cert = GetTestCertificate();
1560 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
David Benjaminf0d8e222017-02-04 10:58:26 -05001561 ASSERT_TRUE(cert);
1562 ASSERT_TRUE(key);
1563 ASSERT_TRUE(SSL_CTX_use_certificate(server_ctx.get(), cert.get()));
1564 ASSERT_TRUE(SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()));
Steven Valdez87eab492016-06-27 16:34:59 -04001565
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001566 bssl::UniquePtr<SSL> client, server;
David Benjaminf0d8e222017-02-04 10:58:26 -05001567 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx.get(),
1568 server_ctx.get(),
1569 nullptr /* no session */));
Steven Valdez87eab492016-06-27 16:34:59 -04001570
1571 SSL_SESSION *session0 = SSL_get_session(client.get());
David Benjaminf0d8e222017-02-04 10:58:26 -05001572 bssl::UniquePtr<SSL_SESSION> session1(
1573 SSL_SESSION_dup(session0, SSL_SESSION_DUP_ALL));
1574 ASSERT_TRUE(session1);
David Benjamin4501bd52016-08-01 13:39:41 -04001575
Steven Valdez84b5c002016-08-25 16:30:58 -04001576 session1->not_resumable = 0;
1577
Steven Valdez87eab492016-06-27 16:34:59 -04001578 uint8_t *s0_bytes, *s1_bytes;
1579 size_t s0_len, s1_len;
1580
David Benjaminf0d8e222017-02-04 10:58:26 -05001581 ASSERT_TRUE(SSL_SESSION_to_bytes(session0, &s0_bytes, &s0_len));
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001582 bssl::UniquePtr<uint8_t> free_s0(s0_bytes);
Steven Valdez87eab492016-06-27 16:34:59 -04001583
David Benjaminf0d8e222017-02-04 10:58:26 -05001584 ASSERT_TRUE(SSL_SESSION_to_bytes(session1.get(), &s1_bytes, &s1_len));
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001585 bssl::UniquePtr<uint8_t> free_s1(s1_bytes);
Steven Valdez87eab492016-06-27 16:34:59 -04001586
David Benjamin7d7554b2017-02-04 11:48:59 -05001587 EXPECT_EQ(Bytes(s0_bytes, s0_len), Bytes(s1_bytes, s1_len));
Steven Valdez87eab492016-06-27 16:34:59 -04001588}
David Benjamin686bb192016-05-10 15:15:41 -04001589
David Benjaminf0d8e222017-02-04 10:58:26 -05001590static void ExpectFDs(const SSL *ssl, int rfd, int wfd) {
1591 EXPECT_EQ(rfd, SSL_get_rfd(ssl));
1592 EXPECT_EQ(wfd, SSL_get_wfd(ssl));
David Benjamin5c0fb882016-06-14 14:03:51 -04001593
1594 // The wrapper BIOs are always equal when fds are equal, even if set
1595 // individually.
David Benjaminf0d8e222017-02-04 10:58:26 -05001596 if (rfd == wfd) {
1597 EXPECT_EQ(SSL_get_rbio(ssl), SSL_get_wbio(ssl));
David Benjamin5c0fb882016-06-14 14:03:51 -04001598 }
David Benjamin5c0fb882016-06-14 14:03:51 -04001599}
1600
David Benjaminf0d8e222017-02-04 10:58:26 -05001601TEST(SSLTest, SetFD) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001602 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
David Benjaminf0d8e222017-02-04 10:58:26 -05001603 ASSERT_TRUE(ctx);
David Benjamin5c0fb882016-06-14 14:03:51 -04001604
1605 // Test setting different read and write FDs.
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001606 bssl::UniquePtr<SSL> ssl(SSL_new(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05001607 ASSERT_TRUE(ssl);
1608 EXPECT_TRUE(SSL_set_rfd(ssl.get(), 1));
1609 EXPECT_TRUE(SSL_set_wfd(ssl.get(), 2));
1610 ExpectFDs(ssl.get(), 1, 2);
David Benjamin5c0fb882016-06-14 14:03:51 -04001611
1612 // Test setting the same FD.
1613 ssl.reset(SSL_new(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05001614 ASSERT_TRUE(ssl);
1615 EXPECT_TRUE(SSL_set_fd(ssl.get(), 1));
1616 ExpectFDs(ssl.get(), 1, 1);
David Benjamin5c0fb882016-06-14 14:03:51 -04001617
1618 // Test setting the same FD one side at a time.
1619 ssl.reset(SSL_new(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05001620 ASSERT_TRUE(ssl);
1621 EXPECT_TRUE(SSL_set_rfd(ssl.get(), 1));
1622 EXPECT_TRUE(SSL_set_wfd(ssl.get(), 1));
1623 ExpectFDs(ssl.get(), 1, 1);
David Benjamin5c0fb882016-06-14 14:03:51 -04001624
1625 // Test setting the same FD in the other order.
1626 ssl.reset(SSL_new(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05001627 ASSERT_TRUE(ssl);
1628 EXPECT_TRUE(SSL_set_wfd(ssl.get(), 1));
1629 EXPECT_TRUE(SSL_set_rfd(ssl.get(), 1));
1630 ExpectFDs(ssl.get(), 1, 1);
David Benjamin5c0fb882016-06-14 14:03:51 -04001631
David Benjamin5c0fb882016-06-14 14:03:51 -04001632 // Test changing the read FD partway through.
1633 ssl.reset(SSL_new(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05001634 ASSERT_TRUE(ssl);
1635 EXPECT_TRUE(SSL_set_fd(ssl.get(), 1));
1636 EXPECT_TRUE(SSL_set_rfd(ssl.get(), 2));
1637 ExpectFDs(ssl.get(), 2, 1);
David Benjamin5c0fb882016-06-14 14:03:51 -04001638
1639 // Test changing the write FD partway through.
1640 ssl.reset(SSL_new(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05001641 ASSERT_TRUE(ssl);
1642 EXPECT_TRUE(SSL_set_fd(ssl.get(), 1));
1643 EXPECT_TRUE(SSL_set_wfd(ssl.get(), 2));
1644 ExpectFDs(ssl.get(), 1, 2);
David Benjamin5c0fb882016-06-14 14:03:51 -04001645
1646 // Test a no-op change to the read FD partway through.
1647 ssl.reset(SSL_new(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05001648 ASSERT_TRUE(ssl);
1649 EXPECT_TRUE(SSL_set_fd(ssl.get(), 1));
1650 EXPECT_TRUE(SSL_set_rfd(ssl.get(), 1));
1651 ExpectFDs(ssl.get(), 1, 1);
David Benjamin5c0fb882016-06-14 14:03:51 -04001652
1653 // Test a no-op change to the write FD partway through.
1654 ssl.reset(SSL_new(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05001655 ASSERT_TRUE(ssl);
1656 EXPECT_TRUE(SSL_set_fd(ssl.get(), 1));
1657 EXPECT_TRUE(SSL_set_wfd(ssl.get(), 1));
1658 ExpectFDs(ssl.get(), 1, 1);
David Benjamin5c0fb882016-06-14 14:03:51 -04001659
1660 // ASan builds will implicitly test that the internal |BIO| reference-counting
1661 // is correct.
David Benjamin5c0fb882016-06-14 14:03:51 -04001662}
1663
David Benjaminf0d8e222017-02-04 10:58:26 -05001664TEST(SSLTest, SetBIO) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001665 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
David Benjaminf0d8e222017-02-04 10:58:26 -05001666 ASSERT_TRUE(ctx);
David Benjamin4501bd52016-08-01 13:39:41 -04001667
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001668 bssl::UniquePtr<SSL> ssl(SSL_new(ctx.get()));
1669 bssl::UniquePtr<BIO> bio1(BIO_new(BIO_s_mem())), bio2(BIO_new(BIO_s_mem())),
David Benjamin4501bd52016-08-01 13:39:41 -04001670 bio3(BIO_new(BIO_s_mem()));
David Benjaminf0d8e222017-02-04 10:58:26 -05001671 ASSERT_TRUE(ssl);
1672 ASSERT_TRUE(bio1);
1673 ASSERT_TRUE(bio2);
1674 ASSERT_TRUE(bio3);
David Benjamin4501bd52016-08-01 13:39:41 -04001675
1676 // SSL_set_bio takes one reference when the parameters are the same.
1677 BIO_up_ref(bio1.get());
1678 SSL_set_bio(ssl.get(), bio1.get(), bio1.get());
1679
1680 // Repeating the call does nothing.
1681 SSL_set_bio(ssl.get(), bio1.get(), bio1.get());
1682
1683 // It takes one reference each when the parameters are different.
1684 BIO_up_ref(bio2.get());
1685 BIO_up_ref(bio3.get());
1686 SSL_set_bio(ssl.get(), bio2.get(), bio3.get());
1687
1688 // Repeating the call does nothing.
1689 SSL_set_bio(ssl.get(), bio2.get(), bio3.get());
1690
1691 // It takes one reference when changing only wbio.
1692 BIO_up_ref(bio1.get());
1693 SSL_set_bio(ssl.get(), bio2.get(), bio1.get());
1694
1695 // It takes one reference when changing only rbio and the two are different.
1696 BIO_up_ref(bio3.get());
1697 SSL_set_bio(ssl.get(), bio3.get(), bio1.get());
1698
1699 // If setting wbio to rbio, it takes no additional references.
1700 SSL_set_bio(ssl.get(), bio3.get(), bio3.get());
1701
1702 // From there, wbio may be switched to something else.
1703 BIO_up_ref(bio1.get());
1704 SSL_set_bio(ssl.get(), bio3.get(), bio1.get());
1705
1706 // If setting rbio to wbio, it takes no additional references.
1707 SSL_set_bio(ssl.get(), bio1.get(), bio1.get());
1708
1709 // From there, rbio may be switched to something else, but, for historical
1710 // reasons, it takes a reference to both parameters.
1711 BIO_up_ref(bio1.get());
1712 BIO_up_ref(bio2.get());
1713 SSL_set_bio(ssl.get(), bio2.get(), bio1.get());
1714
1715 // ASAN builds will implicitly test that the internal |BIO| reference-counting
1716 // is correct.
David Benjamin4501bd52016-08-01 13:39:41 -04001717}
1718
David Benjamin25490f22016-07-14 00:22:54 -04001719static int VerifySucceed(X509_STORE_CTX *store_ctx, void *arg) { return 1; }
1720
David Benjamin0fef3052016-11-18 15:11:10 +09001721static bool TestGetPeerCertificate(bool is_dtls, const SSL_METHOD *method,
1722 uint16_t version) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001723 bssl::UniquePtr<X509> cert = GetTestCertificate();
1724 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
David Benjaminadd5e522016-07-14 00:33:24 -04001725 if (!cert || !key) {
1726 return false;
1727 }
1728
David Benjamin0fef3052016-11-18 15:11:10 +09001729 // Configure both client and server to accept any certificate.
1730 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(method));
1731 if (!ctx ||
1732 !SSL_CTX_use_certificate(ctx.get(), cert.get()) ||
1733 !SSL_CTX_use_PrivateKey(ctx.get(), key.get()) ||
1734 !SSL_CTX_set_min_proto_version(ctx.get(), version) ||
1735 !SSL_CTX_set_max_proto_version(ctx.get(), version)) {
1736 return false;
1737 }
1738 SSL_CTX_set_verify(
1739 ctx.get(), SSL_VERIFY_PEER | SSL_VERIFY_FAIL_IF_NO_PEER_CERT, nullptr);
1740 SSL_CTX_set_cert_verify_callback(ctx.get(), VerifySucceed, NULL);
David Benjaminadd5e522016-07-14 00:33:24 -04001741
David Benjamin0fef3052016-11-18 15:11:10 +09001742 bssl::UniquePtr<SSL> client, server;
1743 if (!ConnectClientAndServer(&client, &server, ctx.get(), ctx.get(),
1744 nullptr /* no session */)) {
1745 return false;
1746 }
David Benjaminadd5e522016-07-14 00:33:24 -04001747
David Benjamin0fef3052016-11-18 15:11:10 +09001748 // Client and server should both see the leaf certificate.
1749 bssl::UniquePtr<X509> peer(SSL_get_peer_certificate(server.get()));
1750 if (!peer || X509_cmp(cert.get(), peer.get()) != 0) {
1751 fprintf(stderr, "Server peer certificate did not match.\n");
1752 return false;
1753 }
David Benjaminadd5e522016-07-14 00:33:24 -04001754
David Benjamin0fef3052016-11-18 15:11:10 +09001755 peer.reset(SSL_get_peer_certificate(client.get()));
1756 if (!peer || X509_cmp(cert.get(), peer.get()) != 0) {
1757 fprintf(stderr, "Client peer certificate did not match.\n");
1758 return false;
1759 }
David Benjaminadd5e522016-07-14 00:33:24 -04001760
David Benjamin0fef3052016-11-18 15:11:10 +09001761 // However, for historical reasons, the chain includes the leaf on the
1762 // client, but does not on the server.
1763 if (sk_X509_num(SSL_get_peer_cert_chain(client.get())) != 1) {
1764 fprintf(stderr, "Client peer chain was incorrect.\n");
1765 return false;
1766 }
David Benjaminadd5e522016-07-14 00:33:24 -04001767
David Benjamin0fef3052016-11-18 15:11:10 +09001768 if (sk_X509_num(SSL_get_peer_cert_chain(server.get())) != 0) {
1769 fprintf(stderr, "Server peer chain was incorrect.\n");
1770 return false;
David Benjaminadd5e522016-07-14 00:33:24 -04001771 }
1772
1773 return true;
1774}
1775
David Benjamin0fef3052016-11-18 15:11:10 +09001776static bool TestRetainOnlySHA256OfCerts(bool is_dtls, const SSL_METHOD *method,
1777 uint16_t version) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001778 bssl::UniquePtr<X509> cert = GetTestCertificate();
1779 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
David Benjamin25490f22016-07-14 00:22:54 -04001780 if (!cert || !key) {
1781 return false;
1782 }
1783
1784 uint8_t *cert_der = NULL;
1785 int cert_der_len = i2d_X509(cert.get(), &cert_der);
1786 if (cert_der_len < 0) {
1787 return false;
1788 }
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001789 bssl::UniquePtr<uint8_t> free_cert_der(cert_der);
David Benjamin25490f22016-07-14 00:22:54 -04001790
1791 uint8_t cert_sha256[SHA256_DIGEST_LENGTH];
1792 SHA256(cert_der, cert_der_len, cert_sha256);
1793
David Benjamin0fef3052016-11-18 15:11:10 +09001794 // Configure both client and server to accept any certificate, but the
1795 // server must retain only the SHA-256 of the peer.
1796 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(method));
1797 if (!ctx ||
1798 !SSL_CTX_use_certificate(ctx.get(), cert.get()) ||
1799 !SSL_CTX_use_PrivateKey(ctx.get(), key.get()) ||
1800 !SSL_CTX_set_min_proto_version(ctx.get(), version) ||
1801 !SSL_CTX_set_max_proto_version(ctx.get(), version)) {
1802 return false;
1803 }
1804 SSL_CTX_set_verify(
1805 ctx.get(), SSL_VERIFY_PEER | SSL_VERIFY_FAIL_IF_NO_PEER_CERT, nullptr);
1806 SSL_CTX_set_cert_verify_callback(ctx.get(), VerifySucceed, NULL);
1807 SSL_CTX_set_retain_only_sha256_of_client_certs(ctx.get(), 1);
David Benjamin25490f22016-07-14 00:22:54 -04001808
David Benjamin0fef3052016-11-18 15:11:10 +09001809 bssl::UniquePtr<SSL> client, server;
1810 if (!ConnectClientAndServer(&client, &server, ctx.get(), ctx.get(),
1811 nullptr /* no session */)) {
1812 return false;
1813 }
David Benjamin25490f22016-07-14 00:22:54 -04001814
David Benjamin0fef3052016-11-18 15:11:10 +09001815 // The peer certificate has been dropped.
1816 bssl::UniquePtr<X509> peer(SSL_get_peer_certificate(server.get()));
1817 if (peer) {
1818 fprintf(stderr, "Peer certificate was retained.\n");
1819 return false;
1820 }
David Benjamin25490f22016-07-14 00:22:54 -04001821
David Benjamin0fef3052016-11-18 15:11:10 +09001822 SSL_SESSION *session = SSL_get_session(server.get());
1823 if (!session->peer_sha256_valid) {
1824 fprintf(stderr, "peer_sha256_valid was not set.\n");
1825 return false;
1826 }
David Benjamin25490f22016-07-14 00:22:54 -04001827
David Benjamin17cf2cb2016-12-13 01:07:13 -05001828 if (OPENSSL_memcmp(cert_sha256, session->peer_sha256, SHA256_DIGEST_LENGTH) !=
1829 0) {
David Benjamin0fef3052016-11-18 15:11:10 +09001830 fprintf(stderr, "peer_sha256 did not match.\n");
1831 return false;
David Benjamin25490f22016-07-14 00:22:54 -04001832 }
1833
1834 return true;
1835}
1836
David Benjaminafc64de2016-07-19 17:12:41 +02001837static bool ClientHelloMatches(uint16_t version, const uint8_t *expected,
1838 size_t expected_len) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001839 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
David Benjamin2dc02042016-09-19 19:57:37 -04001840 if (!ctx ||
David Benjamine4706902016-09-20 15:12:23 -04001841 !SSL_CTX_set_max_proto_version(ctx.get(), version) ||
David Benjamin2dc02042016-09-19 19:57:37 -04001842 // Our default cipher list varies by CPU capabilities, so manually place
1843 // the ChaCha20 ciphers in front.
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -08001844 !SSL_CTX_set_strict_cipher_list(ctx.get(), "CHACHA20:ALL")) {
David Benjaminafc64de2016-07-19 17:12:41 +02001845 return false;
1846 }
David Benjamin2dc02042016-09-19 19:57:37 -04001847
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001848 bssl::UniquePtr<SSL> ssl(SSL_new(ctx.get()));
David Benjaminafc64de2016-07-19 17:12:41 +02001849 if (!ssl) {
1850 return false;
1851 }
1852 std::vector<uint8_t> client_hello;
1853 if (!GetClientHello(ssl.get(), &client_hello)) {
1854 return false;
1855 }
1856
1857 // Zero the client_random.
1858 constexpr size_t kRandomOffset = 1 + 2 + 2 + // record header
1859 1 + 3 + // handshake message header
1860 2; // client_version
1861 if (client_hello.size() < kRandomOffset + SSL3_RANDOM_SIZE) {
1862 fprintf(stderr, "ClientHello for version %04x too short.\n", version);
1863 return false;
1864 }
David Benjamin17cf2cb2016-12-13 01:07:13 -05001865 OPENSSL_memset(client_hello.data() + kRandomOffset, 0, SSL3_RANDOM_SIZE);
David Benjaminafc64de2016-07-19 17:12:41 +02001866
1867 if (client_hello.size() != expected_len ||
David Benjamin17cf2cb2016-12-13 01:07:13 -05001868 OPENSSL_memcmp(client_hello.data(), expected, expected_len) != 0) {
David Benjaminafc64de2016-07-19 17:12:41 +02001869 fprintf(stderr, "ClientHello for version %04x did not match:\n", version);
1870 fprintf(stderr, "Got:\n\t");
1871 for (size_t i = 0; i < client_hello.size(); i++) {
1872 fprintf(stderr, "0x%02x, ", client_hello[i]);
1873 }
1874 fprintf(stderr, "\nWanted:\n\t");
1875 for (size_t i = 0; i < expected_len; i++) {
1876 fprintf(stderr, "0x%02x, ", expected[i]);
1877 }
1878 fprintf(stderr, "\n");
1879 return false;
1880 }
1881
1882 return true;
1883}
1884
1885// Tests that our ClientHellos do not change unexpectedly.
1886static bool TestClientHello() {
1887 static const uint8_t kSSL3ClientHello[] = {
Matt Braithwaite9c8c4182016-08-24 14:36:54 -07001888 0x16,
1889 0x03, 0x00,
1890 0x00, 0x3f,
1891 0x01,
1892 0x00, 0x00, 0x3b,
1893 0x03, 0x00,
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, 0x14,
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,
1909 0x00, 0xff, 0x01, 0x00,
David Benjaminafc64de2016-07-19 17:12:41 +02001910 };
1911 if (!ClientHelloMatches(SSL3_VERSION, kSSL3ClientHello,
1912 sizeof(kSSL3ClientHello))) {
1913 return false;
1914 }
1915
1916 static const uint8_t kTLS1ClientHello[] = {
Matt Braithwaite9c8c4182016-08-24 14:36:54 -07001917 0x16,
1918 0x03, 0x01,
1919 0x00, 0x5e,
1920 0x01,
1921 0x00, 0x00, 0x5a,
1922 0x03, 0x01,
1923 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1924 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1925 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1926 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1927 0x00,
1928 0x00, 0x12,
1929 0xc0, 0x09,
1930 0xc0, 0x13,
1931 0x00, 0x33,
1932 0xc0, 0x0a,
1933 0xc0, 0x14,
1934 0x00, 0x39,
1935 0x00, 0x2f,
1936 0x00, 0x35,
1937 0x00, 0x0a,
David Benjaminafc64de2016-07-19 17:12:41 +02001938 0x01, 0x00, 0x00, 0x1f, 0xff, 0x01, 0x00, 0x01, 0x00, 0x00, 0x17, 0x00,
1939 0x00, 0x00, 0x23, 0x00, 0x00, 0x00, 0x0b, 0x00, 0x02, 0x01, 0x00, 0x00,
1940 0x0a, 0x00, 0x08, 0x00, 0x06, 0x00, 0x1d, 0x00, 0x17, 0x00, 0x18,
1941 };
1942 if (!ClientHelloMatches(TLS1_VERSION, kTLS1ClientHello,
1943 sizeof(kTLS1ClientHello))) {
1944 return false;
1945 }
1946
1947 static const uint8_t kTLS11ClientHello[] = {
Matt Braithwaite9c8c4182016-08-24 14:36:54 -07001948 0x16,
1949 0x03, 0x01,
1950 0x00, 0x5e,
1951 0x01,
1952 0x00, 0x00, 0x5a,
1953 0x03, 0x02,
1954 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1955 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1956 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1957 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1958 0x00,
1959 0x00, 0x12,
1960 0xc0, 0x09,
1961 0xc0, 0x13,
1962 0x00, 0x33,
1963 0xc0, 0x0a,
1964 0xc0, 0x14,
1965 0x00, 0x39,
1966 0x00, 0x2f,
1967 0x00, 0x35,
1968 0x00, 0x0a,
David Benjaminafc64de2016-07-19 17:12:41 +02001969 0x01, 0x00, 0x00, 0x1f, 0xff, 0x01, 0x00, 0x01, 0x00, 0x00, 0x17, 0x00,
1970 0x00, 0x00, 0x23, 0x00, 0x00, 0x00, 0x0b, 0x00, 0x02, 0x01, 0x00, 0x00,
1971 0x0a, 0x00, 0x08, 0x00, 0x06, 0x00, 0x1d, 0x00, 0x17, 0x00, 0x18,
1972 };
1973 if (!ClientHelloMatches(TLS1_1_VERSION, kTLS11ClientHello,
1974 sizeof(kTLS11ClientHello))) {
1975 return false;
1976 }
1977
David Benjamin3b584332017-01-24 22:47:18 -05001978 // kTLS12ClientHello assumes RSA-PSS, which is disabled for Android system
1979 // builds.
1980#if defined(BORINGSSL_ANDROID_SYSTEM)
1981 return true;
1982#endif
1983
David Benjaminafc64de2016-07-19 17:12:41 +02001984 static const uint8_t kTLS12ClientHello[] = {
Adam Langley2e839242017-01-19 15:12:44 -08001985 0x16, 0x03, 0x01, 0x00, 0x9a, 0x01, 0x00, 0x00, 0x96, 0x03, 0x03, 0x00,
David Benjamin57e929f2016-08-30 00:30:38 -04001986 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1987 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
Adam Langley2e839242017-01-19 15:12:44 -08001988 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x36, 0xcc, 0xa9,
1989 0xcc, 0xa8, 0xc0, 0x2b, 0xc0, 0x2f, 0x00, 0x9e, 0xc0, 0x2c, 0xc0, 0x30,
1990 0x00, 0x9f, 0xc0, 0x09, 0xc0, 0x23, 0xc0, 0x13, 0xc0, 0x27, 0x00, 0x33,
1991 0x00, 0x67, 0xc0, 0x0a, 0xc0, 0x24, 0xc0, 0x14, 0xc0, 0x28, 0x00, 0x39,
1992 0x00, 0x6b, 0x00, 0x9c, 0x00, 0x9d, 0x00, 0x2f, 0x00, 0x3c, 0x00, 0x35,
1993 0x00, 0x3d, 0x00, 0x0a, 0x01, 0x00, 0x00, 0x37, 0xff, 0x01, 0x00, 0x01,
1994 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x23, 0x00, 0x00, 0x00, 0x0d, 0x00,
1995 0x14, 0x00, 0x12, 0x04, 0x03, 0x08, 0x04, 0x04, 0x01, 0x05, 0x03, 0x08,
1996 0x05, 0x05, 0x01, 0x08, 0x06, 0x06, 0x01, 0x02, 0x01, 0x00, 0x0b, 0x00,
1997 0x02, 0x01, 0x00, 0x00, 0x0a, 0x00, 0x08, 0x00, 0x06, 0x00, 0x1d, 0x00,
1998 0x17, 0x00, 0x18,
David Benjaminafc64de2016-07-19 17:12:41 +02001999 };
2000 if (!ClientHelloMatches(TLS1_2_VERSION, kTLS12ClientHello,
2001 sizeof(kTLS12ClientHello))) {
2002 return false;
2003 }
2004
2005 // TODO(davidben): Add a change detector for TLS 1.3 once the spec and our
2006 // implementation has settled enough that it won't change.
2007
2008 return true;
2009}
2010
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002011static bssl::UniquePtr<SSL_SESSION> g_last_session;
David Benjamina20e5352016-08-02 19:09:41 -04002012
2013static int SaveLastSession(SSL *ssl, SSL_SESSION *session) {
2014 // Save the most recent session.
2015 g_last_session.reset(session);
2016 return 1;
2017}
2018
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002019static bssl::UniquePtr<SSL_SESSION> CreateClientSession(SSL_CTX *client_ctx,
David Benjamina20e5352016-08-02 19:09:41 -04002020 SSL_CTX *server_ctx) {
2021 g_last_session = nullptr;
2022 SSL_CTX_sess_set_new_cb(client_ctx, SaveLastSession);
2023
2024 // Connect client and server to get a session.
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002025 bssl::UniquePtr<SSL> client, server;
David Benjamina20e5352016-08-02 19:09:41 -04002026 if (!ConnectClientAndServer(&client, &server, client_ctx, server_ctx,
2027 nullptr /* no session */)) {
2028 fprintf(stderr, "Failed to connect client and server.\n");
2029 return nullptr;
2030 }
2031
2032 // Run the read loop to account for post-handshake tickets in TLS 1.3.
2033 SSL_read(client.get(), nullptr, 0);
2034
2035 SSL_CTX_sess_set_new_cb(client_ctx, nullptr);
2036
2037 if (!g_last_session) {
2038 fprintf(stderr, "Client did not receive a session.\n");
2039 return nullptr;
2040 }
2041 return std::move(g_last_session);
2042}
2043
2044static bool ExpectSessionReused(SSL_CTX *client_ctx, SSL_CTX *server_ctx,
2045 SSL_SESSION *session,
2046 bool reused) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002047 bssl::UniquePtr<SSL> client, server;
David Benjamina20e5352016-08-02 19:09:41 -04002048 if (!ConnectClientAndServer(&client, &server, client_ctx,
2049 server_ctx, session)) {
2050 fprintf(stderr, "Failed to connect client and server.\n");
2051 return false;
2052 }
2053
2054 if (SSL_session_reused(client.get()) != SSL_session_reused(server.get())) {
2055 fprintf(stderr, "Client and server were inconsistent.\n");
2056 return false;
2057 }
2058
2059 bool was_reused = !!SSL_session_reused(client.get());
2060 if (was_reused != reused) {
2061 fprintf(stderr, "Session was%s reused, but we expected the opposite.\n",
2062 was_reused ? "" : " not");
2063 return false;
2064 }
2065
2066 return true;
2067}
2068
David Benjamin3c51d9b2016-11-01 17:50:42 -04002069static bssl::UniquePtr<SSL_SESSION> ExpectSessionRenewed(SSL_CTX *client_ctx,
2070 SSL_CTX *server_ctx,
2071 SSL_SESSION *session) {
2072 g_last_session = nullptr;
2073 SSL_CTX_sess_set_new_cb(client_ctx, SaveLastSession);
2074
2075 bssl::UniquePtr<SSL> client, server;
2076 if (!ConnectClientAndServer(&client, &server, client_ctx,
2077 server_ctx, session)) {
2078 fprintf(stderr, "Failed to connect client and server.\n");
2079 return nullptr;
2080 }
2081
2082 if (SSL_session_reused(client.get()) != SSL_session_reused(server.get())) {
2083 fprintf(stderr, "Client and server were inconsistent.\n");
2084 return nullptr;
2085 }
2086
2087 if (!SSL_session_reused(client.get())) {
2088 fprintf(stderr, "Session was not reused.\n");
2089 return nullptr;
2090 }
2091
2092 // Run the read loop to account for post-handshake tickets in TLS 1.3.
2093 SSL_read(client.get(), nullptr, 0);
2094
2095 SSL_CTX_sess_set_new_cb(client_ctx, nullptr);
2096
2097 if (!g_last_session) {
2098 fprintf(stderr, "Client did not receive a renewed session.\n");
2099 return nullptr;
2100 }
2101 return std::move(g_last_session);
2102}
2103
David Benjamina933c382016-10-28 00:10:03 -04002104static int SwitchSessionIDContextSNI(SSL *ssl, int *out_alert, void *arg) {
2105 static const uint8_t kContext[] = {3};
2106
2107 if (!SSL_set_session_id_context(ssl, kContext, sizeof(kContext))) {
2108 return SSL_TLSEXT_ERR_ALERT_FATAL;
2109 }
2110
2111 return SSL_TLSEXT_ERR_OK;
2112}
2113
David Benjamin731058e2016-12-03 23:15:13 -05002114static int SwitchSessionIDContextEarly(const SSL_CLIENT_HELLO *client_hello) {
David Benjamina933c382016-10-28 00:10:03 -04002115 static const uint8_t kContext[] = {3};
2116
David Benjamin731058e2016-12-03 23:15:13 -05002117 if (!SSL_set_session_id_context(client_hello->ssl, kContext,
2118 sizeof(kContext))) {
David Benjamina933c382016-10-28 00:10:03 -04002119 return -1;
2120 }
2121
2122 return 1;
2123}
2124
David Benjamin0fef3052016-11-18 15:11:10 +09002125static bool TestSessionIDContext(bool is_dtls, const SSL_METHOD *method,
2126 uint16_t version) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002127 bssl::UniquePtr<X509> cert = GetTestCertificate();
2128 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
David Benjamina20e5352016-08-02 19:09:41 -04002129 if (!cert || !key) {
2130 return false;
2131 }
2132
2133 static const uint8_t kContext1[] = {1};
2134 static const uint8_t kContext2[] = {2};
2135
David Benjamin0fef3052016-11-18 15:11:10 +09002136 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(method));
2137 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(method));
2138 if (!server_ctx || !client_ctx ||
2139 !SSL_CTX_use_certificate(server_ctx.get(), cert.get()) ||
2140 !SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()) ||
2141 !SSL_CTX_set_session_id_context(server_ctx.get(), kContext1,
2142 sizeof(kContext1)) ||
2143 !SSL_CTX_set_min_proto_version(client_ctx.get(), version) ||
2144 !SSL_CTX_set_max_proto_version(client_ctx.get(), version) ||
2145 !SSL_CTX_set_min_proto_version(server_ctx.get(), version) ||
2146 !SSL_CTX_set_max_proto_version(server_ctx.get(), version)) {
2147 return false;
2148 }
David Benjamina20e5352016-08-02 19:09:41 -04002149
David Benjamin0fef3052016-11-18 15:11:10 +09002150 SSL_CTX_set_session_cache_mode(client_ctx.get(), SSL_SESS_CACHE_BOTH);
2151 SSL_CTX_set_session_cache_mode(server_ctx.get(), SSL_SESS_CACHE_BOTH);
David Benjamina20e5352016-08-02 19:09:41 -04002152
David Benjamin0fef3052016-11-18 15:11:10 +09002153 bssl::UniquePtr<SSL_SESSION> session =
2154 CreateClientSession(client_ctx.get(), server_ctx.get());
2155 if (!session) {
2156 fprintf(stderr, "Error getting session.\n");
2157 return false;
2158 }
David Benjamina20e5352016-08-02 19:09:41 -04002159
David Benjamin0fef3052016-11-18 15:11:10 +09002160 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(), session.get(),
2161 true /* expect session reused */)) {
2162 fprintf(stderr, "Error resuming session.\n");
2163 return false;
2164 }
David Benjamina20e5352016-08-02 19:09:41 -04002165
David Benjamin0fef3052016-11-18 15:11:10 +09002166 // Change the session ID context.
2167 if (!SSL_CTX_set_session_id_context(server_ctx.get(), kContext2,
2168 sizeof(kContext2))) {
2169 return false;
2170 }
David Benjamina20e5352016-08-02 19:09:41 -04002171
David Benjamin0fef3052016-11-18 15:11:10 +09002172 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(), session.get(),
2173 false /* expect session not reused */)) {
2174 fprintf(stderr, "Error connecting with a different context.\n");
2175 return false;
2176 }
David Benjamina933c382016-10-28 00:10:03 -04002177
David Benjamin0fef3052016-11-18 15:11:10 +09002178 // Change the session ID context back and install an SNI callback to switch
2179 // it.
2180 if (!SSL_CTX_set_session_id_context(server_ctx.get(), kContext1,
2181 sizeof(kContext1))) {
2182 return false;
2183 }
David Benjamina933c382016-10-28 00:10:03 -04002184
David Benjamin0fef3052016-11-18 15:11:10 +09002185 SSL_CTX_set_tlsext_servername_callback(server_ctx.get(),
2186 SwitchSessionIDContextSNI);
David Benjamina933c382016-10-28 00:10:03 -04002187
David Benjamin0fef3052016-11-18 15:11:10 +09002188 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(), session.get(),
2189 false /* expect session not reused */)) {
2190 fprintf(stderr, "Error connecting with a context switch on SNI callback.\n");
2191 return false;
2192 }
David Benjamina933c382016-10-28 00:10:03 -04002193
David Benjamin0fef3052016-11-18 15:11:10 +09002194 // Switch the session ID context with the early callback instead.
2195 SSL_CTX_set_tlsext_servername_callback(server_ctx.get(), nullptr);
2196 SSL_CTX_set_select_certificate_cb(server_ctx.get(),
2197 SwitchSessionIDContextEarly);
David Benjamina933c382016-10-28 00:10:03 -04002198
David Benjamin0fef3052016-11-18 15:11:10 +09002199 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(), session.get(),
2200 false /* expect session not reused */)) {
2201 fprintf(stderr,
2202 "Error connecting with a context switch on early callback.\n");
2203 return false;
David Benjamina20e5352016-08-02 19:09:41 -04002204 }
2205
2206 return true;
2207}
2208
David Benjamin721e8b72016-08-03 13:13:17 -04002209static timeval g_current_time;
2210
2211static void CurrentTimeCallback(const SSL *ssl, timeval *out_clock) {
2212 *out_clock = g_current_time;
2213}
2214
David Benjamin17b30832017-01-28 14:00:32 -05002215static void FrozenTimeCallback(const SSL *ssl, timeval *out_clock) {
2216 out_clock->tv_sec = 1000;
2217 out_clock->tv_usec = 0;
2218}
2219
David Benjamin3c51d9b2016-11-01 17:50:42 -04002220static int RenewTicketCallback(SSL *ssl, uint8_t *key_name, uint8_t *iv,
2221 EVP_CIPHER_CTX *ctx, HMAC_CTX *hmac_ctx,
2222 int encrypt) {
2223 static const uint8_t kZeros[16] = {0};
2224
2225 if (encrypt) {
David Benjamin17cf2cb2016-12-13 01:07:13 -05002226 OPENSSL_memcpy(key_name, kZeros, sizeof(kZeros));
David Benjamin3c51d9b2016-11-01 17:50:42 -04002227 RAND_bytes(iv, 16);
David Benjamin17cf2cb2016-12-13 01:07:13 -05002228 } else if (OPENSSL_memcmp(key_name, kZeros, 16) != 0) {
David Benjamin3c51d9b2016-11-01 17:50:42 -04002229 return 0;
2230 }
2231
2232 if (!HMAC_Init_ex(hmac_ctx, kZeros, sizeof(kZeros), EVP_sha256(), NULL) ||
2233 !EVP_CipherInit_ex(ctx, EVP_aes_128_cbc(), NULL, kZeros, iv, encrypt)) {
2234 return -1;
2235 }
2236
2237 // Returning two from the callback in decrypt mode renews the
2238 // session in TLS 1.2 and below.
2239 return encrypt ? 1 : 2;
2240}
2241
David Benjamin123db572016-11-03 16:59:25 -04002242static bool GetServerTicketTime(long *out, const SSL_SESSION *session) {
David Benjamin123db572016-11-03 16:59:25 -04002243 if (session->tlsext_ticklen < 16 + 16 + SHA256_DIGEST_LENGTH) {
2244 return false;
2245 }
2246
David Benjamin123db572016-11-03 16:59:25 -04002247 const uint8_t *ciphertext = session->tlsext_tick + 16 + 16;
2248 size_t len = session->tlsext_ticklen - 16 - 16 - SHA256_DIGEST_LENGTH;
2249 std::unique_ptr<uint8_t[]> plaintext(new uint8_t[len]);
2250
David Benjamin9b63f292016-11-15 00:44:05 -05002251#if defined(BORINGSSL_UNSAFE_FUZZER_MODE)
2252 // Fuzzer-mode tickets are unencrypted.
David Benjamin17cf2cb2016-12-13 01:07:13 -05002253 OPENSSL_memcpy(plaintext.get(), ciphertext, len);
David Benjamin9b63f292016-11-15 00:44:05 -05002254#else
2255 static const uint8_t kZeros[16] = {0};
2256 const uint8_t *iv = session->tlsext_tick + 16;
David Benjamin123db572016-11-03 16:59:25 -04002257 bssl::ScopedEVP_CIPHER_CTX ctx;
2258 int len1, len2;
2259 if (!EVP_DecryptInit_ex(ctx.get(), EVP_aes_128_cbc(), nullptr, kZeros, iv) ||
2260 !EVP_DecryptUpdate(ctx.get(), plaintext.get(), &len1, ciphertext, len) ||
2261 !EVP_DecryptFinal_ex(ctx.get(), plaintext.get() + len1, &len2)) {
2262 return false;
2263 }
2264
2265 len = static_cast<size_t>(len1 + len2);
David Benjamin9b63f292016-11-15 00:44:05 -05002266#endif
David Benjamin123db572016-11-03 16:59:25 -04002267
Adam Langley46db7af2017-02-01 15:49:37 -08002268 bssl::UniquePtr<SSL_CTX> ssl_ctx(SSL_CTX_new(TLS_method()));
2269 if (!ssl_ctx) {
2270 return false;
2271 }
David Benjamin123db572016-11-03 16:59:25 -04002272 bssl::UniquePtr<SSL_SESSION> server_session(
Adam Langley46db7af2017-02-01 15:49:37 -08002273 SSL_SESSION_from_bytes(plaintext.get(), len, ssl_ctx.get()));
David Benjamin123db572016-11-03 16:59:25 -04002274 if (!server_session) {
2275 return false;
2276 }
2277
2278 *out = server_session->time;
2279 return true;
2280}
2281
David Benjamin0fef3052016-11-18 15:11:10 +09002282static bool TestSessionTimeout(bool is_dtls, const SSL_METHOD *method,
2283 uint16_t version) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002284 bssl::UniquePtr<X509> cert = GetTestCertificate();
2285 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
David Benjamin721e8b72016-08-03 13:13:17 -04002286 if (!cert || !key) {
2287 return false;
2288 }
2289
David Benjamin0fef3052016-11-18 15:11:10 +09002290 for (bool server_test : std::vector<bool>{false, true}) {
David Benjamin17b30832017-01-28 14:00:32 -05002291 static const time_t kStartTime = 1000;
David Benjamin0fef3052016-11-18 15:11:10 +09002292 g_current_time.tv_sec = kStartTime;
David Benjamin1b22f852016-10-27 16:36:32 -04002293
David Benjamin17b30832017-01-28 14:00:32 -05002294 // We are willing to use a longer lifetime for TLS 1.3 sessions as
2295 // resumptions still perform ECDHE.
2296 const time_t timeout = version == TLS1_3_VERSION
2297 ? SSL_DEFAULT_SESSION_PSK_DHE_TIMEOUT
2298 : SSL_DEFAULT_SESSION_TIMEOUT;
2299
David Benjamin0fef3052016-11-18 15:11:10 +09002300 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(method));
2301 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(method));
2302 if (!server_ctx || !client_ctx ||
2303 !SSL_CTX_use_certificate(server_ctx.get(), cert.get()) ||
2304 !SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()) ||
2305 !SSL_CTX_set_min_proto_version(client_ctx.get(), version) ||
2306 !SSL_CTX_set_max_proto_version(client_ctx.get(), version) ||
2307 !SSL_CTX_set_min_proto_version(server_ctx.get(), version) ||
2308 !SSL_CTX_set_max_proto_version(server_ctx.get(), version)) {
2309 return false;
2310 }
2311
2312 SSL_CTX_set_session_cache_mode(client_ctx.get(), SSL_SESS_CACHE_BOTH);
2313 SSL_CTX_set_session_cache_mode(server_ctx.get(), SSL_SESS_CACHE_BOTH);
2314
David Benjamin17b30832017-01-28 14:00:32 -05002315 // Both client and server must enforce session timeouts. We configure the
2316 // other side with a frozen clock so it never expires tickets.
David Benjamin0fef3052016-11-18 15:11:10 +09002317 if (server_test) {
David Benjamin17b30832017-01-28 14:00:32 -05002318 SSL_CTX_set_current_time_cb(client_ctx.get(), FrozenTimeCallback);
David Benjamin0fef3052016-11-18 15:11:10 +09002319 SSL_CTX_set_current_time_cb(server_ctx.get(), CurrentTimeCallback);
2320 } else {
2321 SSL_CTX_set_current_time_cb(client_ctx.get(), CurrentTimeCallback);
David Benjamin17b30832017-01-28 14:00:32 -05002322 SSL_CTX_set_current_time_cb(server_ctx.get(), FrozenTimeCallback);
David Benjamin0fef3052016-11-18 15:11:10 +09002323 }
2324
2325 // Configure a ticket callback which renews tickets.
2326 SSL_CTX_set_tlsext_ticket_key_cb(server_ctx.get(), RenewTicketCallback);
2327
2328 bssl::UniquePtr<SSL_SESSION> session =
2329 CreateClientSession(client_ctx.get(), server_ctx.get());
2330 if (!session) {
2331 fprintf(stderr, "Error getting session.\n");
2332 return false;
2333 }
2334
2335 // Advance the clock just behind the timeout.
David Benjamin17b30832017-01-28 14:00:32 -05002336 g_current_time.tv_sec += timeout - 1;
David Benjamin0fef3052016-11-18 15:11:10 +09002337
2338 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(), session.get(),
2339 true /* expect session reused */)) {
2340 fprintf(stderr, "Error resuming session.\n");
2341 return false;
2342 }
2343
2344 // Advance the clock one more second.
2345 g_current_time.tv_sec++;
2346
2347 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(), session.get(),
2348 false /* expect session not reused */)) {
2349 fprintf(stderr, "Error resuming session.\n");
2350 return false;
2351 }
2352
2353 // Rewind the clock to before the session was minted.
2354 g_current_time.tv_sec = kStartTime - 1;
2355
2356 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(), session.get(),
2357 false /* expect session not reused */)) {
2358 fprintf(stderr, "Error resuming session.\n");
2359 return false;
2360 }
2361
2362 // SSL 3.0 cannot renew sessions.
2363 if (version == SSL3_VERSION) {
2364 continue;
2365 }
2366
2367 // Renew the session 10 seconds before expiration.
David Benjamin17b30832017-01-28 14:00:32 -05002368 time_t new_start_time = kStartTime + timeout - 10;
2369 g_current_time.tv_sec = new_start_time;
David Benjamin0fef3052016-11-18 15:11:10 +09002370 bssl::UniquePtr<SSL_SESSION> new_session =
2371 ExpectSessionRenewed(client_ctx.get(), server_ctx.get(), session.get());
2372 if (!new_session) {
2373 fprintf(stderr, "Error renewing session.\n");
2374 return false;
2375 }
2376
2377 // This new session is not the same object as before.
2378 if (session.get() == new_session.get()) {
2379 fprintf(stderr, "New and old sessions alias.\n");
2380 return false;
2381 }
2382
2383 // Check the sessions have timestamps measured from issuance.
2384 long session_time = 0;
2385 if (server_test) {
2386 if (!GetServerTicketTime(&session_time, new_session.get())) {
2387 fprintf(stderr, "Failed to decode session ticket.\n");
David Benjaminb2e2e322016-11-01 17:32:54 -04002388 return false;
2389 }
David Benjamin0fef3052016-11-18 15:11:10 +09002390 } else {
2391 session_time = new_session->time;
2392 }
David Benjamin721e8b72016-08-03 13:13:17 -04002393
David Benjamin0fef3052016-11-18 15:11:10 +09002394 if (session_time != g_current_time.tv_sec) {
2395 fprintf(stderr, "New session is not measured from issuance.\n");
2396 return false;
2397 }
David Benjamin721e8b72016-08-03 13:13:17 -04002398
David Benjamin17b30832017-01-28 14:00:32 -05002399 if (version == TLS1_3_VERSION) {
2400 // Renewal incorporates fresh key material in TLS 1.3, so we extend the
2401 // lifetime TLS 1.3.
2402 g_current_time.tv_sec = new_start_time + timeout - 1;
2403 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(),
2404 new_session.get(),
2405 true /* expect session reused */)) {
2406 fprintf(stderr, "Error resuming renewed session.\n");
2407 return false;
2408 }
David Benjamin721e8b72016-08-03 13:13:17 -04002409
David Benjamin17b30832017-01-28 14:00:32 -05002410 // The new session expires after the new timeout.
2411 g_current_time.tv_sec = new_start_time + timeout + 1;
2412 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(),
2413 new_session.get(),
2414 false /* expect session ot reused */)) {
2415 fprintf(stderr, "Renewed session's lifetime is too long.\n");
2416 return false;
2417 }
2418
2419 // Renew the session until it begins just past the auth timeout.
2420 time_t auth_end_time = kStartTime + SSL_DEFAULT_SESSION_AUTH_TIMEOUT;
2421 while (new_start_time < auth_end_time - 1000) {
2422 // Get as close as possible to target start time.
2423 new_start_time =
2424 std::min(auth_end_time - 1000, new_start_time + timeout - 1);
2425 g_current_time.tv_sec = new_start_time;
2426 new_session = ExpectSessionRenewed(client_ctx.get(), server_ctx.get(),
2427 new_session.get());
2428 if (!new_session) {
2429 fprintf(stderr, "Error renewing session.\n");
2430 return false;
2431 }
2432 }
2433
2434 // Now the session's lifetime is bound by the auth timeout.
2435 g_current_time.tv_sec = auth_end_time - 1;
2436 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(),
2437 new_session.get(),
2438 true /* expect session reused */)) {
2439 fprintf(stderr, "Error resuming renewed session.\n");
2440 return false;
2441 }
2442
2443 g_current_time.tv_sec = auth_end_time + 1;
2444 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(),
2445 new_session.get(),
2446 false /* expect session ot reused */)) {
2447 fprintf(stderr, "Renewed session's lifetime is too long.\n");
2448 return false;
2449 }
2450 } else {
2451 // The new session is usable just before the old expiration.
2452 g_current_time.tv_sec = kStartTime + timeout - 1;
2453 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(),
2454 new_session.get(),
2455 true /* expect session reused */)) {
2456 fprintf(stderr, "Error resuming renewed session.\n");
2457 return false;
2458 }
2459
2460 // Renewal does not extend the lifetime, so it is not usable beyond the
2461 // old expiration.
2462 g_current_time.tv_sec = kStartTime + timeout + 1;
2463 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(),
2464 new_session.get(),
2465 false /* expect session not reused */)) {
2466 fprintf(stderr, "Renewed session's lifetime is too long.\n");
2467 return false;
2468 }
David Benjamin1b22f852016-10-27 16:36:32 -04002469 }
David Benjamin721e8b72016-08-03 13:13:17 -04002470 }
2471
2472 return true;
2473}
2474
David Benjamin0fc37ef2016-08-17 15:29:46 -04002475static int SwitchContext(SSL *ssl, int *out_alert, void *arg) {
2476 SSL_CTX *ctx = reinterpret_cast<SSL_CTX*>(arg);
2477 SSL_set_SSL_CTX(ssl, ctx);
2478 return SSL_TLSEXT_ERR_OK;
2479}
2480
David Benjamin0fef3052016-11-18 15:11:10 +09002481static bool TestSNICallback(bool is_dtls, const SSL_METHOD *method,
2482 uint16_t version) {
2483 // SSL 3.0 lacks extensions.
2484 if (version == SSL3_VERSION) {
2485 return true;
2486 }
2487
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002488 bssl::UniquePtr<X509> cert = GetTestCertificate();
2489 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
2490 bssl::UniquePtr<X509> cert2 = GetECDSATestCertificate();
2491 bssl::UniquePtr<EVP_PKEY> key2 = GetECDSATestKey();
David Benjamin0fc37ef2016-08-17 15:29:46 -04002492 if (!cert || !key || !cert2 || !key2) {
2493 return false;
2494 }
2495
David Benjamin0fef3052016-11-18 15:11:10 +09002496 // Test that switching the |SSL_CTX| at the SNI callback behaves correctly.
2497 static const uint16_t kECDSAWithSHA256 = SSL_SIGN_ECDSA_SECP256R1_SHA256;
David Benjamin0fc37ef2016-08-17 15:29:46 -04002498
David Benjamin83a32122017-02-14 18:34:54 -05002499 static const uint8_t kSCTList[] = {0, 6, 0, 4, 5, 6, 7, 8};
2500 static const uint8_t kOCSPResponse[] = {1, 2, 3, 4};
2501
David Benjamin0fef3052016-11-18 15:11:10 +09002502 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(method));
2503 bssl::UniquePtr<SSL_CTX> server_ctx2(SSL_CTX_new(method));
2504 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(method));
2505 if (!server_ctx || !server_ctx2 || !client_ctx ||
2506 !SSL_CTX_use_certificate(server_ctx.get(), cert.get()) ||
2507 !SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()) ||
2508 !SSL_CTX_use_certificate(server_ctx2.get(), cert2.get()) ||
2509 !SSL_CTX_use_PrivateKey(server_ctx2.get(), key2.get()) ||
David Benjamin83a32122017-02-14 18:34:54 -05002510 !SSL_CTX_set_signed_cert_timestamp_list(server_ctx2.get(), kSCTList,
2511 sizeof(kSCTList)) ||
2512 !SSL_CTX_set_ocsp_response(server_ctx2.get(), kOCSPResponse,
2513 sizeof(kOCSPResponse)) ||
David Benjamin0fef3052016-11-18 15:11:10 +09002514 // Historically signing preferences would be lost in some cases with the
2515 // SNI callback, which triggers the TLS 1.2 SHA-1 default. To ensure
2516 // this doesn't happen when |version| is TLS 1.2, configure the private
2517 // key to only sign SHA-256.
2518 !SSL_CTX_set_signing_algorithm_prefs(server_ctx2.get(), &kECDSAWithSHA256,
2519 1) ||
2520 !SSL_CTX_set_min_proto_version(client_ctx.get(), version) ||
2521 !SSL_CTX_set_max_proto_version(client_ctx.get(), version) ||
2522 !SSL_CTX_set_min_proto_version(server_ctx.get(), version) ||
2523 !SSL_CTX_set_max_proto_version(server_ctx.get(), version) ||
2524 !SSL_CTX_set_min_proto_version(server_ctx2.get(), version) ||
2525 !SSL_CTX_set_max_proto_version(server_ctx2.get(), version)) {
2526 return false;
2527 }
David Benjamin0fc37ef2016-08-17 15:29:46 -04002528
David Benjamin0fef3052016-11-18 15:11:10 +09002529 SSL_CTX_set_tlsext_servername_callback(server_ctx.get(), SwitchContext);
2530 SSL_CTX_set_tlsext_servername_arg(server_ctx.get(), server_ctx2.get());
David Benjamin0fc37ef2016-08-17 15:29:46 -04002531
David Benjamin83a32122017-02-14 18:34:54 -05002532 SSL_CTX_enable_signed_cert_timestamps(client_ctx.get());
2533 SSL_CTX_enable_ocsp_stapling(client_ctx.get());
2534
David Benjamin0fef3052016-11-18 15:11:10 +09002535 bssl::UniquePtr<SSL> client, server;
2536 if (!ConnectClientAndServer(&client, &server, client_ctx.get(),
2537 server_ctx.get(), nullptr)) {
2538 fprintf(stderr, "Handshake failed.\n");
2539 return false;
2540 }
David Benjamin0fc37ef2016-08-17 15:29:46 -04002541
David Benjamin0fef3052016-11-18 15:11:10 +09002542 // The client should have received |cert2|.
2543 bssl::UniquePtr<X509> peer(SSL_get_peer_certificate(client.get()));
2544 if (!peer || X509_cmp(peer.get(), cert2.get()) != 0) {
2545 fprintf(stderr, "Incorrect certificate received.\n");
2546 return false;
David Benjamin0fc37ef2016-08-17 15:29:46 -04002547 }
2548
David Benjamin83a32122017-02-14 18:34:54 -05002549 // The client should have received |server_ctx2|'s SCT list.
2550 const uint8_t *data;
2551 size_t len;
2552 SSL_get0_signed_cert_timestamp_list(client.get(), &data, &len);
2553 if (Bytes(kSCTList) != Bytes(data, len)) {
2554 fprintf(stderr, "Incorrect SCT list received.\n");
2555 return false;
2556 }
2557
2558 // The client should have received |server_ctx2|'s OCSP response.
2559 SSL_get0_ocsp_response(client.get(), &data, &len);
2560 if (Bytes(kOCSPResponse) != Bytes(data, len)) {
2561 fprintf(stderr, "Incorrect OCSP response received.\n");
2562 return false;
2563 }
2564
David Benjamin0fc37ef2016-08-17 15:29:46 -04002565 return true;
2566}
2567
David Benjaminf0d8e222017-02-04 10:58:26 -05002568// Test that the early callback can swap the maximum version.
2569TEST(SSLTest, EarlyCallbackVersionSwitch) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002570 bssl::UniquePtr<X509> cert = GetTestCertificate();
2571 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
2572 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(TLS_method()));
2573 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLS_method()));
David Benjaminf0d8e222017-02-04 10:58:26 -05002574 ASSERT_TRUE(cert);
2575 ASSERT_TRUE(key);
2576 ASSERT_TRUE(server_ctx);
2577 ASSERT_TRUE(client_ctx);
2578 ASSERT_TRUE(SSL_CTX_use_certificate(server_ctx.get(), cert.get()));
2579 ASSERT_TRUE(SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()));
2580 ASSERT_TRUE(SSL_CTX_set_max_proto_version(client_ctx.get(), TLS1_3_VERSION));
2581 ASSERT_TRUE(SSL_CTX_set_max_proto_version(server_ctx.get(), TLS1_3_VERSION));
David Benjamin99620572016-08-30 00:35:36 -04002582
David Benjaminf0d8e222017-02-04 10:58:26 -05002583 SSL_CTX_set_select_certificate_cb(
2584 server_ctx.get(), [](const SSL_CLIENT_HELLO *client_hello) -> int {
2585 if (!SSL_set_max_proto_version(client_hello->ssl, TLS1_2_VERSION)) {
2586 return -1;
2587 }
2588
2589 return 1;
2590 });
David Benjamin99620572016-08-30 00:35:36 -04002591
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002592 bssl::UniquePtr<SSL> client, server;
David Benjaminf0d8e222017-02-04 10:58:26 -05002593 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx.get(),
2594 server_ctx.get(), nullptr));
2595 EXPECT_EQ(TLS1_2_VERSION, SSL_version(client.get()));
David Benjamin99620572016-08-30 00:35:36 -04002596}
2597
David Benjaminf0d8e222017-02-04 10:58:26 -05002598TEST(SSLTest, SetVersion) {
David Benjamin2dc02042016-09-19 19:57:37 -04002599 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
David Benjaminf0d8e222017-02-04 10:58:26 -05002600 ASSERT_TRUE(ctx);
David Benjamin2dc02042016-09-19 19:57:37 -04002601
David Benjaminf0d8e222017-02-04 10:58:26 -05002602 // Set valid TLS versions.
2603 EXPECT_TRUE(SSL_CTX_set_max_proto_version(ctx.get(), TLS1_VERSION));
2604 EXPECT_TRUE(SSL_CTX_set_max_proto_version(ctx.get(), TLS1_1_VERSION));
2605 EXPECT_TRUE(SSL_CTX_set_min_proto_version(ctx.get(), TLS1_VERSION));
2606 EXPECT_TRUE(SSL_CTX_set_min_proto_version(ctx.get(), TLS1_1_VERSION));
David Benjamin2dc02042016-09-19 19:57:37 -04002607
David Benjaminf0d8e222017-02-04 10:58:26 -05002608 // Invalid TLS versions are rejected.
2609 EXPECT_FALSE(SSL_CTX_set_max_proto_version(ctx.get(), DTLS1_VERSION));
2610 EXPECT_FALSE(SSL_CTX_set_max_proto_version(ctx.get(), 0x0200));
2611 EXPECT_FALSE(SSL_CTX_set_max_proto_version(ctx.get(), 0x1234));
2612 EXPECT_FALSE(SSL_CTX_set_min_proto_version(ctx.get(), DTLS1_VERSION));
2613 EXPECT_FALSE(SSL_CTX_set_min_proto_version(ctx.get(), 0x0200));
2614 EXPECT_FALSE(SSL_CTX_set_min_proto_version(ctx.get(), 0x1234));
David Benjamin2dc02042016-09-19 19:57:37 -04002615
David Benjaminf0d8e222017-02-04 10:58:26 -05002616 // Zero is the default version.
2617 EXPECT_TRUE(SSL_CTX_set_max_proto_version(ctx.get(), 0));
2618 EXPECT_EQ(TLS1_2_VERSION, ctx->max_version);
2619 EXPECT_TRUE(SSL_CTX_set_min_proto_version(ctx.get(), 0));
2620 EXPECT_EQ(SSL3_VERSION, ctx->min_version);
David Benjamine34bcc92016-09-21 16:53:09 -04002621
David Benjamin2dc02042016-09-19 19:57:37 -04002622 ctx.reset(SSL_CTX_new(DTLS_method()));
David Benjaminf0d8e222017-02-04 10:58:26 -05002623 ASSERT_TRUE(ctx);
David Benjamin2dc02042016-09-19 19:57:37 -04002624
David Benjaminf0d8e222017-02-04 10:58:26 -05002625 EXPECT_TRUE(SSL_CTX_set_max_proto_version(ctx.get(), DTLS1_VERSION));
2626 EXPECT_TRUE(SSL_CTX_set_max_proto_version(ctx.get(), DTLS1_2_VERSION));
2627 EXPECT_TRUE(SSL_CTX_set_min_proto_version(ctx.get(), DTLS1_VERSION));
2628 EXPECT_TRUE(SSL_CTX_set_min_proto_version(ctx.get(), DTLS1_2_VERSION));
David Benjamin2dc02042016-09-19 19:57:37 -04002629
David Benjaminf0d8e222017-02-04 10:58:26 -05002630 EXPECT_FALSE(SSL_CTX_set_max_proto_version(ctx.get(), TLS1_VERSION));
2631 EXPECT_FALSE(SSL_CTX_set_max_proto_version(ctx.get(), 0xfefe /* DTLS 1.1 */));
2632 EXPECT_FALSE(SSL_CTX_set_max_proto_version(ctx.get(), 0xfffe /* DTLS 0.1 */));
2633 EXPECT_FALSE(SSL_CTX_set_max_proto_version(ctx.get(), 0x1234));
2634 EXPECT_FALSE(SSL_CTX_set_min_proto_version(ctx.get(), TLS1_VERSION));
2635 EXPECT_FALSE(SSL_CTX_set_min_proto_version(ctx.get(), 0xfefe /* DTLS 1.1 */));
2636 EXPECT_FALSE(SSL_CTX_set_min_proto_version(ctx.get(), 0xfffe /* DTLS 0.1 */));
2637 EXPECT_FALSE(SSL_CTX_set_min_proto_version(ctx.get(), 0x1234));
David Benjamin2dc02042016-09-19 19:57:37 -04002638
David Benjaminf0d8e222017-02-04 10:58:26 -05002639 EXPECT_TRUE(SSL_CTX_set_max_proto_version(ctx.get(), 0));
2640 EXPECT_EQ(TLS1_2_VERSION, ctx->max_version);
2641 EXPECT_TRUE(SSL_CTX_set_min_proto_version(ctx.get(), 0));
2642 EXPECT_EQ(TLS1_1_VERSION, ctx->min_version);
David Benjamin2dc02042016-09-19 19:57:37 -04002643}
2644
David Benjamin458334a2016-12-15 13:53:25 -05002645static const char *GetVersionName(uint16_t version) {
2646 switch (version) {
2647 case SSL3_VERSION:
2648 return "SSLv3";
2649 case TLS1_VERSION:
2650 return "TLSv1";
2651 case TLS1_1_VERSION:
2652 return "TLSv1.1";
2653 case TLS1_2_VERSION:
2654 return "TLSv1.2";
2655 case TLS1_3_VERSION:
2656 return "TLSv1.3";
2657 case DTLS1_VERSION:
2658 return "DTLSv1";
2659 case DTLS1_2_VERSION:
2660 return "DTLSv1.2";
2661 default:
2662 return "???";
2663 }
2664}
2665
David Benjamin0fef3052016-11-18 15:11:10 +09002666static bool TestVersion(bool is_dtls, const SSL_METHOD *method,
2667 uint16_t version) {
David Benjamincb18ac22016-09-27 14:09:15 -04002668 bssl::UniquePtr<X509> cert = GetTestCertificate();
2669 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
2670 if (!cert || !key) {
2671 return false;
2672 }
2673
David Benjamin0fef3052016-11-18 15:11:10 +09002674 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(method));
2675 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(method));
2676 bssl::UniquePtr<SSL> client, server;
2677 if (!server_ctx || !client_ctx ||
2678 !SSL_CTX_use_certificate(server_ctx.get(), cert.get()) ||
2679 !SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()) ||
2680 !SSL_CTX_set_min_proto_version(client_ctx.get(), version) ||
2681 !SSL_CTX_set_max_proto_version(client_ctx.get(), version) ||
2682 !SSL_CTX_set_min_proto_version(server_ctx.get(), version) ||
2683 !SSL_CTX_set_max_proto_version(server_ctx.get(), version) ||
2684 !ConnectClientAndServer(&client, &server, client_ctx.get(),
2685 server_ctx.get(), nullptr /* no session */)) {
2686 fprintf(stderr, "Failed to connect.\n");
2687 return false;
2688 }
David Benjamincb18ac22016-09-27 14:09:15 -04002689
David Benjamin0fef3052016-11-18 15:11:10 +09002690 if (SSL_version(client.get()) != version ||
2691 SSL_version(server.get()) != version) {
2692 fprintf(stderr, "Version mismatch. Got %04x and %04x, wanted %04x.\n",
2693 SSL_version(client.get()), SSL_version(server.get()), version);
2694 return false;
David Benjamincb18ac22016-09-27 14:09:15 -04002695 }
2696
David Benjamin458334a2016-12-15 13:53:25 -05002697 // Test the version name is reported as expected.
2698 const char *version_name = GetVersionName(version);
2699 if (strcmp(version_name, SSL_get_version(client.get())) != 0 ||
2700 strcmp(version_name, SSL_get_version(server.get())) != 0) {
2701 fprintf(stderr, "Version name mismatch. Got '%s' and '%s', wanted '%s'.\n",
2702 SSL_get_version(client.get()), SSL_get_version(server.get()),
2703 version_name);
2704 return false;
2705 }
2706
2707 // Test SSL_SESSION reports the same name.
2708 const char *client_name =
2709 SSL_SESSION_get_version(SSL_get_session(client.get()));
2710 const char *server_name =
2711 SSL_SESSION_get_version(SSL_get_session(server.get()));
2712 if (strcmp(version_name, client_name) != 0 ||
2713 strcmp(version_name, server_name) != 0) {
2714 fprintf(stderr,
2715 "Session version name mismatch. Got '%s' and '%s', wanted '%s'.\n",
2716 client_name, server_name, version_name);
2717 return false;
2718 }
2719
David Benjamincb18ac22016-09-27 14:09:15 -04002720 return true;
2721}
2722
David Benjamin9ef31f02016-10-31 18:01:13 -04002723// Tests that that |SSL_get_pending_cipher| is available during the ALPN
2724// selection callback.
David Benjamin0fef3052016-11-18 15:11:10 +09002725static bool TestALPNCipherAvailable(bool is_dtls, const SSL_METHOD *method,
2726 uint16_t version) {
2727 // SSL 3.0 lacks extensions.
2728 if (version == SSL3_VERSION) {
2729 return true;
2730 }
2731
David Benjamin9ef31f02016-10-31 18:01:13 -04002732 static const uint8_t kALPNProtos[] = {0x03, 'f', 'o', 'o'};
2733
2734 bssl::UniquePtr<X509> cert = GetTestCertificate();
2735 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
2736 if (!cert || !key) {
2737 return false;
2738 }
2739
David Benjamin0fef3052016-11-18 15:11:10 +09002740 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(method));
2741 if (!ctx || !SSL_CTX_use_certificate(ctx.get(), cert.get()) ||
2742 !SSL_CTX_use_PrivateKey(ctx.get(), key.get()) ||
2743 !SSL_CTX_set_min_proto_version(ctx.get(), version) ||
2744 !SSL_CTX_set_max_proto_version(ctx.get(), version) ||
2745 SSL_CTX_set_alpn_protos(ctx.get(), kALPNProtos, sizeof(kALPNProtos)) !=
2746 0) {
2747 return false;
2748 }
2749
2750 // The ALPN callback does not fail the handshake on error, so have the
2751 // callback write a boolean.
2752 std::pair<uint16_t, bool> callback_state(version, false);
2753 SSL_CTX_set_alpn_select_cb(
2754 ctx.get(),
2755 [](SSL *ssl, const uint8_t **out, uint8_t *out_len, const uint8_t *in,
2756 unsigned in_len, void *arg) -> int {
2757 auto state = reinterpret_cast<std::pair<uint16_t, bool> *>(arg);
2758 if (SSL_get_pending_cipher(ssl) != nullptr &&
2759 SSL_version(ssl) == state->first) {
2760 state->second = true;
2761 }
2762 return SSL_TLSEXT_ERR_NOACK;
2763 },
2764 &callback_state);
2765
2766 bssl::UniquePtr<SSL> client, server;
2767 if (!ConnectClientAndServer(&client, &server, ctx.get(), ctx.get(),
2768 nullptr /* no session */)) {
2769 return false;
2770 }
2771
2772 if (!callback_state.second) {
2773 fprintf(stderr, "The pending cipher was not known in the ALPN callback.\n");
2774 return false;
2775 }
2776
2777 return true;
2778}
2779
David Benjaminb79cc842016-12-07 15:57:14 -05002780static bool TestSSLClearSessionResumption(bool is_dtls,
2781 const SSL_METHOD *method,
2782 uint16_t version) {
2783 // Skip this for TLS 1.3. TLS 1.3's ticket mechanism is incompatible with this
2784 // API pattern.
2785 if (version == TLS1_3_VERSION) {
2786 return true;
2787 }
2788
2789 bssl::UniquePtr<X509> cert = GetTestCertificate();
2790 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
2791 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(method));
2792 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(method));
2793 if (!cert || !key || !server_ctx || !client_ctx ||
2794 !SSL_CTX_use_certificate(server_ctx.get(), cert.get()) ||
2795 !SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()) ||
2796 !SSL_CTX_set_min_proto_version(client_ctx.get(), version) ||
2797 !SSL_CTX_set_max_proto_version(client_ctx.get(), version) ||
2798 !SSL_CTX_set_min_proto_version(server_ctx.get(), version) ||
2799 !SSL_CTX_set_max_proto_version(server_ctx.get(), version)) {
2800 return false;
2801 }
2802
2803 // Connect a client and a server.
2804 bssl::UniquePtr<SSL> client, server;
2805 if (!ConnectClientAndServer(&client, &server, client_ctx.get(),
2806 server_ctx.get(), nullptr /* no session */)) {
2807 return false;
2808 }
2809
2810 if (SSL_session_reused(client.get()) ||
2811 SSL_session_reused(server.get())) {
2812 fprintf(stderr, "Session unexpectedly reused.\n");
2813 return false;
2814 }
2815
2816 // Reset everything.
2817 if (!SSL_clear(client.get()) ||
2818 !SSL_clear(server.get())) {
2819 fprintf(stderr, "SSL_clear failed.\n");
2820 return false;
2821 }
2822
2823 // Attempt to connect a second time.
2824 if (!CompleteHandshakes(client.get(), server.get())) {
2825 fprintf(stderr, "Could not reuse SSL objects.\n");
2826 return false;
2827 }
2828
2829 // |SSL_clear| should implicitly offer the previous session to the server.
2830 if (!SSL_session_reused(client.get()) ||
2831 !SSL_session_reused(server.get())) {
2832 fprintf(stderr, "Session was not reused in second try.\n");
2833 return false;
2834 }
2835
2836 return true;
2837}
2838
David Benjamin1444c3a2016-12-20 17:23:11 -05002839static bool ChainsEqual(STACK_OF(X509) *chain,
2840 const std::vector<X509 *> &expected) {
2841 if (sk_X509_num(chain) != expected.size()) {
2842 return false;
2843 }
2844
2845 for (size_t i = 0; i < expected.size(); i++) {
2846 if (X509_cmp(sk_X509_value(chain, i), expected[i]) != 0) {
2847 return false;
2848 }
2849 }
2850
2851 return true;
2852}
2853
2854static bool TestAutoChain(bool is_dtls, const SSL_METHOD *method,
2855 uint16_t version) {
David Benjamin1444c3a2016-12-20 17:23:11 -05002856 bssl::UniquePtr<X509> cert = GetChainTestCertificate();
2857 bssl::UniquePtr<X509> intermediate = GetChainTestIntermediate();
2858 bssl::UniquePtr<EVP_PKEY> key = GetChainTestKey();
2859 if (!cert || !intermediate || !key) {
2860 return false;
2861 }
2862
2863 // Configure both client and server to accept any certificate. Add
2864 // |intermediate| to the cert store.
2865 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(method));
2866 if (!ctx ||
2867 !SSL_CTX_use_certificate(ctx.get(), cert.get()) ||
2868 !SSL_CTX_use_PrivateKey(ctx.get(), key.get()) ||
2869 !SSL_CTX_set_min_proto_version(ctx.get(), version) ||
2870 !SSL_CTX_set_max_proto_version(ctx.get(), version) ||
2871 !X509_STORE_add_cert(SSL_CTX_get_cert_store(ctx.get()),
2872 intermediate.get())) {
2873 return false;
2874 }
2875 SSL_CTX_set_verify(
2876 ctx.get(), SSL_VERIFY_PEER | SSL_VERIFY_FAIL_IF_NO_PEER_CERT, nullptr);
2877 SSL_CTX_set_cert_verify_callback(ctx.get(), VerifySucceed, NULL);
2878
2879 // By default, the client and server should each only send the leaf.
2880 bssl::UniquePtr<SSL> client, server;
2881 if (!ConnectClientAndServer(&client, &server, ctx.get(), ctx.get(),
2882 nullptr /* no session */)) {
2883 return false;
2884 }
2885
2886 if (!ChainsEqual(SSL_get_peer_full_cert_chain(client.get()), {cert.get()})) {
2887 fprintf(stderr, "Client-received chain did not match.\n");
2888 return false;
2889 }
2890
2891 if (!ChainsEqual(SSL_get_peer_full_cert_chain(server.get()), {cert.get()})) {
2892 fprintf(stderr, "Server-received chain did not match.\n");
2893 return false;
2894 }
2895
2896 // If auto-chaining is enabled, then the intermediate is sent.
2897 SSL_CTX_clear_mode(ctx.get(), SSL_MODE_NO_AUTO_CHAIN);
2898 if (!ConnectClientAndServer(&client, &server, ctx.get(), ctx.get(),
2899 nullptr /* no session */)) {
2900 return false;
2901 }
2902
2903 if (!ChainsEqual(SSL_get_peer_full_cert_chain(client.get()),
2904 {cert.get(), intermediate.get()})) {
2905 fprintf(stderr, "Client-received chain did not match (auto-chaining).\n");
2906 return false;
2907 }
2908
2909 if (!ChainsEqual(SSL_get_peer_full_cert_chain(server.get()),
2910 {cert.get(), intermediate.get()})) {
2911 fprintf(stderr, "Server-received chain did not match (auto-chaining).\n");
2912 return false;
2913 }
2914
2915 // Auto-chaining does not override explicitly-configured intermediates.
2916 if (!SSL_CTX_add1_chain_cert(ctx.get(), cert.get()) ||
2917 !ConnectClientAndServer(&client, &server, ctx.get(), ctx.get(),
2918 nullptr /* no session */)) {
2919 return false;
2920 }
2921
2922 if (!ChainsEqual(SSL_get_peer_full_cert_chain(client.get()),
2923 {cert.get(), cert.get()})) {
2924 fprintf(stderr,
2925 "Client-received chain did not match (auto-chaining, explicit "
2926 "intermediate).\n");
2927 return false;
2928 }
2929
2930 if (!ChainsEqual(SSL_get_peer_full_cert_chain(server.get()),
2931 {cert.get(), cert.get()})) {
2932 fprintf(stderr,
2933 "Server-received chain did not match (auto-chaining, explicit "
2934 "intermediate).\n");
2935 return false;
2936 }
2937
2938 return true;
2939}
2940
David Benjamin48063c22017-01-01 23:56:36 -05002941static bool ExpectBadWriteRetry() {
2942 int err = ERR_get_error();
2943 if (ERR_GET_LIB(err) != ERR_LIB_SSL ||
2944 ERR_GET_REASON(err) != SSL_R_BAD_WRITE_RETRY) {
2945 char buf[ERR_ERROR_STRING_BUF_LEN];
2946 ERR_error_string_n(err, buf, sizeof(buf));
2947 fprintf(stderr, "Wanted SSL_R_BAD_WRITE_RETRY, got: %s.\n", buf);
2948 return false;
2949 }
2950
2951 if (ERR_peek_error() != 0) {
2952 fprintf(stderr, "Unexpected error following SSL_R_BAD_WRITE_RETRY.\n");
2953 return false;
2954 }
2955
2956 return true;
2957}
2958
2959static bool TestSSLWriteRetry(bool is_dtls, const SSL_METHOD *method,
2960 uint16_t version) {
2961 if (is_dtls) {
2962 return true;
2963 }
2964
2965 for (bool enable_partial_write : std::vector<bool>{false, true}) {
2966 // Connect a client and server.
2967 bssl::UniquePtr<X509> cert = GetTestCertificate();
2968 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
2969 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(method));
2970 bssl::UniquePtr<SSL> client, server;
2971 if (!cert || !key || !ctx ||
2972 !SSL_CTX_use_certificate(ctx.get(), cert.get()) ||
2973 !SSL_CTX_use_PrivateKey(ctx.get(), key.get()) ||
2974 !SSL_CTX_set_min_proto_version(ctx.get(), version) ||
2975 !SSL_CTX_set_max_proto_version(ctx.get(), version) ||
2976 !ConnectClientAndServer(&client, &server, ctx.get(), ctx.get(),
2977 nullptr /* no session */)) {
2978 return false;
2979 }
2980
2981 if (enable_partial_write) {
2982 SSL_set_mode(client.get(), SSL_MODE_ENABLE_PARTIAL_WRITE);
2983 }
2984
2985 // Write without reading until the buffer is full and we have an unfinished
2986 // write. Keep a count so we may reread it again later. "hello!" will be
2987 // written in two chunks, "hello" and "!".
2988 char data[] = "hello!";
2989 static const int kChunkLen = 5; // The length of "hello".
2990 unsigned count = 0;
2991 for (;;) {
2992 int ret = SSL_write(client.get(), data, kChunkLen);
2993 if (ret <= 0) {
2994 int err = SSL_get_error(client.get(), ret);
2995 if (SSL_get_error(client.get(), ret) == SSL_ERROR_WANT_WRITE) {
2996 break;
2997 }
2998 fprintf(stderr, "SSL_write failed in unexpected way: %d\n", err);
2999 return false;
3000 }
3001
3002 if (ret != 5) {
3003 fprintf(stderr, "SSL_write wrote %d bytes, expected 5.\n", ret);
3004 return false;
3005 }
3006
3007 count++;
3008 }
3009
3010 // Retrying with the same parameters is legal.
3011 if (SSL_get_error(client.get(), SSL_write(client.get(), data, kChunkLen)) !=
3012 SSL_ERROR_WANT_WRITE) {
3013 fprintf(stderr, "SSL_write retry unexpectedly failed.\n");
3014 return false;
3015 }
3016
3017 // Retrying with the same buffer but shorter length is not legal.
3018 if (SSL_get_error(client.get(),
3019 SSL_write(client.get(), data, kChunkLen - 1)) !=
3020 SSL_ERROR_SSL ||
3021 !ExpectBadWriteRetry()) {
3022 fprintf(stderr, "SSL_write retry did not fail as expected.\n");
3023 return false;
3024 }
3025
3026 // Retrying with a different buffer pointer is not legal.
3027 char data2[] = "hello";
3028 if (SSL_get_error(client.get(), SSL_write(client.get(), data2,
3029 kChunkLen)) != SSL_ERROR_SSL ||
3030 !ExpectBadWriteRetry()) {
3031 fprintf(stderr, "SSL_write retry did not fail as expected.\n");
3032 return false;
3033 }
3034
3035 // With |SSL_MODE_ACCEPT_MOVING_WRITE_BUFFER|, the buffer may move.
3036 SSL_set_mode(client.get(), SSL_MODE_ACCEPT_MOVING_WRITE_BUFFER);
3037 if (SSL_get_error(client.get(),
3038 SSL_write(client.get(), data2, kChunkLen)) !=
3039 SSL_ERROR_WANT_WRITE) {
3040 fprintf(stderr, "SSL_write retry unexpectedly failed.\n");
3041 return false;
3042 }
3043
3044 // |SSL_MODE_ACCEPT_MOVING_WRITE_BUFFER| does not disable length checks.
3045 if (SSL_get_error(client.get(),
3046 SSL_write(client.get(), data2, kChunkLen - 1)) !=
3047 SSL_ERROR_SSL ||
3048 !ExpectBadWriteRetry()) {
3049 fprintf(stderr, "SSL_write retry did not fail as expected.\n");
3050 return false;
3051 }
3052
3053 // Retrying with a larger buffer is legal.
3054 if (SSL_get_error(client.get(),
3055 SSL_write(client.get(), data, kChunkLen + 1)) !=
3056 SSL_ERROR_WANT_WRITE) {
3057 fprintf(stderr, "SSL_write retry unexpectedly failed.\n");
3058 return false;
3059 }
3060
3061 // Drain the buffer.
3062 char buf[20];
3063 for (unsigned i = 0; i < count; i++) {
3064 if (SSL_read(server.get(), buf, sizeof(buf)) != kChunkLen ||
3065 OPENSSL_memcmp(buf, "hello", kChunkLen) != 0) {
3066 fprintf(stderr, "Failed to read initial records.\n");
3067 return false;
3068 }
3069 }
3070
3071 // Now that there is space, a retry with a larger buffer should flush the
3072 // pending record, skip over that many bytes of input (on assumption they
3073 // are the same), and write the remainder. If SSL_MODE_ENABLE_PARTIAL_WRITE
3074 // is set, this will complete in two steps.
3075 char data3[] = "_____!";
3076 if (enable_partial_write) {
3077 if (SSL_write(client.get(), data3, kChunkLen + 1) != kChunkLen ||
3078 SSL_write(client.get(), data3 + kChunkLen, 1) != 1) {
3079 fprintf(stderr, "SSL_write retry failed.\n");
3080 return false;
3081 }
3082 } else if (SSL_write(client.get(), data3, kChunkLen + 1) != kChunkLen + 1) {
3083 fprintf(stderr, "SSL_write retry failed.\n");
3084 return false;
3085 }
3086
3087 // Check the last write was correct. The data will be spread over two
3088 // records, so SSL_read returns twice.
3089 if (SSL_read(server.get(), buf, sizeof(buf)) != kChunkLen ||
3090 OPENSSL_memcmp(buf, "hello", kChunkLen) != 0 ||
3091 SSL_read(server.get(), buf, sizeof(buf)) != 1 ||
3092 buf[0] != '!') {
3093 fprintf(stderr, "Failed to read write retry.\n");
3094 return false;
3095 }
3096 }
3097
3098 return true;
3099}
3100
David Benjamin0fef3052016-11-18 15:11:10 +09003101static bool ForEachVersion(bool (*test_func)(bool is_dtls,
3102 const SSL_METHOD *method,
3103 uint16_t version)) {
3104 static uint16_t kTLSVersions[] = {
David Benjamin3b584332017-01-24 22:47:18 -05003105 SSL3_VERSION,
3106 TLS1_VERSION,
3107 TLS1_1_VERSION,
3108 TLS1_2_VERSION,
3109// TLS 1.3 requires RSA-PSS, which is disabled for Android system builds.
3110#if !defined(BORINGSSL_ANDROID_SYSTEM)
3111 TLS1_3_VERSION,
3112#endif
David Benjamin0fef3052016-11-18 15:11:10 +09003113 };
3114
3115 static uint16_t kDTLSVersions[] = {
3116 DTLS1_VERSION, DTLS1_2_VERSION,
3117 };
3118
David Benjamin9ef31f02016-10-31 18:01:13 -04003119 for (uint16_t version : kTLSVersions) {
David Benjamin0fef3052016-11-18 15:11:10 +09003120 if (!test_func(false, TLS_method(), version)) {
3121 fprintf(stderr, "Test failed at TLS version %04x.\n", version);
David Benjamin9ef31f02016-10-31 18:01:13 -04003122 return false;
3123 }
David Benjamin0fef3052016-11-18 15:11:10 +09003124 }
David Benjamin9ef31f02016-10-31 18:01:13 -04003125
David Benjamin0fef3052016-11-18 15:11:10 +09003126 for (uint16_t version : kDTLSVersions) {
3127 if (!test_func(true, DTLS_method(), version)) {
3128 fprintf(stderr, "Test failed at DTLS version %04x.\n", version);
David Benjamin9ef31f02016-10-31 18:01:13 -04003129 return false;
3130 }
3131 }
3132
3133 return true;
3134}
3135
Adam Langleye1e78132017-01-31 15:24:31 -08003136TEST(SSLTest, AddChainCertHack) {
3137 // Ensure that we don't accidently break the hack that we have in place to
3138 // keep curl and serf happy when they use an |X509| even after transfering
3139 // ownership.
3140
3141 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
3142 ASSERT_TRUE(ctx);
3143 X509 *cert = GetTestCertificate().release();
3144 ASSERT_TRUE(cert);
3145 SSL_CTX_add0_chain_cert(ctx.get(), cert);
3146
3147 // This should not trigger a use-after-free.
3148 X509_cmp(cert, cert);
3149}
3150
David Benjaminb2ff2622017-02-03 17:06:18 -05003151TEST(SSLTest, GetCertificate) {
3152 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
3153 ASSERT_TRUE(ctx);
3154 bssl::UniquePtr<X509> cert = GetTestCertificate();
3155 ASSERT_TRUE(cert);
3156 ASSERT_TRUE(SSL_CTX_use_certificate(ctx.get(), cert.get()));
3157 bssl::UniquePtr<SSL> ssl(SSL_new(ctx.get()));
3158 ASSERT_TRUE(ssl);
3159
3160 X509 *cert2 = SSL_CTX_get0_certificate(ctx.get());
3161 ASSERT_TRUE(cert2);
3162 X509 *cert3 = SSL_get_certificate(ssl.get());
3163 ASSERT_TRUE(cert3);
3164
3165 // The old and new certificates must be identical.
3166 EXPECT_EQ(0, X509_cmp(cert.get(), cert2));
3167 EXPECT_EQ(0, X509_cmp(cert.get(), cert3));
3168
3169 uint8_t *der = nullptr;
3170 long der_len = i2d_X509(cert.get(), &der);
3171 ASSERT_LT(0, der_len);
3172 bssl::UniquePtr<uint8_t> free_der(der);
3173
3174 uint8_t *der2 = nullptr;
3175 long der2_len = i2d_X509(cert2, &der2);
3176 ASSERT_LT(0, der2_len);
3177 bssl::UniquePtr<uint8_t> free_der2(der2);
3178
3179 uint8_t *der3 = nullptr;
3180 long der3_len = i2d_X509(cert3, &der3);
3181 ASSERT_LT(0, der3_len);
3182 bssl::UniquePtr<uint8_t> free_der3(der3);
3183
3184 // They must also encode identically.
David Benjamin7d7554b2017-02-04 11:48:59 -05003185 EXPECT_EQ(Bytes(der, der_len), Bytes(der2, der2_len));
3186 EXPECT_EQ(Bytes(der, der_len), Bytes(der3, der3_len));
David Benjaminb2ff2622017-02-03 17:06:18 -05003187}
3188
Adam Langleyd04ca952017-02-28 11:26:51 -08003189TEST(SSLTest, SetChainAndKeyMismatch) {
3190 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_with_buffers_method()));
3191 ASSERT_TRUE(ctx);
3192
3193 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
3194 ASSERT_TRUE(key);
3195 bssl::UniquePtr<CRYPTO_BUFFER> leaf = GetChainTestCertificateBuffer();
3196 ASSERT_TRUE(leaf);
3197 std::vector<CRYPTO_BUFFER*> chain = {
3198 leaf.get(),
3199 };
3200
3201 // Should fail because |GetTestKey| doesn't match the chain-test certificate.
3202 ASSERT_FALSE(SSL_CTX_set_chain_and_key(ctx.get(), &chain[0], chain.size(),
3203 key.get(), nullptr));
3204 ERR_clear_error();
3205}
3206
3207TEST(SSLTest, SetChainAndKey) {
3208 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLS_with_buffers_method()));
3209 ASSERT_TRUE(client_ctx);
3210 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(TLS_with_buffers_method()));
3211 ASSERT_TRUE(server_ctx);
3212
3213 bssl::UniquePtr<EVP_PKEY> key = GetChainTestKey();
3214 ASSERT_TRUE(key);
3215 bssl::UniquePtr<CRYPTO_BUFFER> leaf = GetChainTestCertificateBuffer();
3216 ASSERT_TRUE(leaf);
3217 bssl::UniquePtr<CRYPTO_BUFFER> intermediate =
3218 GetChainTestIntermediateBuffer();
3219 ASSERT_TRUE(intermediate);
3220 std::vector<CRYPTO_BUFFER*> chain = {
3221 leaf.get(), intermediate.get(),
3222 };
3223 ASSERT_TRUE(SSL_CTX_set_chain_and_key(server_ctx.get(), &chain[0],
3224 chain.size(), key.get(), nullptr));
3225
3226 SSL_CTX_i_promise_to_verify_certs_after_the_handshake(client_ctx.get());
3227
3228 bssl::UniquePtr<SSL> client, server;
3229 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx.get(),
3230 server_ctx.get(),
3231 nullptr /* no session */));
3232}
3233
David Benjamin91222b82017-03-09 20:10:56 -05003234// Configuring the empty cipher list, though an error, should still modify the
3235// configuration.
3236TEST(SSLTest, EmptyCipherList) {
3237 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
3238 ASSERT_TRUE(ctx);
3239
3240 // Initially, the cipher list is not empty.
3241 EXPECT_NE(0u, sk_SSL_CIPHER_num(SSL_CTX_get_ciphers(ctx.get())));
3242
3243 // Configuring the empty cipher list fails.
3244 EXPECT_FALSE(SSL_CTX_set_cipher_list(ctx.get(), ""));
3245 ERR_clear_error();
3246
3247 // But the cipher list is still updated to empty.
3248 EXPECT_EQ(0u, sk_SSL_CIPHER_num(SSL_CTX_get_ciphers(ctx.get())));
3249}
3250
Adam Langley4c341d02017-03-08 19:33:21 -08003251// ssl_test_ticket_aead_failure_mode enumerates the possible ways in which the
3252// test |SSL_TICKET_AEAD_METHOD| can fail.
3253enum ssl_test_ticket_aead_failure_mode {
3254 ssl_test_ticket_aead_ok = 0,
3255 ssl_test_ticket_aead_seal_fail,
3256 ssl_test_ticket_aead_open_soft_fail,
3257 ssl_test_ticket_aead_open_hard_fail,
3258};
3259
3260struct ssl_test_ticket_aead_state {
3261 unsigned retry_count;
3262 ssl_test_ticket_aead_failure_mode failure_mode;
3263};
3264
3265static int ssl_test_ticket_aead_ex_index_dup(CRYPTO_EX_DATA *to,
3266 const CRYPTO_EX_DATA *from,
3267 void **from_d, int index,
3268 long argl, void *argp) {
3269 abort();
3270}
3271
3272static void ssl_test_ticket_aead_ex_index_free(void *parent, void *ptr,
3273 CRYPTO_EX_DATA *ad, int index,
3274 long argl, void *argp) {
3275 auto state = reinterpret_cast<ssl_test_ticket_aead_state*>(ptr);
3276 if (state == nullptr) {
3277 return;
3278 }
3279
3280 OPENSSL_free(state);
3281}
3282
3283static CRYPTO_once_t g_ssl_test_ticket_aead_ex_index_once = CRYPTO_ONCE_INIT;
3284static int g_ssl_test_ticket_aead_ex_index;
3285
3286static int ssl_test_ticket_aead_get_ex_index() {
3287 CRYPTO_once(&g_ssl_test_ticket_aead_ex_index_once, [] {
3288 g_ssl_test_ticket_aead_ex_index = SSL_get_ex_new_index(
3289 0, nullptr, nullptr, ssl_test_ticket_aead_ex_index_dup,
3290 ssl_test_ticket_aead_ex_index_free);
3291 });
3292 return g_ssl_test_ticket_aead_ex_index;
3293}
3294
3295static size_t ssl_test_ticket_aead_max_overhead(SSL *ssl) {
3296 return 1;
3297}
3298
3299static int ssl_test_ticket_aead_seal(SSL *ssl, uint8_t *out, size_t *out_len,
3300 size_t max_out_len, const uint8_t *in,
3301 size_t in_len) {
3302 auto state = reinterpret_cast<ssl_test_ticket_aead_state *>(
3303 SSL_get_ex_data(ssl, ssl_test_ticket_aead_get_ex_index()));
3304
3305 if (state->failure_mode == ssl_test_ticket_aead_seal_fail ||
3306 max_out_len < in_len + 1) {
3307 return 0;
3308 }
3309
3310 OPENSSL_memmove(out, in, in_len);
3311 out[in_len] = 0xff;
3312 *out_len = in_len + 1;
3313
3314 return 1;
3315}
3316
3317static ssl_ticket_aead_result_t ssl_test_ticket_aead_open(
3318 SSL *ssl, uint8_t *out, size_t *out_len, size_t max_out_len,
3319 const uint8_t *in, size_t in_len) {
3320 auto state = reinterpret_cast<ssl_test_ticket_aead_state *>(
3321 SSL_get_ex_data(ssl, ssl_test_ticket_aead_get_ex_index()));
3322
3323 if (state->retry_count > 0) {
3324 state->retry_count--;
3325 return ssl_ticket_aead_retry;
3326 }
3327
3328 switch (state->failure_mode) {
3329 case ssl_test_ticket_aead_ok:
3330 break;
3331 case ssl_test_ticket_aead_seal_fail:
3332 // If |seal| failed then there shouldn't be any ticket to try and
3333 // decrypt.
3334 abort();
3335 break;
3336 case ssl_test_ticket_aead_open_soft_fail:
3337 return ssl_ticket_aead_ignore_ticket;
3338 case ssl_test_ticket_aead_open_hard_fail:
3339 return ssl_ticket_aead_error;
3340 }
3341
3342 if (in_len == 0 || in[in_len - 1] != 0xff) {
3343 return ssl_ticket_aead_ignore_ticket;
3344 }
3345
3346 if (max_out_len < in_len - 1) {
3347 return ssl_ticket_aead_error;
3348 }
3349
3350 OPENSSL_memmove(out, in, in_len - 1);
3351 *out_len = in_len - 1;
3352 return ssl_ticket_aead_success;
3353}
3354
3355static const SSL_TICKET_AEAD_METHOD kSSLTestTicketMethod = {
3356 ssl_test_ticket_aead_max_overhead,
3357 ssl_test_ticket_aead_seal,
3358 ssl_test_ticket_aead_open,
3359};
3360
3361static void ConnectClientAndServerWithTicketMethod(
3362 bssl::UniquePtr<SSL> *out_client, bssl::UniquePtr<SSL> *out_server,
3363 SSL_CTX *client_ctx, SSL_CTX *server_ctx, unsigned retry_count,
3364 ssl_test_ticket_aead_failure_mode failure_mode, SSL_SESSION *session) {
3365 bssl::UniquePtr<SSL> client(SSL_new(client_ctx)), server(SSL_new(server_ctx));
3366 ASSERT_TRUE(client);
3367 ASSERT_TRUE(server);
3368 SSL_set_connect_state(client.get());
3369 SSL_set_accept_state(server.get());
3370
3371 auto state = reinterpret_cast<ssl_test_ticket_aead_state *>(
3372 OPENSSL_malloc(sizeof(ssl_test_ticket_aead_state)));
3373 ASSERT_TRUE(state);
3374 OPENSSL_memset(state, 0, sizeof(ssl_test_ticket_aead_state));
3375 state->retry_count = retry_count;
3376 state->failure_mode = failure_mode;
3377
3378 ASSERT_TRUE(SSL_set_ex_data(server.get(), ssl_test_ticket_aead_get_ex_index(),
3379 state));
3380
3381 SSL_set_session(client.get(), session);
3382
3383 BIO *bio1, *bio2;
3384 ASSERT_TRUE(BIO_new_bio_pair(&bio1, 0, &bio2, 0));
3385
3386 // SSL_set_bio takes ownership.
3387 SSL_set_bio(client.get(), bio1, bio1);
3388 SSL_set_bio(server.get(), bio2, bio2);
3389
3390 if (CompleteHandshakes(client.get(), server.get())) {
3391 *out_client = std::move(client);
3392 *out_server = std::move(server);
3393 } else {
3394 out_client->reset();
3395 out_server->reset();
3396 }
3397}
3398
3399class TicketAEADMethodTest
3400 : public ::testing::TestWithParam<testing::tuple<
3401 uint16_t, unsigned, ssl_test_ticket_aead_failure_mode>> {};
3402
3403TEST_P(TicketAEADMethodTest, Resume) {
3404 bssl::UniquePtr<X509> cert = GetTestCertificate();
3405 ASSERT_TRUE(cert);
3406 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
3407 ASSERT_TRUE(key);
3408
3409 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(TLS_method()));
3410 ASSERT_TRUE(server_ctx);
3411 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLS_method()));
3412 ASSERT_TRUE(client_ctx);
3413
3414 const uint16_t version = testing::get<0>(GetParam());
3415 const unsigned retry_count = testing::get<1>(GetParam());
3416 const ssl_test_ticket_aead_failure_mode failure_mode =
3417 testing::get<2>(GetParam());
3418
3419 ASSERT_TRUE(SSL_CTX_use_certificate(server_ctx.get(), cert.get()));
3420 ASSERT_TRUE(SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()));
3421 ASSERT_TRUE(SSL_CTX_set_min_proto_version(client_ctx.get(), version));
3422 ASSERT_TRUE(SSL_CTX_set_max_proto_version(client_ctx.get(), version));
3423 ASSERT_TRUE(SSL_CTX_set_min_proto_version(server_ctx.get(), version));
3424 ASSERT_TRUE(SSL_CTX_set_max_proto_version(server_ctx.get(), version));
3425
3426 SSL_CTX_set_session_cache_mode(client_ctx.get(), SSL_SESS_CACHE_BOTH);
3427 SSL_CTX_set_session_cache_mode(server_ctx.get(), SSL_SESS_CACHE_BOTH);
3428 SSL_CTX_set_current_time_cb(client_ctx.get(), FrozenTimeCallback);
3429 SSL_CTX_set_current_time_cb(server_ctx.get(), FrozenTimeCallback);
David Benjamin707af292017-03-10 17:47:18 -05003430 SSL_CTX_sess_set_new_cb(client_ctx.get(), SaveLastSession);
Adam Langley4c341d02017-03-08 19:33:21 -08003431
3432 SSL_CTX_set_ticket_aead_method(server_ctx.get(), &kSSLTestTicketMethod);
3433
3434 bssl::UniquePtr<SSL> client, server;
3435 ConnectClientAndServerWithTicketMethod(&client, &server, client_ctx.get(),
3436 server_ctx.get(), retry_count,
3437 failure_mode, nullptr);
3438 switch (failure_mode) {
3439 case ssl_test_ticket_aead_ok:
3440 case ssl_test_ticket_aead_open_hard_fail:
3441 case ssl_test_ticket_aead_open_soft_fail:
3442 ASSERT_TRUE(client);
3443 break;
3444 case ssl_test_ticket_aead_seal_fail:
3445 EXPECT_FALSE(client);
3446 return;
3447 }
3448 EXPECT_FALSE(SSL_session_reused(client.get()));
3449 EXPECT_FALSE(SSL_session_reused(server.get()));
3450
David Benjamin707af292017-03-10 17:47:18 -05003451 // Run the read loop to account for post-handshake tickets in TLS 1.3.
3452 SSL_read(client.get(), nullptr, 0);
3453
3454 bssl::UniquePtr<SSL_SESSION> session = std::move(g_last_session);
Adam Langley4c341d02017-03-08 19:33:21 -08003455 ConnectClientAndServerWithTicketMethod(&client, &server, client_ctx.get(),
3456 server_ctx.get(), retry_count,
David Benjamin707af292017-03-10 17:47:18 -05003457 failure_mode, session.get());
Adam Langley4c341d02017-03-08 19:33:21 -08003458 switch (failure_mode) {
3459 case ssl_test_ticket_aead_ok:
3460 ASSERT_TRUE(client);
3461 EXPECT_TRUE(SSL_session_reused(client.get()));
3462 EXPECT_TRUE(SSL_session_reused(server.get()));
3463 break;
3464 case ssl_test_ticket_aead_seal_fail:
3465 abort();
3466 break;
3467 case ssl_test_ticket_aead_open_hard_fail:
3468 EXPECT_FALSE(client);
3469 break;
3470 case ssl_test_ticket_aead_open_soft_fail:
3471 ASSERT_TRUE(client);
3472 EXPECT_FALSE(SSL_session_reused(client.get()));
3473 EXPECT_FALSE(SSL_session_reused(server.get()));
3474 }
3475}
3476
3477INSTANTIATE_TEST_CASE_P(
3478 TicketAEADMethodTests, TicketAEADMethodTest,
3479 testing::Combine(
David Benjamin707af292017-03-10 17:47:18 -05003480 testing::Values(TLS1_2_VERSION, TLS1_3_VERSION),
Adam Langley4c341d02017-03-08 19:33:21 -08003481 testing::Values(0, 1, 2),
3482 testing::Values(ssl_test_ticket_aead_ok,
3483 ssl_test_ticket_aead_seal_fail,
3484 ssl_test_ticket_aead_open_soft_fail,
3485 ssl_test_ticket_aead_open_hard_fail)));
3486
David Benjamin96628432017-01-19 19:05:47 -05003487// TODO(davidben): Convert this file to GTest properly.
3488TEST(SSLTest, AllTests) {
Adam Langley10f97f32016-07-12 08:09:33 -07003489 if (!TestCipherRules() ||
Alessandro Ghedini5fd18072016-09-28 21:04:25 +01003490 !TestCurveRules() ||
Adam Langley10f97f32016-07-12 08:09:33 -07003491 !TestSSL_SESSIONEncoding(kOpenSSLSession) ||
3492 !TestSSL_SESSIONEncoding(kCustomSession) ||
3493 !TestSSL_SESSIONEncoding(kBoringSSLSession) ||
3494 !TestBadSSL_SESSIONEncoding(kBadSessionExtraField) ||
3495 !TestBadSSL_SESSIONEncoding(kBadSessionVersion) ||
3496 !TestBadSSL_SESSIONEncoding(kBadSessionTrailingData) ||
David Benjamin10e664b2016-06-20 22:20:47 -04003497 // TODO(svaldez): Update this when TLS 1.3 is enabled by default.
Adam Langley10f97f32016-07-12 08:09:33 -07003498 !TestDefaultVersion(SSL3_VERSION, TLS1_2_VERSION, &TLS_method) ||
3499 !TestDefaultVersion(SSL3_VERSION, SSL3_VERSION, &SSLv3_method) ||
3500 !TestDefaultVersion(TLS1_VERSION, TLS1_VERSION, &TLSv1_method) ||
3501 !TestDefaultVersion(TLS1_1_VERSION, TLS1_1_VERSION, &TLSv1_1_method) ||
3502 !TestDefaultVersion(TLS1_2_VERSION, TLS1_2_VERSION, &TLSv1_2_method) ||
3503 !TestDefaultVersion(TLS1_1_VERSION, TLS1_2_VERSION, &DTLS_method) ||
3504 !TestDefaultVersion(TLS1_1_VERSION, TLS1_1_VERSION, &DTLSv1_method) ||
3505 !TestDefaultVersion(TLS1_2_VERSION, TLS1_2_VERSION, &DTLSv1_2_method) ||
3506 !TestCipherGetRFCName() ||
Steven Valdeza833c352016-11-01 13:39:36 -04003507 // Test the padding extension at TLS 1.2.
3508 !TestPaddingExtension(TLS1_2_VERSION, TLS1_2_VERSION) ||
3509 // Test the padding extension at TLS 1.3 with a TLS 1.2 session, so there
3510 // will be no PSK binder after the padding extension.
3511 !TestPaddingExtension(TLS1_3_VERSION, TLS1_2_VERSION) ||
3512 // Test the padding extension at TLS 1.3 with a TLS 1.3 session, so there
3513 // will be a PSK binder after the padding extension.
3514 !TestPaddingExtension(TLS1_3_VERSION, TLS1_3_DRAFT_VERSION) ||
Adam Langley10f97f32016-07-12 08:09:33 -07003515 !TestInternalSessionCache() ||
David Benjamin0fef3052016-11-18 15:11:10 +09003516 !ForEachVersion(TestSequenceNumber) ||
David Benjamin68f37b72016-11-18 15:14:42 +09003517 !ForEachVersion(TestOneSidedShutdown) ||
David Benjamin0fef3052016-11-18 15:11:10 +09003518 !ForEachVersion(TestGetPeerCertificate) ||
3519 !ForEachVersion(TestRetainOnlySHA256OfCerts) ||
David Benjamina20e5352016-08-02 19:09:41 -04003520 !TestClientHello() ||
David Benjamin0fef3052016-11-18 15:11:10 +09003521 !ForEachVersion(TestSessionIDContext) ||
3522 !ForEachVersion(TestSessionTimeout) ||
3523 !ForEachVersion(TestSNICallback) ||
David Benjamin0fef3052016-11-18 15:11:10 +09003524 !ForEachVersion(TestVersion) ||
David Benjaminb79cc842016-12-07 15:57:14 -05003525 !ForEachVersion(TestALPNCipherAvailable) ||
David Benjamin1444c3a2016-12-20 17:23:11 -05003526 !ForEachVersion(TestSSLClearSessionResumption) ||
David Benjamin48063c22017-01-01 23:56:36 -05003527 !ForEachVersion(TestAutoChain) ||
3528 !ForEachVersion(TestSSLWriteRetry)) {
David Benjamin96628432017-01-19 19:05:47 -05003529 ADD_FAILURE() << "Tests failed";
David Benjaminbb0a17c2014-09-20 15:35:39 -04003530 }
David Benjamin2e521212014-07-16 14:37:51 -04003531}