blob: caa25b7ef9eb0a15704dcd248888c2457b876f28 [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
Matthew Braithwaitecedc6f12017-03-15 19:20:23 -0700125 // selections. Select AES_128_GCM, but order the key exchanges RSA,
David Benjaminfb974e62015-12-16 19:34:22 -0500126 // ECDHE_RSA.
127 {
Matthew Braithwaitecedc6f12017-03-15 19:20:23 -0700128 "ALL:-kECDHE:"
Matthew Braithwaitecedc6f12017-03-15 19:20:23 -0700129 "-kRSA:-ALL:"
David Benjaminfb974e62015-12-16 19:34:22 -0500130 "AESGCM+AES128+aRSA",
131 {
132 {TLS1_CK_RSA_WITH_AES_128_GCM_SHA256, 0},
David Benjaminfb974e62015-12-16 19:34:22 -0500133 {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 Braithwaitecedc6f12017-03-15 19:20:23 -0700185 "!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 Benjamine11726a2017-04-23 12:14:28 -0400309static std::string CipherListToString(ssl_cipher_preference_list_st *list) {
David Benjamin1d77e562015-03-22 17:22:08 -0400310 bool in_group = false;
David Benjamine11726a2017-04-23 12:14:28 -0400311 std::string ret;
David Benjamin1d77e562015-03-22 17:22:08 -0400312 for (size_t i = 0; i < sk_SSL_CIPHER_num(list->ciphers); i++) {
David Benjaminbb0a17c2014-09-20 15:35:39 -0400313 const SSL_CIPHER *cipher = sk_SSL_CIPHER_value(list->ciphers, i);
314 if (!in_group && list->in_group_flags[i]) {
David Benjamine11726a2017-04-23 12:14:28 -0400315 ret += "\t[\n";
David Benjamin1d77e562015-03-22 17:22:08 -0400316 in_group = true;
David Benjaminbb0a17c2014-09-20 15:35:39 -0400317 }
David Benjamine11726a2017-04-23 12:14:28 -0400318 ret += "\t";
David Benjaminbb0a17c2014-09-20 15:35:39 -0400319 if (in_group) {
David Benjamine11726a2017-04-23 12:14:28 -0400320 ret += " ";
David Benjaminbb0a17c2014-09-20 15:35:39 -0400321 }
David Benjamine11726a2017-04-23 12:14:28 -0400322 ret += SSL_CIPHER_get_name(cipher);
323 ret += "\n";
David Benjaminbb0a17c2014-09-20 15:35:39 -0400324 if (in_group && !list->in_group_flags[i]) {
David Benjamine11726a2017-04-23 12:14:28 -0400325 ret += "\t]\n";
David Benjamin1d77e562015-03-22 17:22:08 -0400326 in_group = false;
David Benjaminbb0a17c2014-09-20 15:35:39 -0400327 }
328 }
David Benjamine11726a2017-04-23 12:14:28 -0400329 return ret;
David Benjaminbb0a17c2014-09-20 15:35:39 -0400330}
331
David Benjamine11726a2017-04-23 12:14:28 -0400332static bool CipherListsEqual(ssl_cipher_preference_list_st *list,
333 const std::vector<ExpectedCipher> &expected) {
334 if (sk_SSL_CIPHER_num(list->ciphers) != expected.size()) {
David Benjamin1d77e562015-03-22 17:22:08 -0400335 return false;
David Benjamin65226252015-02-05 16:49:47 -0500336 }
337
David Benjamine11726a2017-04-23 12:14:28 -0400338 for (size_t i = 0; i < expected.size(); i++) {
339 const SSL_CIPHER *cipher = sk_SSL_CIPHER_value(list->ciphers, i);
340 if (expected[i].id != SSL_CIPHER_get_id(cipher) ||
341 expected[i].in_group_flag != list->in_group_flags[i]) {
David Benjamin1d77e562015-03-22 17:22:08 -0400342 return false;
David Benjaminbb0a17c2014-09-20 15:35:39 -0400343 }
344 }
345
David Benjamin1d77e562015-03-22 17:22:08 -0400346 return true;
David Benjaminbb0a17c2014-09-20 15:35:39 -0400347}
348
David Benjamine11726a2017-04-23 12:14:28 -0400349TEST(SSLTest, CipherRules) {
350 for (const CipherTest &t : kCipherTests) {
351 SCOPED_TRACE(t.rule);
352 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
353 ASSERT_TRUE(ctx);
Matt Braithwaiteaf096752015-09-02 19:48:16 -0700354
David Benjamine11726a2017-04-23 12:14:28 -0400355 // Test lax mode.
356 ASSERT_TRUE(SSL_CTX_set_cipher_list(ctx.get(), t.rule));
357 EXPECT_TRUE(CipherListsEqual(ctx->cipher_list, t.expected))
358 << "Cipher rule evaluated to:\n"
359 << CipherListToString(ctx->cipher_list);
360
361 // Test strict mode.
362 if (t.strict_fail) {
363 EXPECT_FALSE(SSL_CTX_set_strict_cipher_list(ctx.get(), t.rule));
364 } else {
365 ASSERT_TRUE(SSL_CTX_set_strict_cipher_list(ctx.get(), t.rule));
366 EXPECT_TRUE(CipherListsEqual(ctx->cipher_list, t.expected))
367 << "Cipher rule evaluated to:\n"
368 << CipherListToString(ctx->cipher_list);
David Benjaminbb0a17c2014-09-20 15:35:39 -0400369 }
370 }
371
David Benjaminfb974e62015-12-16 19:34:22 -0500372 for (const char *rule : kBadRules) {
David Benjamine11726a2017-04-23 12:14:28 -0400373 SCOPED_TRACE(rule);
374 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
375 ASSERT_TRUE(ctx);
376
377 EXPECT_FALSE(SSL_CTX_set_cipher_list(ctx.get(), rule));
David Benjaminbb0a17c2014-09-20 15:35:39 -0400378 ERR_clear_error();
David Benjaminbb0a17c2014-09-20 15:35:39 -0400379 }
380
David Benjaminfb974e62015-12-16 19:34:22 -0500381 for (const char *rule : kMustNotIncludeNull) {
David Benjamine11726a2017-04-23 12:14:28 -0400382 SCOPED_TRACE(rule);
383 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
384 ASSERT_TRUE(ctx);
385
386 ASSERT_TRUE(SSL_CTX_set_strict_cipher_list(ctx.get(), rule));
387 for (size_t i = 0; i < sk_SSL_CIPHER_num(ctx->cipher_list->ciphers); i++) {
388 EXPECT_FALSE(SSL_CIPHER_is_NULL(
389 sk_SSL_CIPHER_value(ctx->cipher_list->ciphers, i)));
Matt Braithwaiteaf096752015-09-02 19:48:16 -0700390 }
391 }
David Benjaminbb0a17c2014-09-20 15:35:39 -0400392}
David Benjamin2e521212014-07-16 14:37:51 -0400393
David Benjamine11726a2017-04-23 12:14:28 -0400394TEST(SSLTest, CurveRules) {
395 for (const CurveTest &t : kCurveTests) {
396 SCOPED_TRACE(t.rule);
397 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
398 ASSERT_TRUE(ctx);
Alessandro Ghedini5fd18072016-09-28 21:04:25 +0100399
David Benjamine11726a2017-04-23 12:14:28 -0400400 ASSERT_TRUE(SSL_CTX_set1_curves_list(ctx.get(), t.rule));
401 ASSERT_EQ(t.expected.size(), ctx->supported_group_list_len);
402 for (size_t i = 0; i < t.expected.size(); i++) {
403 EXPECT_EQ(t.expected[i], ctx->supported_group_list[i]);
Alessandro Ghedini5fd18072016-09-28 21:04:25 +0100404 }
405 }
406
407 for (const char *rule : kBadCurvesLists) {
David Benjamine11726a2017-04-23 12:14:28 -0400408 SCOPED_TRACE(rule);
409 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
410 ASSERT_TRUE(ctx);
411
412 EXPECT_FALSE(SSL_CTX_set1_curves_list(ctx.get(), rule));
Alessandro Ghedini5fd18072016-09-28 21:04:25 +0100413 ERR_clear_error();
414 }
Alessandro Ghedini5fd18072016-09-28 21:04:25 +0100415}
416
Adam Langley364f7a62016-12-12 10:51:00 -0800417// kOpenSSLSession is a serialized SSL_SESSION.
Adam Langley10f97f32016-07-12 08:09:33 -0700418static const char kOpenSSLSession[] =
Adam Langley364f7a62016-12-12 10:51:00 -0800419 "MIIFqgIBAQICAwMEAsAvBCAG5Q1ndq4Yfmbeo1zwLkNRKmCXGdNgWvGT3cskV0yQ"
Adam Langley10f97f32016-07-12 08:09:33 -0700420 "kAQwJlrlzkAWBOWiLj/jJ76D7l+UXoizP2KI2C7I2FccqMmIfFmmkUy32nIJ0mZH"
421 "IWoJoQYCBFRDO46iBAICASyjggR6MIIEdjCCA16gAwIBAgIIK9dUvsPWSlUwDQYJ"
422 "KoZIhvcNAQEFBQAwSTELMAkGA1UEBhMCVVMxEzARBgNVBAoTCkdvb2dsZSBJbmMx"
423 "JTAjBgNVBAMTHEdvb2dsZSBJbnRlcm5ldCBBdXRob3JpdHkgRzIwHhcNMTQxMDA4"
424 "MTIwNzU3WhcNMTUwMTA2MDAwMDAwWjBoMQswCQYDVQQGEwJVUzETMBEGA1UECAwK"
425 "Q2FsaWZvcm5pYTEWMBQGA1UEBwwNTW91bnRhaW4gVmlldzETMBEGA1UECgwKR29v"
426 "Z2xlIEluYzEXMBUGA1UEAwwOd3d3Lmdvb2dsZS5jb20wggEiMA0GCSqGSIb3DQEB"
427 "AQUAA4IBDwAwggEKAoIBAQCcKeLrplAC+Lofy8t/wDwtB6eu72CVp0cJ4V3lknN6"
428 "huH9ct6FFk70oRIh/VBNBBz900jYy+7111Jm1b8iqOTQ9aT5C7SEhNcQFJvqzH3e"
429 "MPkb6ZSWGm1yGF7MCQTGQXF20Sk/O16FSjAynU/b3oJmOctcycWYkY0ytS/k3LBu"
430 "Id45PJaoMqjB0WypqvNeJHC3q5JjCB4RP7Nfx5jjHSrCMhw8lUMW4EaDxjaR9KDh"
431 "PLgjsk+LDIySRSRDaCQGhEOWLJZVLzLo4N6/UlctCHEllpBUSvEOyFga52qroGjg"
432 "rf3WOQ925MFwzd6AK+Ich0gDRg8sQfdLH5OuP1cfLfU1AgMBAAGjggFBMIIBPTAd"
433 "BgNVHSUEFjAUBggrBgEFBQcDAQYIKwYBBQUHAwIwGQYDVR0RBBIwEIIOd3d3Lmdv"
434 "b2dsZS5jb20waAYIKwYBBQUHAQEEXDBaMCsGCCsGAQUFBzAChh9odHRwOi8vcGtp"
435 "Lmdvb2dsZS5jb20vR0lBRzIuY3J0MCsGCCsGAQUFBzABhh9odHRwOi8vY2xpZW50"
436 "czEuZ29vZ2xlLmNvbS9vY3NwMB0GA1UdDgQWBBQ7a+CcxsZByOpc+xpYFcIbnUMZ"
437 "hTAMBgNVHRMBAf8EAjAAMB8GA1UdIwQYMBaAFErdBhYbvPZotXb1gba7Yhq6WoEv"
438 "MBcGA1UdIAQQMA4wDAYKKwYBBAHWeQIFATAwBgNVHR8EKTAnMCWgI6Ahhh9odHRw"
439 "Oi8vcGtpLmdvb2dsZS5jb20vR0lBRzIuY3JsMA0GCSqGSIb3DQEBBQUAA4IBAQCa"
440 "OXCBdoqUy5bxyq+Wrh1zsyyCFim1PH5VU2+yvDSWrgDY8ibRGJmfff3r4Lud5kal"
441 "dKs9k8YlKD3ITG7P0YT/Rk8hLgfEuLcq5cc0xqmE42xJ+Eo2uzq9rYorc5emMCxf"
442 "5L0TJOXZqHQpOEcuptZQ4OjdYMfSxk5UzueUhA3ogZKRcRkdB3WeWRp+nYRhx4St"
443 "o2rt2A0MKmY9165GHUqMK9YaaXHDXqBu7Sefr1uSoAP9gyIJKeihMivsGqJ1TD6Z"
444 "cc6LMe+dN2P8cZEQHtD1y296ul4Mivqk3jatUVL8/hCwgch9A8O4PGZq9WqBfEWm"
445 "IyHh1dPtbg1lOXdYCWtjpAIEAKUDAgEUqQUCAwGJwKqBpwSBpBwUQvoeOk0Kg36S"
446 "YTcLEkXqKwOBfF9vE4KX0NxeLwjcDTpsuh3qXEaZ992r1N38VDcyS6P7I6HBYN9B"
447 "sNHM362zZnY27GpTw+Kwd751CLoXFPoaMOe57dbBpXoro6Pd3BTbf/Tzr88K06yE"
448 "OTDKPNj3+inbMaVigtK4PLyPq+Topyzvx9USFgRvyuoxn0Hgb+R0A3j6SLRuyOdA"
Adam Langley364f7a62016-12-12 10:51:00 -0800449 "i4gv7Y5oliyntgMBAQA=";
Adam Langley10f97f32016-07-12 08:09:33 -0700450
451// kCustomSession is a custom serialized SSL_SESSION generated by
452// filling in missing fields from |kOpenSSLSession|. This includes
453// providing |peer_sha256|, so |peer| is not serialized.
454static const char kCustomSession[] =
455 "MIIBdgIBAQICAwMEAsAvBCAG5Q1ndq4Yfmbeo1zwLkNRKmCXGdNgWvGT3cskV0yQ"
456 "kAQwJlrlzkAWBOWiLj/jJ76D7l+UXoizP2KI2C7I2FccqMmIfFmmkUy32nIJ0mZH"
457 "IWoJoQYCBFRDO46iBAICASykAwQBAqUDAgEUphAEDnd3dy5nb29nbGUuY29tqAcE"
458 "BXdvcmxkqQUCAwGJwKqBpwSBpBwUQvoeOk0Kg36SYTcLEkXqKwOBfF9vE4KX0Nxe"
459 "LwjcDTpsuh3qXEaZ992r1N38VDcyS6P7I6HBYN9BsNHM362zZnY27GpTw+Kwd751"
460 "CLoXFPoaMOe57dbBpXoro6Pd3BTbf/Tzr88K06yEOTDKPNj3+inbMaVigtK4PLyP"
461 "q+Topyzvx9USFgRvyuoxn0Hgb+R0A3j6SLRuyOdAi4gv7Y5oliynrSIEIAYGBgYG"
462 "BgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGrgMEAQevAwQBBLADBAEF";
463
464// kBoringSSLSession is a serialized SSL_SESSION generated from bssl client.
465static const char kBoringSSLSession[] =
466 "MIIRwQIBAQICAwMEAsAvBCDdoGxGK26mR+8lM0uq6+k9xYuxPnwAjpcF9n0Yli9R"
467 "kQQwbyshfWhdi5XQ1++7n2L1qqrcVlmHBPpr6yknT/u4pUrpQB5FZ7vqvNn8MdHf"
468 "9rWgoQYCBFXgs7uiBAICHCCjggR6MIIEdjCCA16gAwIBAgIIf+yfD7Y6UicwDQYJ"
469 "KoZIhvcNAQELBQAwSTELMAkGA1UEBhMCVVMxEzARBgNVBAoTCkdvb2dsZSBJbmMx"
470 "JTAjBgNVBAMTHEdvb2dsZSBJbnRlcm5ldCBBdXRob3JpdHkgRzIwHhcNMTUwODEy"
471 "MTQ1MzE1WhcNMTUxMTEwMDAwMDAwWjBoMQswCQYDVQQGEwJVUzETMBEGA1UECAwK"
472 "Q2FsaWZvcm5pYTEWMBQGA1UEBwwNTW91bnRhaW4gVmlldzETMBEGA1UECgwKR29v"
473 "Z2xlIEluYzEXMBUGA1UEAwwOd3d3Lmdvb2dsZS5jb20wggEiMA0GCSqGSIb3DQEB"
474 "AQUAA4IBDwAwggEKAoIBAQC0MeG5YGQ0t+IeJeoneP/PrhEaieibeKYkbKVLNZpo"
475 "PLuBinvhkXZo3DC133NpCBpy6ZktBwamqyixAyuk/NU6OjgXqwwxfQ7di1AInLIU"
476 "792c7hFyNXSUCG7At8Ifi3YwBX9Ba6u/1d6rWTGZJrdCq3QU11RkKYyTq2KT5mce"
477 "Tv9iGKqSkSTlp8puy/9SZ/3DbU3U+BuqCFqeSlz7zjwFmk35acdCilpJlVDDN5C/"
478 "RCh8/UKc8PaL+cxlt531qoTENvYrflBno14YEZlCBZsPiFeUSILpKEj3Ccwhy0eL"
479 "EucWQ72YZU8mUzXBoXGn0zA0crFl5ci/2sTBBGZsylNBAgMBAAGjggFBMIIBPTAd"
480 "BgNVHSUEFjAUBggrBgEFBQcDAQYIKwYBBQUHAwIwGQYDVR0RBBIwEIIOd3d3Lmdv"
481 "b2dsZS5jb20waAYIKwYBBQUHAQEEXDBaMCsGCCsGAQUFBzAChh9odHRwOi8vcGtp"
482 "Lmdvb2dsZS5jb20vR0lBRzIuY3J0MCsGCCsGAQUFBzABhh9odHRwOi8vY2xpZW50"
483 "czEuZ29vZ2xlLmNvbS9vY3NwMB0GA1UdDgQWBBS/bzHxcE73Q4j3slC4BLbMtLjG"
484 "GjAMBgNVHRMBAf8EAjAAMB8GA1UdIwQYMBaAFErdBhYbvPZotXb1gba7Yhq6WoEv"
485 "MBcGA1UdIAQQMA4wDAYKKwYBBAHWeQIFATAwBgNVHR8EKTAnMCWgI6Ahhh9odHRw"
486 "Oi8vcGtpLmdvb2dsZS5jb20vR0lBRzIuY3JsMA0GCSqGSIb3DQEBCwUAA4IBAQAb"
487 "qdWPZEHk0X7iKPCTHL6S3w6q1eR67goxZGFSM1lk1hjwyu7XcLJuvALVV9uY3ovE"
488 "kQZSHwT+pyOPWQhsSjO+1GyjvCvK/CAwiUmBX+bQRGaqHsRcio7xSbdVcajQ3bXd"
489 "X+s0WdbOpn6MStKAiBVloPlSxEI8pxY6x/BBCnTIk/+DMB17uZlOjG3vbAnkDkP+"
490 "n0OTucD9sHV7EVj9XUxi51nOfNBCN/s7lpUjDS/NJ4k3iwOtbCPswiot8vLO779a"
491 "f07vR03r349Iz/KTzk95rlFtX0IU+KYNxFNsanIXZ+C9FYGRXkwhHcvFb4qMUB1y"
492 "TTlM80jBMOwyjZXmjRAhpAIEAKUDAgEUqQUCAwGJwKqBpwSBpOgebbmn9NRUtMWH"
493 "+eJpqA5JLMFSMCChOsvKey3toBaCNGU7HfAEiiXNuuAdCBoK262BjQc2YYfqFzqH"
494 "zuppopXCvhohx7j/tnCNZIMgLYt/O9SXK2RYI5z8FhCCHvB4CbD5G0LGl5EFP27s"
495 "Jb6S3aTTYPkQe8yZSlxevg6NDwmTogLO9F7UUkaYmVcMQhzssEE2ZRYNwSOU6KjE"
496 "0Yj+8fAiBtbQriIEIN2L8ZlpaVrdN5KFNdvcmOxJu81P8q53X55xQyGTnGWwsgMC"
497 "ARezggvvMIIEdjCCA16gAwIBAgIIf+yfD7Y6UicwDQYJKoZIhvcNAQELBQAwSTEL"
498 "MAkGA1UEBhMCVVMxEzARBgNVBAoTCkdvb2dsZSBJbmMxJTAjBgNVBAMTHEdvb2ds"
499 "ZSBJbnRlcm5ldCBBdXRob3JpdHkgRzIwHhcNMTUwODEyMTQ1MzE1WhcNMTUxMTEw"
500 "MDAwMDAwWjBoMQswCQYDVQQGEwJVUzETMBEGA1UECAwKQ2FsaWZvcm5pYTEWMBQG"
501 "A1UEBwwNTW91bnRhaW4gVmlldzETMBEGA1UECgwKR29vZ2xlIEluYzEXMBUGA1UE"
502 "AwwOd3d3Lmdvb2dsZS5jb20wggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIB"
503 "AQC0MeG5YGQ0t+IeJeoneP/PrhEaieibeKYkbKVLNZpoPLuBinvhkXZo3DC133Np"
504 "CBpy6ZktBwamqyixAyuk/NU6OjgXqwwxfQ7di1AInLIU792c7hFyNXSUCG7At8If"
505 "i3YwBX9Ba6u/1d6rWTGZJrdCq3QU11RkKYyTq2KT5mceTv9iGKqSkSTlp8puy/9S"
506 "Z/3DbU3U+BuqCFqeSlz7zjwFmk35acdCilpJlVDDN5C/RCh8/UKc8PaL+cxlt531"
507 "qoTENvYrflBno14YEZlCBZsPiFeUSILpKEj3Ccwhy0eLEucWQ72YZU8mUzXBoXGn"
508 "0zA0crFl5ci/2sTBBGZsylNBAgMBAAGjggFBMIIBPTAdBgNVHSUEFjAUBggrBgEF"
509 "BQcDAQYIKwYBBQUHAwIwGQYDVR0RBBIwEIIOd3d3Lmdvb2dsZS5jb20waAYIKwYB"
510 "BQUHAQEEXDBaMCsGCCsGAQUFBzAChh9odHRwOi8vcGtpLmdvb2dsZS5jb20vR0lB"
511 "RzIuY3J0MCsGCCsGAQUFBzABhh9odHRwOi8vY2xpZW50czEuZ29vZ2xlLmNvbS9v"
512 "Y3NwMB0GA1UdDgQWBBS/bzHxcE73Q4j3slC4BLbMtLjGGjAMBgNVHRMBAf8EAjAA"
513 "MB8GA1UdIwQYMBaAFErdBhYbvPZotXb1gba7Yhq6WoEvMBcGA1UdIAQQMA4wDAYK"
514 "KwYBBAHWeQIFATAwBgNVHR8EKTAnMCWgI6Ahhh9odHRwOi8vcGtpLmdvb2dsZS5j"
515 "b20vR0lBRzIuY3JsMA0GCSqGSIb3DQEBCwUAA4IBAQAbqdWPZEHk0X7iKPCTHL6S"
516 "3w6q1eR67goxZGFSM1lk1hjwyu7XcLJuvALVV9uY3ovEkQZSHwT+pyOPWQhsSjO+"
517 "1GyjvCvK/CAwiUmBX+bQRGaqHsRcio7xSbdVcajQ3bXdX+s0WdbOpn6MStKAiBVl"
518 "oPlSxEI8pxY6x/BBCnTIk/+DMB17uZlOjG3vbAnkDkP+n0OTucD9sHV7EVj9XUxi"
519 "51nOfNBCN/s7lpUjDS/NJ4k3iwOtbCPswiot8vLO779af07vR03r349Iz/KTzk95"
520 "rlFtX0IU+KYNxFNsanIXZ+C9FYGRXkwhHcvFb4qMUB1yTTlM80jBMOwyjZXmjRAh"
521 "MIID8DCCAtigAwIBAgIDAjqDMA0GCSqGSIb3DQEBCwUAMEIxCzAJBgNVBAYTAlVT"
522 "MRYwFAYDVQQKEw1HZW9UcnVzdCBJbmMuMRswGQYDVQQDExJHZW9UcnVzdCBHbG9i"
523 "YWwgQ0EwHhcNMTMwNDA1MTUxNTU2WhcNMTYxMjMxMjM1OTU5WjBJMQswCQYDVQQG"
524 "EwJVUzETMBEGA1UEChMKR29vZ2xlIEluYzElMCMGA1UEAxMcR29vZ2xlIEludGVy"
525 "bmV0IEF1dGhvcml0eSBHMjCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEB"
526 "AJwqBHdc2FCROgajguDYUEi8iT/xGXAaiEZ+4I/F8YnOIe5a/mENtzJEiaB0C1NP"
527 "VaTOgmKV7utZX8bhBYASxF6UP7xbSDj0U/ck5vuR6RXEz/RTDfRK/J9U3n2+oGtv"
528 "h8DQUB8oMANA2ghzUWx//zo8pzcGjr1LEQTrfSTe5vn8MXH7lNVg8y5Kr0LSy+rE"
529 "ahqyzFPdFUuLH8gZYR/Nnag+YyuENWllhMgZxUYi+FOVvuOAShDGKuy6lyARxzmZ"
530 "EASg8GF6lSWMTlJ14rbtCMoU/M4iarNOz0YDl5cDfsCx3nuvRTPPuj5xt970JSXC"
531 "DTWJnZ37DhF5iR43xa+OcmkCAwEAAaOB5zCB5DAfBgNVHSMEGDAWgBTAephojYn7"
532 "qwVkDBF9qn1luMrMTjAdBgNVHQ4EFgQUSt0GFhu89mi1dvWBtrtiGrpagS8wDgYD"
533 "VR0PAQH/BAQDAgEGMC4GCCsGAQUFBwEBBCIwIDAeBggrBgEFBQcwAYYSaHR0cDov"
534 "L2cuc3ltY2QuY29tMBIGA1UdEwEB/wQIMAYBAf8CAQAwNQYDVR0fBC4wLDAqoCig"
535 "JoYkaHR0cDovL2cuc3ltY2IuY29tL2NybHMvZ3RnbG9iYWwuY3JsMBcGA1UdIAQQ"
536 "MA4wDAYKKwYBBAHWeQIFATANBgkqhkiG9w0BAQsFAAOCAQEAqvqpIM1qZ4PtXtR+"
537 "3h3Ef+AlBgDFJPupyC1tft6dgmUsgWM0Zj7pUsIItMsv91+ZOmqcUHqFBYx90SpI"
538 "hNMJbHzCzTWf84LuUt5oX+QAihcglvcpjZpNy6jehsgNb1aHA30DP9z6eX0hGfnI"
539 "Oi9RdozHQZJxjyXON/hKTAAj78Q1EK7gI4BzfE00LshukNYQHpmEcxpw8u1VDu4X"
540 "Bupn7jLrLN1nBz/2i8Jw3lsA5rsb0zYaImxssDVCbJAJPZPpZAkiDoUGn8JzIdPm"
541 "X4DkjYUiOnMDsWCOrmji9D6X52ASCWg23jrW4kOVWzeBkoEfu43XrVJkFleW2V40"
542 "fsg12DCCA30wggLmoAMCAQICAxK75jANBgkqhkiG9w0BAQUFADBOMQswCQYDVQQG"
543 "EwJVUzEQMA4GA1UEChMHRXF1aWZheDEtMCsGA1UECxMkRXF1aWZheCBTZWN1cmUg"
544 "Q2VydGlmaWNhdGUgQXV0aG9yaXR5MB4XDTAyMDUyMTA0MDAwMFoXDTE4MDgyMTA0"
545 "MDAwMFowQjELMAkGA1UEBhMCVVMxFjAUBgNVBAoTDUdlb1RydXN0IEluYy4xGzAZ"
546 "BgNVBAMTEkdlb1RydXN0IEdsb2JhbCBDQTCCASIwDQYJKoZIhvcNAQEBBQADggEP"
547 "ADCCAQoCggEBANrMGGMw/fQXIxpWflvfPGw45HG3eJHUvKHYTPioQ7YD6U0hBwiI"
548 "2lgvZjkpvQV4i5046AW3an5xpObEYKaw74DkiSgPniXW7YPzraaRx5jJQhg1FJ2t"
549 "mEaSLk/K8YdDwRaVVy1Q74ktgHpXrfLuX2vSAI25FPgUFTXZwEaje3LIkb/JVSvN"
550 "0Jc+nCZkzN/Ogxlxyk7m1NV7qRnNVd7I7NJeOFPlXE+MLf5QIzb8ZubLjqQ5GQC3"
551 "lQI5kQsO/jgu0R0FmvZNPm8PBx2vLB6PYDni+jZTEznUXiYr2z2oFL0y6xgDKFIE"
552 "ceWrMz3hOLsHNoRinHnqFjD0X8Ar6HFr5PkCAwEAAaOB8DCB7TAfBgNVHSMEGDAW"
553 "gBRI5mj5K9KylddH2CMgEE8zmJCf1DAdBgNVHQ4EFgQUwHqYaI2J+6sFZAwRfap9"
554 "ZbjKzE4wDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMCAQYwOgYDVR0fBDMw"
555 "MTAvoC2gK4YpaHR0cDovL2NybC5nZW90cnVzdC5jb20vY3Jscy9zZWN1cmVjYS5j"
556 "cmwwTgYDVR0gBEcwRTBDBgRVHSAAMDswOQYIKwYBBQUHAgEWLWh0dHBzOi8vd3d3"
557 "Lmdlb3RydXN0LmNvbS9yZXNvdXJjZXMvcmVwb3NpdG9yeTANBgkqhkiG9w0BAQUF"
558 "AAOBgQB24RJuTksWEoYwBrKBCM/wCMfHcX5m7sLt1Dsf//DwyE7WQziwuTB9GNBV"
559 "g6JqyzYRnOhIZqNtf7gT1Ef+i1pcc/yu2RsyGTirlzQUqpbS66McFAhJtrvlke+D"
560 "NusdVm/K2rxzY5Dkf3s+Iss9B+1fOHSc4wNQTqGvmO5h8oQ/Eg==";
561
562// kBadSessionExtraField is a custom serialized SSL_SESSION generated by replacing
563// the final (optional) element of |kCustomSession| with tag number 30.
564static const char kBadSessionExtraField[] =
565 "MIIBdgIBAQICAwMEAsAvBCAG5Q1ndq4Yfmbeo1zwLkNRKmCXGdNgWvGT3cskV0yQ"
566 "kAQwJlrlzkAWBOWiLj/jJ76D7l+UXoizP2KI2C7I2FccqMmIfFmmkUy32nIJ0mZH"
567 "IWoJoQYCBFRDO46iBAICASykAwQBAqUDAgEUphAEDnd3dy5nb29nbGUuY29tqAcE"
568 "BXdvcmxkqQUCAwGJwKqBpwSBpBwUQvoeOk0Kg36SYTcLEkXqKwOBfF9vE4KX0Nxe"
569 "LwjcDTpsuh3qXEaZ992r1N38VDcyS6P7I6HBYN9BsNHM362zZnY27GpTw+Kwd751"
570 "CLoXFPoaMOe57dbBpXoro6Pd3BTbf/Tzr88K06yEOTDKPNj3+inbMaVigtK4PLyP"
571 "q+Topyzvx9USFgRvyuoxn0Hgb+R0A3j6SLRuyOdAi4gv7Y5oliynrSIEIAYGBgYG"
572 "BgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGrgMEAQevAwQBBL4DBAEF";
573
574// kBadSessionVersion is a custom serialized SSL_SESSION generated by replacing
575// the version of |kCustomSession| with 2.
576static const char kBadSessionVersion[] =
577 "MIIBdgIBAgICAwMEAsAvBCAG5Q1ndq4Yfmbeo1zwLkNRKmCXGdNgWvGT3cskV0yQ"
578 "kAQwJlrlzkAWBOWiLj/jJ76D7l+UXoizP2KI2C7I2FccqMmIfFmmkUy32nIJ0mZH"
579 "IWoJoQYCBFRDO46iBAICASykAwQBAqUDAgEUphAEDnd3dy5nb29nbGUuY29tqAcE"
580 "BXdvcmxkqQUCAwGJwKqBpwSBpBwUQvoeOk0Kg36SYTcLEkXqKwOBfF9vE4KX0Nxe"
581 "LwjcDTpsuh3qXEaZ992r1N38VDcyS6P7I6HBYN9BsNHM362zZnY27GpTw+Kwd751"
582 "CLoXFPoaMOe57dbBpXoro6Pd3BTbf/Tzr88K06yEOTDKPNj3+inbMaVigtK4PLyP"
583 "q+Topyzvx9USFgRvyuoxn0Hgb+R0A3j6SLRuyOdAi4gv7Y5oliynrSIEIAYGBgYG"
584 "BgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGrgMEAQevAwQBBLADBAEF";
585
586// kBadSessionTrailingData is a custom serialized SSL_SESSION with trailing data
587// appended.
588static const char kBadSessionTrailingData[] =
589 "MIIBdgIBAQICAwMEAsAvBCAG5Q1ndq4Yfmbeo1zwLkNRKmCXGdNgWvGT3cskV0yQ"
590 "kAQwJlrlzkAWBOWiLj/jJ76D7l+UXoizP2KI2C7I2FccqMmIfFmmkUy32nIJ0mZH"
591 "IWoJoQYCBFRDO46iBAICASykAwQBAqUDAgEUphAEDnd3dy5nb29nbGUuY29tqAcE"
592 "BXdvcmxkqQUCAwGJwKqBpwSBpBwUQvoeOk0Kg36SYTcLEkXqKwOBfF9vE4KX0Nxe"
593 "LwjcDTpsuh3qXEaZ992r1N38VDcyS6P7I6HBYN9BsNHM362zZnY27GpTw+Kwd751"
594 "CLoXFPoaMOe57dbBpXoro6Pd3BTbf/Tzr88K06yEOTDKPNj3+inbMaVigtK4PLyP"
595 "q+Topyzvx9USFgRvyuoxn0Hgb+R0A3j6SLRuyOdAi4gv7Y5oliynrSIEIAYGBgYG"
596 "BgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGrgMEAQevAwQBBLADBAEFAAAA";
597
David Benjamin1d77e562015-03-22 17:22:08 -0400598static bool DecodeBase64(std::vector<uint8_t> *out, const char *in) {
David Benjamin751e8892014-10-19 00:59:36 -0400599 size_t len;
David Benjamin751e8892014-10-19 00:59:36 -0400600 if (!EVP_DecodedLength(&len, strlen(in))) {
601 fprintf(stderr, "EVP_DecodedLength failed\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400602 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400603 }
604
David Benjamin1d77e562015-03-22 17:22:08 -0400605 out->resize(len);
David Benjaminef14b2d2015-11-11 14:01:27 -0800606 if (!EVP_DecodeBase64(out->data(), &len, len, (const uint8_t *)in,
David Benjamin751e8892014-10-19 00:59:36 -0400607 strlen(in))) {
608 fprintf(stderr, "EVP_DecodeBase64 failed\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400609 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400610 }
David Benjamin1d77e562015-03-22 17:22:08 -0400611 out->resize(len);
612 return true;
David Benjamin751e8892014-10-19 00:59:36 -0400613}
614
David Benjamin1d77e562015-03-22 17:22:08 -0400615static bool TestSSL_SESSIONEncoding(const char *input_b64) {
David Benjamin751e8892014-10-19 00:59:36 -0400616 const uint8_t *cptr;
617 uint8_t *ptr;
David Benjamin751e8892014-10-19 00:59:36 -0400618
David Benjamin1d77e562015-03-22 17:22:08 -0400619 // Decode the input.
620 std::vector<uint8_t> input;
621 if (!DecodeBase64(&input, input_b64)) {
622 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400623 }
624
David Benjamin1d77e562015-03-22 17:22:08 -0400625 // Verify the SSL_SESSION decodes.
Adam Langley46db7af2017-02-01 15:49:37 -0800626 bssl::UniquePtr<SSL_CTX> ssl_ctx(SSL_CTX_new(TLS_method()));
627 if (!ssl_ctx) {
628 return false;
629 }
630 bssl::UniquePtr<SSL_SESSION> session(
631 SSL_SESSION_from_bytes(input.data(), input.size(), ssl_ctx.get()));
David Benjaminfd67aa82015-06-15 19:41:48 -0400632 if (!session) {
633 fprintf(stderr, "SSL_SESSION_from_bytes failed\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400634 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400635 }
636
David Benjamin1d77e562015-03-22 17:22:08 -0400637 // Verify the SSL_SESSION encoding round-trips.
638 size_t encoded_len;
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700639 bssl::UniquePtr<uint8_t> encoded;
David Benjamin1d77e562015-03-22 17:22:08 -0400640 uint8_t *encoded_raw;
641 if (!SSL_SESSION_to_bytes(session.get(), &encoded_raw, &encoded_len)) {
David Benjamin3cac4502014-10-21 01:46:30 -0400642 fprintf(stderr, "SSL_SESSION_to_bytes failed\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400643 return false;
David Benjamin3cac4502014-10-21 01:46:30 -0400644 }
David Benjamin1d77e562015-03-22 17:22:08 -0400645 encoded.reset(encoded_raw);
646 if (encoded_len != input.size() ||
David Benjamin17cf2cb2016-12-13 01:07:13 -0500647 OPENSSL_memcmp(input.data(), encoded.get(), input.size()) != 0) {
David Benjamin3cac4502014-10-21 01:46:30 -0400648 fprintf(stderr, "SSL_SESSION_to_bytes did not round-trip\n");
Sigbjorn Vik2b23d242015-06-29 15:07:26 +0200649 hexdump(stderr, "Before: ", input.data(), input.size());
650 hexdump(stderr, "After: ", encoded_raw, encoded_len);
David Benjamin1d77e562015-03-22 17:22:08 -0400651 return false;
David Benjamin3cac4502014-10-21 01:46:30 -0400652 }
David Benjamin3cac4502014-10-21 01:46:30 -0400653
David Benjaminfd67aa82015-06-15 19:41:48 -0400654 // Verify the SSL_SESSION also decodes with the legacy API.
David Benjaminef14b2d2015-11-11 14:01:27 -0800655 cptr = input.data();
David Benjaminfd67aa82015-06-15 19:41:48 -0400656 session.reset(d2i_SSL_SESSION(NULL, &cptr, input.size()));
David Benjaminef14b2d2015-11-11 14:01:27 -0800657 if (!session || cptr != input.data() + input.size()) {
David Benjaminfd67aa82015-06-15 19:41:48 -0400658 fprintf(stderr, "d2i_SSL_SESSION failed\n");
659 return false;
660 }
661
David Benjamin1d77e562015-03-22 17:22:08 -0400662 // Verify the SSL_SESSION encoding round-trips via the legacy API.
663 int len = i2d_SSL_SESSION(session.get(), NULL);
664 if (len < 0 || (size_t)len != input.size()) {
David Benjamin751e8892014-10-19 00:59:36 -0400665 fprintf(stderr, "i2d_SSL_SESSION(NULL) returned invalid length\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400666 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400667 }
668
David Benjamin1d77e562015-03-22 17:22:08 -0400669 encoded.reset((uint8_t *)OPENSSL_malloc(input.size()));
670 if (!encoded) {
David Benjamin751e8892014-10-19 00:59:36 -0400671 fprintf(stderr, "malloc failed\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400672 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400673 }
David Benjamin1d77e562015-03-22 17:22:08 -0400674
675 ptr = encoded.get();
676 len = i2d_SSL_SESSION(session.get(), &ptr);
677 if (len < 0 || (size_t)len != input.size()) {
David Benjamin751e8892014-10-19 00:59:36 -0400678 fprintf(stderr, "i2d_SSL_SESSION returned invalid length\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400679 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400680 }
David Benjamin1d77e562015-03-22 17:22:08 -0400681 if (ptr != encoded.get() + input.size()) {
David Benjamin751e8892014-10-19 00:59:36 -0400682 fprintf(stderr, "i2d_SSL_SESSION did not advance ptr correctly\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400683 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400684 }
David Benjamin17cf2cb2016-12-13 01:07:13 -0500685 if (OPENSSL_memcmp(input.data(), encoded.get(), input.size()) != 0) {
David Benjamin751e8892014-10-19 00:59:36 -0400686 fprintf(stderr, "i2d_SSL_SESSION did not round-trip\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400687 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400688 }
689
David Benjamin1d77e562015-03-22 17:22:08 -0400690 return true;
David Benjamin751e8892014-10-19 00:59:36 -0400691}
692
David Benjaminf297e022015-05-28 19:55:29 -0400693static bool TestBadSSL_SESSIONEncoding(const char *input_b64) {
694 std::vector<uint8_t> input;
695 if (!DecodeBase64(&input, input_b64)) {
696 return false;
697 }
698
699 // Verify that the SSL_SESSION fails to decode.
Adam Langley46db7af2017-02-01 15:49:37 -0800700 bssl::UniquePtr<SSL_CTX> ssl_ctx(SSL_CTX_new(TLS_method()));
701 if (!ssl_ctx) {
702 return false;
703 }
704 bssl::UniquePtr<SSL_SESSION> session(
705 SSL_SESSION_from_bytes(input.data(), input.size(), ssl_ctx.get()));
David Benjaminf297e022015-05-28 19:55:29 -0400706 if (session) {
David Benjaminfd67aa82015-06-15 19:41:48 -0400707 fprintf(stderr, "SSL_SESSION_from_bytes unexpectedly succeeded\n");
David Benjaminf297e022015-05-28 19:55:29 -0400708 return false;
709 }
710 ERR_clear_error();
711 return true;
712}
713
David Benjamin10e664b2016-06-20 22:20:47 -0400714static bool TestDefaultVersion(uint16_t min_version, uint16_t max_version,
David Benjamin1d77e562015-03-22 17:22:08 -0400715 const SSL_METHOD *(*method)(void)) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700716 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(method()));
David Benjamin1d77e562015-03-22 17:22:08 -0400717 if (!ctx) {
718 return false;
David Benjamin82c9e902014-12-12 15:55:27 -0500719 }
David Benjaminb6a0a512016-06-21 10:33:21 -0400720 if (ctx->min_version != min_version || ctx->max_version != max_version) {
721 fprintf(stderr, "Got min %04x, max %04x; wanted min %04x, max %04x\n",
722 ctx->min_version, ctx->max_version, min_version, max_version);
723 return false;
724 }
725 return true;
David Benjamin82c9e902014-12-12 15:55:27 -0500726}
727
David Benjamin65226252015-02-05 16:49:47 -0500728typedef struct {
David Benjamin2bdb35c2015-02-21 11:03:06 -0500729 int id;
David Benjamin65226252015-02-05 16:49:47 -0500730 const char *rfc_name;
731} CIPHER_RFC_NAME_TEST;
732
733static const CIPHER_RFC_NAME_TEST kCipherRFCNameTests[] = {
Steven Valdez803c77a2016-09-06 14:13:43 -0400734 {SSL3_CK_RSA_DES_192_CBC3_SHA, "TLS_RSA_WITH_3DES_EDE_CBC_SHA"},
735 {TLS1_CK_RSA_WITH_AES_128_SHA, "TLS_RSA_WITH_AES_128_CBC_SHA"},
Steven Valdez803c77a2016-09-06 14:13:43 -0400736 {TLS1_CK_ECDHE_RSA_WITH_AES_128_SHA256,
737 "TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256"},
738 {TLS1_CK_ECDHE_RSA_WITH_AES_256_SHA384,
739 "TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384"},
740 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256,
741 "TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256"},
742 {TLS1_CK_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256,
743 "TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256"},
744 {TLS1_CK_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384,
745 "TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384"},
746 {TLS1_CK_ECDHE_PSK_WITH_AES_128_CBC_SHA,
747 "TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA"},
748 {TLS1_CK_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256,
749 "TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256"},
750 {TLS1_CK_AES_256_GCM_SHA384, "TLS_AES_256_GCM_SHA384"},
751 {TLS1_CK_AES_128_GCM_SHA256, "TLS_AES_128_GCM_SHA256"},
752 {TLS1_CK_CHACHA20_POLY1305_SHA256, "TLS_CHACHA20_POLY1305_SHA256"},
David Benjamin65226252015-02-05 16:49:47 -0500753};
754
David Benjamine11726a2017-04-23 12:14:28 -0400755TEST(SSLTest, CipherGetRFCName) {
756 for (const CIPHER_RFC_NAME_TEST &t : kCipherRFCNameTests) {
757 SCOPED_TRACE(t.rfc_name);
758
759 const SSL_CIPHER *cipher = SSL_get_cipher_by_value(t.id & 0xffff);
760 ASSERT_TRUE(cipher);
761 bssl::UniquePtr<char> rfc_name(SSL_CIPHER_get_rfc_name(cipher));
762 ASSERT_TRUE(rfc_name);
763
764 EXPECT_STREQ(t.rfc_name, rfc_name.get());
David Benjamin65226252015-02-05 16:49:47 -0500765 }
David Benjamin65226252015-02-05 16:49:47 -0500766}
767
Steven Valdeza833c352016-11-01 13:39:36 -0400768// CreateSessionWithTicket returns a sample |SSL_SESSION| with the specified
769// version and ticket length or nullptr on failure.
770static bssl::UniquePtr<SSL_SESSION> CreateSessionWithTicket(uint16_t version,
771 size_t ticket_len) {
David Benjamin422fe082015-07-21 22:03:43 -0400772 std::vector<uint8_t> der;
773 if (!DecodeBase64(&der, kOpenSSLSession)) {
774 return nullptr;
775 }
Adam Langley46db7af2017-02-01 15:49:37 -0800776
777 bssl::UniquePtr<SSL_CTX> ssl_ctx(SSL_CTX_new(TLS_method()));
778 if (!ssl_ctx) {
779 return nullptr;
780 }
Steven Valdeza833c352016-11-01 13:39:36 -0400781 bssl::UniquePtr<SSL_SESSION> session(
Adam Langley46db7af2017-02-01 15:49:37 -0800782 SSL_SESSION_from_bytes(der.data(), der.size(), ssl_ctx.get()));
David Benjamin422fe082015-07-21 22:03:43 -0400783 if (!session) {
784 return nullptr;
785 }
786
Steven Valdeza833c352016-11-01 13:39:36 -0400787 session->ssl_version = version;
788
David Benjamin422fe082015-07-21 22:03:43 -0400789 // Swap out the ticket for a garbage one.
790 OPENSSL_free(session->tlsext_tick);
791 session->tlsext_tick = reinterpret_cast<uint8_t*>(OPENSSL_malloc(ticket_len));
792 if (session->tlsext_tick == nullptr) {
793 return nullptr;
794 }
David Benjamin17cf2cb2016-12-13 01:07:13 -0500795 OPENSSL_memset(session->tlsext_tick, 'a', ticket_len);
David Benjamin422fe082015-07-21 22:03:43 -0400796 session->tlsext_ticklen = ticket_len;
David Benjamin1269ddd2015-10-18 15:18:55 -0400797
798 // Fix up the timeout.
David Benjamin9b63f292016-11-15 00:44:05 -0500799#if defined(BORINGSSL_UNSAFE_DETERMINISTIC_MODE)
800 session->time = 1234;
801#else
David Benjamin1269ddd2015-10-18 15:18:55 -0400802 session->time = time(NULL);
David Benjamin9b63f292016-11-15 00:44:05 -0500803#endif
David Benjamin422fe082015-07-21 22:03:43 -0400804 return session;
805}
806
David Benjaminafc64de2016-07-19 17:12:41 +0200807static bool GetClientHello(SSL *ssl, std::vector<uint8_t> *out) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700808 bssl::UniquePtr<BIO> bio(BIO_new(BIO_s_mem()));
David Benjaminafc64de2016-07-19 17:12:41 +0200809 if (!bio) {
810 return false;
811 }
812 // Do not configure a reading BIO, but record what's written to a memory BIO.
David Benjamin96a16cd2016-08-11 12:14:47 -0400813 BIO_up_ref(bio.get());
814 SSL_set_bio(ssl, nullptr /* rbio */, bio.get());
David Benjaminafc64de2016-07-19 17:12:41 +0200815 int ret = SSL_connect(ssl);
816 if (ret > 0) {
817 // SSL_connect should fail without a BIO to write to.
818 return false;
819 }
820 ERR_clear_error();
821
822 const uint8_t *client_hello;
823 size_t client_hello_len;
824 if (!BIO_mem_contents(bio.get(), &client_hello, &client_hello_len)) {
825 return false;
826 }
827 *out = std::vector<uint8_t>(client_hello, client_hello + client_hello_len);
828 return true;
829}
830
Steven Valdeza833c352016-11-01 13:39:36 -0400831// GetClientHelloLen creates a client SSL connection with the specified version
832// and ticket length. It returns the length of the ClientHello, not including
833// the record header, on success and zero on error.
834static size_t GetClientHelloLen(uint16_t max_version, uint16_t session_version,
835 size_t ticket_len) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700836 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
Steven Valdeza833c352016-11-01 13:39:36 -0400837 bssl::UniquePtr<SSL_SESSION> session =
838 CreateSessionWithTicket(session_version, ticket_len);
David Benjamin422fe082015-07-21 22:03:43 -0400839 if (!ctx || !session) {
840 return 0;
841 }
Steven Valdeza833c352016-11-01 13:39:36 -0400842
843 // Set a one-element cipher list so the baseline ClientHello is unpadded.
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700844 bssl::UniquePtr<SSL> ssl(SSL_new(ctx.get()));
Steven Valdez2c62fe92016-10-14 12:08:12 -0400845 if (!ssl || !SSL_set_session(ssl.get(), session.get()) ||
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800846 !SSL_set_strict_cipher_list(ssl.get(), "ECDHE-RSA-AES128-GCM-SHA256") ||
Steven Valdeza833c352016-11-01 13:39:36 -0400847 !SSL_set_max_proto_version(ssl.get(), max_version)) {
David Benjamin422fe082015-07-21 22:03:43 -0400848 return 0;
849 }
Steven Valdeza833c352016-11-01 13:39:36 -0400850
David Benjaminafc64de2016-07-19 17:12:41 +0200851 std::vector<uint8_t> client_hello;
852 if (!GetClientHello(ssl.get(), &client_hello) ||
853 client_hello.size() <= SSL3_RT_HEADER_LENGTH) {
David Benjamin422fe082015-07-21 22:03:43 -0400854 return 0;
855 }
Steven Valdeza833c352016-11-01 13:39:36 -0400856
David Benjaminafc64de2016-07-19 17:12:41 +0200857 return client_hello.size() - SSL3_RT_HEADER_LENGTH;
David Benjamin422fe082015-07-21 22:03:43 -0400858}
859
860struct PaddingTest {
861 size_t input_len, padded_len;
862};
863
864static const PaddingTest kPaddingTests[] = {
865 // ClientHellos of length below 0x100 do not require padding.
866 {0xfe, 0xfe},
867 {0xff, 0xff},
868 // ClientHellos of length 0x100 through 0x1fb are padded up to 0x200.
869 {0x100, 0x200},
870 {0x123, 0x200},
871 {0x1fb, 0x200},
872 // ClientHellos of length 0x1fc through 0x1ff get padded beyond 0x200. The
873 // padding extension takes a minimum of four bytes plus one required content
874 // byte. (To work around yet more server bugs, we avoid empty final
875 // extensions.)
876 {0x1fc, 0x201},
877 {0x1fd, 0x202},
878 {0x1fe, 0x203},
879 {0x1ff, 0x204},
880 // Finally, larger ClientHellos need no padding.
881 {0x200, 0x200},
882 {0x201, 0x201},
883};
884
Steven Valdeza833c352016-11-01 13:39:36 -0400885static bool TestPaddingExtension(uint16_t max_version,
886 uint16_t session_version) {
David Benjamin422fe082015-07-21 22:03:43 -0400887 // Sample a baseline length.
Steven Valdeza833c352016-11-01 13:39:36 -0400888 size_t base_len = GetClientHelloLen(max_version, session_version, 1);
David Benjamin422fe082015-07-21 22:03:43 -0400889 if (base_len == 0) {
890 return false;
891 }
892
893 for (const PaddingTest &test : kPaddingTests) {
894 if (base_len > test.input_len) {
Steven Valdeza833c352016-11-01 13:39:36 -0400895 fprintf(stderr,
896 "Baseline ClientHello too long (max_version = %04x, "
897 "session_version = %04x).\n",
898 max_version, session_version);
David Benjamin422fe082015-07-21 22:03:43 -0400899 return false;
900 }
901
Steven Valdeza833c352016-11-01 13:39:36 -0400902 size_t padded_len = GetClientHelloLen(max_version, session_version,
903 1 + test.input_len - base_len);
David Benjamin422fe082015-07-21 22:03:43 -0400904 if (padded_len != test.padded_len) {
Steven Valdeza833c352016-11-01 13:39:36 -0400905 fprintf(stderr,
906 "%u-byte ClientHello padded to %u bytes, not %u (max_version = "
907 "%04x, session_version = %04x).\n",
David Benjamin422fe082015-07-21 22:03:43 -0400908 static_cast<unsigned>(test.input_len),
909 static_cast<unsigned>(padded_len),
Steven Valdeza833c352016-11-01 13:39:36 -0400910 static_cast<unsigned>(test.padded_len), max_version,
911 session_version);
David Benjamin422fe082015-07-21 22:03:43 -0400912 return false;
913 }
914 }
Steven Valdeza833c352016-11-01 13:39:36 -0400915
David Benjamin422fe082015-07-21 22:03:43 -0400916 return true;
917}
918
David Benjamin1d128f32015-09-08 17:41:40 -0400919// Test that |SSL_get_client_CA_list| echoes back the configured parameter even
920// before configuring as a server.
David Benjaminf0d8e222017-02-04 10:58:26 -0500921TEST(SSLTest, ClientCAList) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700922 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
David Benjaminf0d8e222017-02-04 10:58:26 -0500923 ASSERT_TRUE(ctx);
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700924 bssl::UniquePtr<SSL> ssl(SSL_new(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -0500925 ASSERT_TRUE(ssl);
David Benjamin1d128f32015-09-08 17:41:40 -0400926
Adam Langley34b4c822017-02-02 10:57:17 -0800927 bssl::UniquePtr<X509_NAME> name(X509_NAME_new());
928 ASSERT_TRUE(name);
David Benjamin1d128f32015-09-08 17:41:40 -0400929
Adam Langley34b4c822017-02-02 10:57:17 -0800930 bssl::UniquePtr<X509_NAME> name_dup(X509_NAME_dup(name.get()));
931 ASSERT_TRUE(name_dup);
932
933 bssl::UniquePtr<STACK_OF(X509_NAME)> stack(sk_X509_NAME_new_null());
934 ASSERT_TRUE(stack);
935
936 ASSERT_TRUE(sk_X509_NAME_push(stack.get(), name_dup.get()));
937 name_dup.release();
938
939 // |SSL_set_client_CA_list| takes ownership.
940 SSL_set_client_CA_list(ssl.get(), stack.release());
941
942 STACK_OF(X509_NAME) *result = SSL_get_client_CA_list(ssl.get());
943 ASSERT_TRUE(result);
944 ASSERT_EQ(1u, sk_X509_NAME_num(result));
945 EXPECT_EQ(0, X509_NAME_cmp(sk_X509_NAME_value(result, 0), name.get()));
David Benjamin1d128f32015-09-08 17:41:40 -0400946}
947
David Benjamin0f653952015-10-18 14:28:01 -0400948static void AppendSession(SSL_SESSION *session, void *arg) {
949 std::vector<SSL_SESSION*> *out =
950 reinterpret_cast<std::vector<SSL_SESSION*>*>(arg);
951 out->push_back(session);
952}
953
David Benjamine11726a2017-04-23 12:14:28 -0400954// CacheEquals returns true if |ctx|'s session cache consists of |expected|, in
David Benjamin0f653952015-10-18 14:28:01 -0400955// order.
David Benjamine11726a2017-04-23 12:14:28 -0400956static bool CacheEquals(SSL_CTX *ctx,
David Benjamin0f653952015-10-18 14:28:01 -0400957 const std::vector<SSL_SESSION*> &expected) {
958 // Check the linked list.
959 SSL_SESSION *ptr = ctx->session_cache_head;
960 for (SSL_SESSION *session : expected) {
961 if (ptr != session) {
962 return false;
963 }
964 // TODO(davidben): This is an absurd way to denote the end of the list.
965 if (ptr->next ==
966 reinterpret_cast<SSL_SESSION *>(&ctx->session_cache_tail)) {
967 ptr = nullptr;
968 } else {
969 ptr = ptr->next;
970 }
971 }
972 if (ptr != nullptr) {
973 return false;
974 }
975
976 // Check the hash table.
977 std::vector<SSL_SESSION*> actual, expected_copy;
978 lh_SSL_SESSION_doall_arg(SSL_CTX_sessions(ctx), AppendSession, &actual);
979 expected_copy = expected;
980
981 std::sort(actual.begin(), actual.end());
982 std::sort(expected_copy.begin(), expected_copy.end());
983
984 return actual == expected_copy;
985}
986
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700987static bssl::UniquePtr<SSL_SESSION> CreateTestSession(uint32_t number) {
Adam Langley46db7af2017-02-01 15:49:37 -0800988 bssl::UniquePtr<SSL_CTX> ssl_ctx(SSL_CTX_new(TLS_method()));
989 if (!ssl_ctx) {
990 return nullptr;
991 }
992 bssl::UniquePtr<SSL_SESSION> ret(SSL_SESSION_new(ssl_ctx.get()));
David Benjamin0f653952015-10-18 14:28:01 -0400993 if (!ret) {
994 return nullptr;
995 }
996
997 ret->session_id_length = SSL3_SSL_SESSION_ID_LENGTH;
David Benjamin17cf2cb2016-12-13 01:07:13 -0500998 OPENSSL_memset(ret->session_id, 0, ret->session_id_length);
999 OPENSSL_memcpy(ret->session_id, &number, sizeof(number));
David Benjamin0f653952015-10-18 14:28:01 -04001000 return ret;
1001}
1002
David Benjamin0f653952015-10-18 14:28:01 -04001003// Test that the internal session cache behaves as expected.
David Benjamine11726a2017-04-23 12:14:28 -04001004TEST(SSLTest, InternalSessionCache) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001005 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
David Benjamine11726a2017-04-23 12:14:28 -04001006 ASSERT_TRUE(ctx);
David Benjamin0f653952015-10-18 14:28:01 -04001007
1008 // Prepare 10 test sessions.
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001009 std::vector<bssl::UniquePtr<SSL_SESSION>> sessions;
David Benjamin0f653952015-10-18 14:28:01 -04001010 for (int i = 0; i < 10; i++) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001011 bssl::UniquePtr<SSL_SESSION> session = CreateTestSession(i);
David Benjamine11726a2017-04-23 12:14:28 -04001012 ASSERT_TRUE(session);
David Benjamin4f6acaf2015-11-21 03:00:50 -05001013 sessions.push_back(std::move(session));
David Benjamin0f653952015-10-18 14:28:01 -04001014 }
1015
1016 SSL_CTX_sess_set_cache_size(ctx.get(), 5);
1017
1018 // Insert all the test sessions.
David Benjamin4f6acaf2015-11-21 03:00:50 -05001019 for (const auto &session : sessions) {
David Benjamine11726a2017-04-23 12:14:28 -04001020 ASSERT_TRUE(SSL_CTX_add_session(ctx.get(), session.get()));
David Benjamin0f653952015-10-18 14:28:01 -04001021 }
1022
1023 // Only the last five should be in the list.
David Benjamine11726a2017-04-23 12:14:28 -04001024 ASSERT_TRUE(CacheEquals(
1025 ctx.get(), {sessions[9].get(), sessions[8].get(), sessions[7].get(),
1026 sessions[6].get(), sessions[5].get()}));
David Benjamin0f653952015-10-18 14:28:01 -04001027
David Benjamine11726a2017-04-23 12:14:28 -04001028 // Inserting an element already in the cache should fail and leave the cache
1029 // unchanged.
1030 ASSERT_FALSE(SSL_CTX_add_session(ctx.get(), sessions[7].get()));
1031 ASSERT_TRUE(CacheEquals(
1032 ctx.get(), {sessions[9].get(), sessions[8].get(), sessions[7].get(),
1033 sessions[6].get(), sessions[5].get()}));
David Benjamin0f653952015-10-18 14:28:01 -04001034
1035 // Although collisions should be impossible (256-bit session IDs), the cache
1036 // must handle them gracefully.
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001037 bssl::UniquePtr<SSL_SESSION> collision(CreateTestSession(7));
David Benjamine11726a2017-04-23 12:14:28 -04001038 ASSERT_TRUE(collision);
1039 ASSERT_TRUE(SSL_CTX_add_session(ctx.get(), collision.get()));
1040 ASSERT_TRUE(CacheEquals(
1041 ctx.get(), {collision.get(), sessions[9].get(), sessions[8].get(),
1042 sessions[6].get(), sessions[5].get()}));
David Benjamin0f653952015-10-18 14:28:01 -04001043
1044 // Removing sessions behaves correctly.
David Benjamine11726a2017-04-23 12:14:28 -04001045 ASSERT_TRUE(SSL_CTX_remove_session(ctx.get(), sessions[6].get()));
1046 ASSERT_TRUE(CacheEquals(ctx.get(), {collision.get(), sessions[9].get(),
1047 sessions[8].get(), sessions[5].get()}));
David Benjamin0f653952015-10-18 14:28:01 -04001048
1049 // Removing sessions requires an exact match.
David Benjamine11726a2017-04-23 12:14:28 -04001050 ASSERT_FALSE(SSL_CTX_remove_session(ctx.get(), sessions[0].get()));
1051 ASSERT_FALSE(SSL_CTX_remove_session(ctx.get(), sessions[7].get()));
David Benjamin0f653952015-10-18 14:28:01 -04001052
David Benjamine11726a2017-04-23 12:14:28 -04001053 // The cache remains unchanged.
1054 ASSERT_TRUE(CacheEquals(ctx.get(), {collision.get(), sessions[9].get(),
1055 sessions[8].get(), sessions[5].get()}));
David Benjamin0f653952015-10-18 14:28:01 -04001056}
1057
David Benjaminde942382016-02-11 12:02:01 -05001058static uint16_t EpochFromSequence(uint64_t seq) {
1059 return static_cast<uint16_t>(seq >> 48);
1060}
1061
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001062static bssl::UniquePtr<X509> GetTestCertificate() {
David Benjaminde942382016-02-11 12:02:01 -05001063 static const char kCertPEM[] =
1064 "-----BEGIN CERTIFICATE-----\n"
1065 "MIICWDCCAcGgAwIBAgIJAPuwTC6rEJsMMA0GCSqGSIb3DQEBBQUAMEUxCzAJBgNV\n"
1066 "BAYTAkFVMRMwEQYDVQQIDApTb21lLVN0YXRlMSEwHwYDVQQKDBhJbnRlcm5ldCBX\n"
1067 "aWRnaXRzIFB0eSBMdGQwHhcNMTQwNDIzMjA1MDQwWhcNMTcwNDIyMjA1MDQwWjBF\n"
1068 "MQswCQYDVQQGEwJBVTETMBEGA1UECAwKU29tZS1TdGF0ZTEhMB8GA1UECgwYSW50\n"
1069 "ZXJuZXQgV2lkZ2l0cyBQdHkgTHRkMIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKB\n"
1070 "gQDYK8imMuRi/03z0K1Zi0WnvfFHvwlYeyK9Na6XJYaUoIDAtB92kWdGMdAQhLci\n"
1071 "HnAjkXLI6W15OoV3gA/ElRZ1xUpxTMhjP6PyY5wqT5r6y8FxbiiFKKAnHmUcrgfV\n"
1072 "W28tQ+0rkLGMryRtrukXOgXBv7gcrmU7G1jC2a7WqmeI8QIDAQABo1AwTjAdBgNV\n"
1073 "HQ4EFgQUi3XVrMsIvg4fZbf6Vr5sp3Xaha8wHwYDVR0jBBgwFoAUi3XVrMsIvg4f\n"
1074 "Zbf6Vr5sp3Xaha8wDAYDVR0TBAUwAwEB/zANBgkqhkiG9w0BAQUFAAOBgQA76Hht\n"
1075 "ldY9avcTGSwbwoiuIqv0jTL1fHFnzy3RHMLDh+Lpvolc5DSrSJHCP5WuK0eeJXhr\n"
1076 "T5oQpHL9z/cCDLAKCKRa4uV0fhEdOWBqyR9p8y5jJtye72t6CuFUV5iqcpF4BH4f\n"
1077 "j2VNHwsSrJwkD4QUGlUtH7vwnQmyCFxZMmWAJg==\n"
1078 "-----END CERTIFICATE-----\n";
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001079 bssl::UniquePtr<BIO> bio(BIO_new_mem_buf(kCertPEM, strlen(kCertPEM)));
David Benjamin1444c3a2016-12-20 17:23:11 -05001080 return bssl::UniquePtr<X509>(
1081 PEM_read_bio_X509(bio.get(), nullptr, nullptr, nullptr));
David Benjaminde942382016-02-11 12:02:01 -05001082}
1083
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001084static bssl::UniquePtr<EVP_PKEY> GetTestKey() {
David Benjaminde942382016-02-11 12:02:01 -05001085 static const char kKeyPEM[] =
1086 "-----BEGIN RSA PRIVATE KEY-----\n"
1087 "MIICXgIBAAKBgQDYK8imMuRi/03z0K1Zi0WnvfFHvwlYeyK9Na6XJYaUoIDAtB92\n"
1088 "kWdGMdAQhLciHnAjkXLI6W15OoV3gA/ElRZ1xUpxTMhjP6PyY5wqT5r6y8FxbiiF\n"
1089 "KKAnHmUcrgfVW28tQ+0rkLGMryRtrukXOgXBv7gcrmU7G1jC2a7WqmeI8QIDAQAB\n"
1090 "AoGBAIBy09Fd4DOq/Ijp8HeKuCMKTHqTW1xGHshLQ6jwVV2vWZIn9aIgmDsvkjCe\n"
1091 "i6ssZvnbjVcwzSoByhjN8ZCf/i15HECWDFFh6gt0P5z0MnChwzZmvatV/FXCT0j+\n"
1092 "WmGNB/gkehKjGXLLcjTb6dRYVJSCZhVuOLLcbWIV10gggJQBAkEA8S8sGe4ezyyZ\n"
1093 "m4e9r95g6s43kPqtj5rewTsUxt+2n4eVodD+ZUlCULWVNAFLkYRTBCASlSrm9Xhj\n"
1094 "QpmWAHJUkQJBAOVzQdFUaewLtdOJoPCtpYoY1zd22eae8TQEmpGOR11L6kbxLQsk\n"
1095 "aMly/DOnOaa82tqAGTdqDEZgSNmCeKKknmECQAvpnY8GUOVAubGR6c+W90iBuQLj\n"
1096 "LtFp/9ihd2w/PoDwrHZaoUYVcT4VSfJQog/k7kjE4MYXYWL8eEKg3WTWQNECQQDk\n"
1097 "104Wi91Umd1PzF0ijd2jXOERJU1wEKe6XLkYYNHWQAe5l4J4MWj9OdxFXAxIuuR/\n"
1098 "tfDwbqkta4xcux67//khAkEAvvRXLHTaa6VFzTaiiO8SaFsHV3lQyXOtMrBpB5jd\n"
1099 "moZWgjHvB2W9Ckn7sDqsPB+U2tyX0joDdQEyuiMECDY8oQ==\n"
1100 "-----END RSA PRIVATE KEY-----\n";
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001101 bssl::UniquePtr<BIO> bio(BIO_new_mem_buf(kKeyPEM, strlen(kKeyPEM)));
1102 return bssl::UniquePtr<EVP_PKEY>(
David Benjaminde942382016-02-11 12:02:01 -05001103 PEM_read_bio_PrivateKey(bio.get(), nullptr, nullptr, nullptr));
1104}
1105
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001106static bssl::UniquePtr<X509> GetECDSATestCertificate() {
David Benjamin0fc37ef2016-08-17 15:29:46 -04001107 static const char kCertPEM[] =
1108 "-----BEGIN CERTIFICATE-----\n"
1109 "MIIBzzCCAXagAwIBAgIJANlMBNpJfb/rMAkGByqGSM49BAEwRTELMAkGA1UEBhMC\n"
1110 "QVUxEzARBgNVBAgMClNvbWUtU3RhdGUxITAfBgNVBAoMGEludGVybmV0IFdpZGdp\n"
1111 "dHMgUHR5IEx0ZDAeFw0xNDA0MjMyMzIxNTdaFw0xNDA1MjMyMzIxNTdaMEUxCzAJ\n"
1112 "BgNVBAYTAkFVMRMwEQYDVQQIDApTb21lLVN0YXRlMSEwHwYDVQQKDBhJbnRlcm5l\n"
1113 "dCBXaWRnaXRzIFB0eSBMdGQwWTATBgcqhkjOPQIBBggqhkjOPQMBBwNCAATmK2ni\n"
1114 "v2Wfl74vHg2UikzVl2u3qR4NRvvdqakendy6WgHn1peoChj5w8SjHlbifINI2xYa\n"
1115 "HPUdfvGULUvPciLBo1AwTjAdBgNVHQ4EFgQUq4TSrKuV8IJOFngHVVdf5CaNgtEw\n"
1116 "HwYDVR0jBBgwFoAUq4TSrKuV8IJOFngHVVdf5CaNgtEwDAYDVR0TBAUwAwEB/zAJ\n"
1117 "BgcqhkjOPQQBA0gAMEUCIQDyoDVeUTo2w4J5m+4nUIWOcAZ0lVfSKXQA9L4Vh13E\n"
1118 "BwIgfB55FGohg/B6dGh5XxSZmmi08cueFV7mHzJSYV51yRQ=\n"
1119 "-----END CERTIFICATE-----\n";
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001120 bssl::UniquePtr<BIO> bio(BIO_new_mem_buf(kCertPEM, strlen(kCertPEM)));
1121 return bssl::UniquePtr<X509>(PEM_read_bio_X509(bio.get(), nullptr, nullptr, nullptr));
David Benjamin0fc37ef2016-08-17 15:29:46 -04001122}
1123
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001124static bssl::UniquePtr<EVP_PKEY> GetECDSATestKey() {
David Benjamin0fc37ef2016-08-17 15:29:46 -04001125 static const char kKeyPEM[] =
1126 "-----BEGIN PRIVATE KEY-----\n"
1127 "MIGHAgEAMBMGByqGSM49AgEGCCqGSM49AwEHBG0wawIBAQQgBw8IcnrUoEqc3VnJ\n"
1128 "TYlodwi1b8ldMHcO6NHJzgqLtGqhRANCAATmK2niv2Wfl74vHg2UikzVl2u3qR4N\n"
1129 "Rvvdqakendy6WgHn1peoChj5w8SjHlbifINI2xYaHPUdfvGULUvPciLB\n"
1130 "-----END PRIVATE KEY-----\n";
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001131 bssl::UniquePtr<BIO> bio(BIO_new_mem_buf(kKeyPEM, strlen(kKeyPEM)));
1132 return bssl::UniquePtr<EVP_PKEY>(
David Benjamin0fc37ef2016-08-17 15:29:46 -04001133 PEM_read_bio_PrivateKey(bio.get(), nullptr, nullptr, nullptr));
1134}
1135
Adam Langleyd04ca952017-02-28 11:26:51 -08001136static bssl::UniquePtr<CRYPTO_BUFFER> BufferFromPEM(const char *pem) {
1137 bssl::UniquePtr<BIO> bio(BIO_new_mem_buf(pem, strlen(pem)));
1138 char *name, *header;
1139 uint8_t *data;
1140 long data_len;
1141 if (!PEM_read_bio(bio.get(), &name, &header, &data,
1142 &data_len)) {
1143 return nullptr;
1144 }
1145 OPENSSL_free(name);
1146 OPENSSL_free(header);
1147
1148 auto ret = bssl::UniquePtr<CRYPTO_BUFFER>(
1149 CRYPTO_BUFFER_new(data, data_len, nullptr));
1150 OPENSSL_free(data);
1151 return ret;
1152}
1153
1154static bssl::UniquePtr<CRYPTO_BUFFER> GetChainTestCertificateBuffer() {
David Benjamin1444c3a2016-12-20 17:23:11 -05001155 static const char kCertPEM[] =
1156 "-----BEGIN CERTIFICATE-----\n"
1157 "MIIC0jCCAbqgAwIBAgICEAAwDQYJKoZIhvcNAQELBQAwDzENMAsGA1UEAwwEQiBD\n"
1158 "QTAeFw0xNjAyMjgyMDI3MDNaFw0yNjAyMjUyMDI3MDNaMBgxFjAUBgNVBAMMDUNs\n"
1159 "aWVudCBDZXJ0IEEwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDRvaz8\n"
1160 "CC/cshpCafJo4jLkHEoBqDLhdgFelJoAiQUyIqyWl2O7YHPnpJH+TgR7oelzNzt/\n"
1161 "kLRcH89M/TszB6zqyLTC4aqmvzKL0peD/jL2LWBucR0WXIvjA3zoRuF/x86+rYH3\n"
1162 "tHb+xs2PSs8EGL/Ev+ss+qTzTGEn26fuGNHkNw6tOwPpc+o8+wUtzf/kAthamo+c\n"
1163 "IDs2rQ+lP7+aLZTLeU/q4gcLutlzcK5imex5xy2jPkweq48kijK0kIzl1cPlA5d1\n"
1164 "z7C8jU50Pj9X9sQDJTN32j7UYRisJeeYQF8GaaN8SbrDI6zHgKzrRLyxDt/KQa9V\n"
1165 "iLeXANgZi+Xx9KgfAgMBAAGjLzAtMAwGA1UdEwEB/wQCMAAwHQYDVR0lBBYwFAYI\n"
1166 "KwYBBQUHAwEGCCsGAQUFBwMCMA0GCSqGSIb3DQEBCwUAA4IBAQBFEVbmYl+2RtNw\n"
1167 "rDftRDF1v2QUbcN2ouSnQDHxeDQdSgasLzT3ui8iYu0Rw2WWcZ0DV5e0ztGPhWq7\n"
1168 "AO0B120aFRMOY+4+bzu9Q2FFkQqc7/fKTvTDzIJI5wrMnFvUfzzvxh3OHWMYSs/w\n"
1169 "giq33hTKeHEq6Jyk3btCny0Ycecyc3yGXH10sizUfiHlhviCkDuESk8mFDwDDzqW\n"
1170 "ZF0IipzFbEDHoIxLlm3GQxpiLoEV4k8KYJp3R5KBLFyxM6UGPz8h72mIPCJp2RuK\n"
1171 "MYgF91UDvVzvnYm6TfseM2+ewKirC00GOrZ7rEcFvtxnKSqYf4ckqfNdSU1Y+RRC\n"
1172 "1ngWZ7Ih\n"
1173 "-----END CERTIFICATE-----\n";
Adam Langleyd04ca952017-02-28 11:26:51 -08001174 return BufferFromPEM(kCertPEM);
David Benjamin1444c3a2016-12-20 17:23:11 -05001175}
1176
Adam Langleyd04ca952017-02-28 11:26:51 -08001177static bssl::UniquePtr<X509> X509FromBuffer(
1178 bssl::UniquePtr<CRYPTO_BUFFER> buffer) {
1179 if (!buffer) {
1180 return nullptr;
1181 }
1182 const uint8_t *derp = CRYPTO_BUFFER_data(buffer.get());
1183 return bssl::UniquePtr<X509>(
1184 d2i_X509(NULL, &derp, CRYPTO_BUFFER_len(buffer.get())));
1185}
1186
1187static bssl::UniquePtr<X509> GetChainTestCertificate() {
1188 return X509FromBuffer(GetChainTestCertificateBuffer());
1189}
1190
1191static bssl::UniquePtr<CRYPTO_BUFFER> GetChainTestIntermediateBuffer() {
David Benjamin1444c3a2016-12-20 17:23:11 -05001192 static const char kCertPEM[] =
1193 "-----BEGIN CERTIFICATE-----\n"
1194 "MIICwjCCAaqgAwIBAgICEAEwDQYJKoZIhvcNAQELBQAwFDESMBAGA1UEAwwJQyBS\n"
1195 "b290IENBMB4XDTE2MDIyODIwMjcwM1oXDTI2MDIyNTIwMjcwM1owDzENMAsGA1UE\n"
1196 "AwwEQiBDQTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBALsSCYmDip2D\n"
1197 "GkjFxw7ykz26JSjELkl6ArlYjFJ3aT/SCh8qbS4gln7RH8CPBd78oFdfhIKQrwtZ\n"
1198 "3/q21ykD9BAS3qHe2YdcJfm8/kWAy5DvXk6NXU4qX334KofBAEpgdA/igEFq1P1l\n"
1199 "HAuIfZCpMRfT+i5WohVsGi8f/NgpRvVaMONLNfgw57mz1lbtFeBEISmX0kbsuJxF\n"
1200 "Qj/Bwhi5/0HAEXG8e7zN4cEx0yPRvmOATRdVb/8dW2pwOHRJq9R5M0NUkIsTSnL7\n"
1201 "6N/z8hRAHMsV3IudC5Yd7GXW1AGu9a+iKU+Q4xcZCoj0DC99tL4VKujrV1kAeqsM\n"
1202 "cz5/dKzi6+cCAwEAAaMjMCEwDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMC\n"
1203 "AQYwDQYJKoZIhvcNAQELBQADggEBAIIeZiEeNhWWQ8Y4D+AGDwqUUeG8NjCbKrXQ\n"
1204 "BlHg5wZ8xftFaiP1Dp/UAezmx2LNazdmuwrYB8lm3FVTyaPDTKEGIPS4wJKHgqH1\n"
1205 "QPDhqNm85ey7TEtI9oYjsNim/Rb+iGkIAMXaxt58SzxbjvP0kMr1JfJIZbic9vye\n"
1206 "NwIspMFIpP3FB8ywyu0T0hWtCQgL4J47nigCHpOu58deP88fS/Nyz/fyGVWOZ76b\n"
1207 "WhWwgM3P3X95fQ3d7oFPR/bVh0YV+Cf861INwplokXgXQ3/TCQ+HNXeAMWn3JLWv\n"
1208 "XFwk8owk9dq/kQGdndGgy3KTEW4ctPX5GNhf3LJ9Q7dLji4ReQ4=\n"
1209 "-----END CERTIFICATE-----\n";
Adam Langleyd04ca952017-02-28 11:26:51 -08001210 return BufferFromPEM(kCertPEM);
1211}
1212
1213static bssl::UniquePtr<X509> GetChainTestIntermediate() {
1214 return X509FromBuffer(GetChainTestIntermediateBuffer());
David Benjamin1444c3a2016-12-20 17:23:11 -05001215}
1216
1217static bssl::UniquePtr<EVP_PKEY> GetChainTestKey() {
1218 static const char kKeyPEM[] =
1219 "-----BEGIN PRIVATE KEY-----\n"
1220 "MIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQDRvaz8CC/cshpC\n"
1221 "afJo4jLkHEoBqDLhdgFelJoAiQUyIqyWl2O7YHPnpJH+TgR7oelzNzt/kLRcH89M\n"
1222 "/TszB6zqyLTC4aqmvzKL0peD/jL2LWBucR0WXIvjA3zoRuF/x86+rYH3tHb+xs2P\n"
1223 "Ss8EGL/Ev+ss+qTzTGEn26fuGNHkNw6tOwPpc+o8+wUtzf/kAthamo+cIDs2rQ+l\n"
1224 "P7+aLZTLeU/q4gcLutlzcK5imex5xy2jPkweq48kijK0kIzl1cPlA5d1z7C8jU50\n"
1225 "Pj9X9sQDJTN32j7UYRisJeeYQF8GaaN8SbrDI6zHgKzrRLyxDt/KQa9ViLeXANgZ\n"
1226 "i+Xx9KgfAgMBAAECggEBAK0VjSJzkyPaamcyTVSWjo7GdaBGcK60lk657RjR+lK0\n"
1227 "YJ7pkej4oM2hdsVZFsP8Cs4E33nXLa/0pDsRov/qrp0WQm2skwqGMC1I/bZ0WRPk\n"
1228 "wHaDrBBfESWnJDX/AGpVtlyOjPmgmK6J2usMPihQUDkKdAYrVWJePrMIxt1q6BMe\n"
1229 "iczs3qriMmtY3bUc4UyUwJ5fhDLjshHvfuIpYQyI6EXZM6dZksn9LylXJnigY6QJ\n"
1230 "HxOYO0BDwOsZ8yQ8J8afLk88i0GizEkgE1z3REtQUwgWfxr1WV/ud+T6/ZhSAgH9\n"
1231 "042mQvSFZnIUSEsmCvjhWuAunfxHKCTcAoYISWfzWpkCgYEA7gpf3HHU5Tn+CgUn\n"
1232 "1X5uGpG3DmcMgfeGgs2r2f/IIg/5Ac1dfYILiybL1tN9zbyLCJfcbFpWBc9hJL6f\n"
1233 "CPc5hUiwWFJqBJewxQkC1Ae/HakHbip+IZ+Jr0842O4BAArvixk4Lb7/N2Ct9sTE\n"
1234 "NJO6RtK9lbEZ5uK61DglHy8CS2UCgYEA4ZC1o36kPAMQBggajgnucb2yuUEelk0f\n"
1235 "AEr+GI32MGE+93xMr7rAhBoqLg4AITyIfEnOSQ5HwagnIHonBbv1LV/Gf9ursx8Z\n"
1236 "YOGbvT8zzzC+SU1bkDzdjAYnFQVGIjMtKOBJ3K07++ypwX1fr4QsQ8uKL8WSOWwt\n"
1237 "Z3Bym6XiZzMCgYADnhy+2OwHX85AkLt+PyGlPbmuelpyTzS4IDAQbBa6jcuW/2wA\n"
1238 "UE2km75VUXmD+u2R/9zVuLm99NzhFhSMqlUxdV1YukfqMfP5yp1EY6m/5aW7QuIP\n"
1239 "2MDa7TVL9rIFMiVZ09RKvbBbQxjhuzPQKL6X/PPspnhiTefQ+dl2k9xREQKBgHDS\n"
1240 "fMfGNEeAEKezrfSVqxphE9/tXms3L+ZpnCaT+yu/uEr5dTIAawKoQ6i9f/sf1/Sy\n"
1241 "xedsqR+IB+oKrzIDDWMgoJybN4pkZ8E5lzhVQIjFjKgFdWLzzqyW9z1gYfABQPlN\n"
1242 "FiS20WX0vgP1vcKAjdNrHzc9zyHBpgQzDmAj3NZZAoGBAI8vKCKdH7w3aL5CNkZQ\n"
1243 "2buIeWNA2HZazVwAGG5F2TU/LmXfRKnG6dX5bkU+AkBZh56jNZy//hfFSewJB4Kk\n"
1244 "buB7ERSdaNbO21zXt9FEA3+z0RfMd/Zv2vlIWOSB5nzl/7UKti3sribK6s9ZVLfi\n"
1245 "SxpiPQ8d/hmSGwn4ksrWUsJD\n"
1246 "-----END PRIVATE KEY-----\n";
1247 bssl::UniquePtr<BIO> bio(BIO_new_mem_buf(kKeyPEM, strlen(kKeyPEM)));
1248 return bssl::UniquePtr<EVP_PKEY>(
1249 PEM_read_bio_PrivateKey(bio.get(), nullptr, nullptr, nullptr));
1250}
1251
David Benjaminb79cc842016-12-07 15:57:14 -05001252static bool CompleteHandshakes(SSL *client, SSL *server) {
1253 // Drive both their handshakes to completion.
1254 for (;;) {
1255 int client_ret = SSL_do_handshake(client);
1256 int client_err = SSL_get_error(client, client_ret);
1257 if (client_err != SSL_ERROR_NONE &&
1258 client_err != SSL_ERROR_WANT_READ &&
Adam Langley4c341d02017-03-08 19:33:21 -08001259 client_err != SSL_ERROR_WANT_WRITE &&
1260 client_err != SSL_ERROR_PENDING_TICKET) {
David Benjaminb79cc842016-12-07 15:57:14 -05001261 fprintf(stderr, "Client error: %d\n", client_err);
1262 return false;
1263 }
1264
1265 int server_ret = SSL_do_handshake(server);
1266 int server_err = SSL_get_error(server, server_ret);
1267 if (server_err != SSL_ERROR_NONE &&
1268 server_err != SSL_ERROR_WANT_READ &&
Adam Langley4c341d02017-03-08 19:33:21 -08001269 server_err != SSL_ERROR_WANT_WRITE &&
1270 server_err != SSL_ERROR_PENDING_TICKET) {
David Benjaminb79cc842016-12-07 15:57:14 -05001271 fprintf(stderr, "Server error: %d\n", server_err);
1272 return false;
1273 }
1274
1275 if (client_ret == 1 && server_ret == 1) {
1276 break;
1277 }
1278 }
1279
1280 return true;
1281}
1282
1283static bool ConnectClientAndServer(bssl::UniquePtr<SSL> *out_client,
1284 bssl::UniquePtr<SSL> *out_server,
David Benjamina20e5352016-08-02 19:09:41 -04001285 SSL_CTX *client_ctx, SSL_CTX *server_ctx,
1286 SSL_SESSION *session) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001287 bssl::UniquePtr<SSL> client(SSL_new(client_ctx)), server(SSL_new(server_ctx));
David Benjaminde942382016-02-11 12:02:01 -05001288 if (!client || !server) {
1289 return false;
1290 }
1291 SSL_set_connect_state(client.get());
1292 SSL_set_accept_state(server.get());
1293
David Benjamina20e5352016-08-02 19:09:41 -04001294 SSL_set_session(client.get(), session);
1295
David Benjaminde942382016-02-11 12:02:01 -05001296 BIO *bio1, *bio2;
1297 if (!BIO_new_bio_pair(&bio1, 0, &bio2, 0)) {
1298 return false;
1299 }
1300 // SSL_set_bio takes ownership.
1301 SSL_set_bio(client.get(), bio1, bio1);
1302 SSL_set_bio(server.get(), bio2, bio2);
1303
David Benjaminb79cc842016-12-07 15:57:14 -05001304 if (!CompleteHandshakes(client.get(), server.get())) {
1305 return false;
David Benjaminde942382016-02-11 12:02:01 -05001306 }
1307
David Benjamin686bb192016-05-10 15:15:41 -04001308 *out_client = std::move(client);
1309 *out_server = std::move(server);
1310 return true;
1311}
1312
David Benjamin0fef3052016-11-18 15:11:10 +09001313static bool TestSequenceNumber(bool is_dtls, const SSL_METHOD *method,
1314 uint16_t version) {
1315 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(method));
1316 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(method));
1317 if (!server_ctx || !client_ctx ||
1318 !SSL_CTX_set_min_proto_version(client_ctx.get(), version) ||
1319 !SSL_CTX_set_max_proto_version(client_ctx.get(), version) ||
1320 !SSL_CTX_set_min_proto_version(server_ctx.get(), version) ||
1321 !SSL_CTX_set_max_proto_version(server_ctx.get(), version)) {
1322 return false;
1323 }
David Benjamin686bb192016-05-10 15:15:41 -04001324
David Benjamin0fef3052016-11-18 15:11:10 +09001325 bssl::UniquePtr<X509> cert = GetTestCertificate();
1326 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
1327 if (!cert || !key || !SSL_CTX_use_certificate(server_ctx.get(), cert.get()) ||
1328 !SSL_CTX_use_PrivateKey(server_ctx.get(), key.get())) {
1329 return false;
1330 }
David Benjamin686bb192016-05-10 15:15:41 -04001331
David Benjamin0fef3052016-11-18 15:11:10 +09001332 bssl::UniquePtr<SSL> client, server;
1333 if (!ConnectClientAndServer(&client, &server, client_ctx.get(),
1334 server_ctx.get(), nullptr /* no session */)) {
1335 return false;
1336 }
David Benjamin686bb192016-05-10 15:15:41 -04001337
David Benjamin0fef3052016-11-18 15:11:10 +09001338 // Drain any post-handshake messages to ensure there are no unread records
1339 // on either end.
1340 uint8_t byte = 0;
1341 if (SSL_read(client.get(), &byte, 1) > 0 ||
1342 SSL_read(server.get(), &byte, 1) > 0) {
1343 fprintf(stderr, "Received unexpected data.\n");
1344 return false;
1345 }
David Benjaminde942382016-02-11 12:02:01 -05001346
David Benjamin0fef3052016-11-18 15:11:10 +09001347 uint64_t client_read_seq = SSL_get_read_sequence(client.get());
1348 uint64_t client_write_seq = SSL_get_write_sequence(client.get());
1349 uint64_t server_read_seq = SSL_get_read_sequence(server.get());
1350 uint64_t server_write_seq = SSL_get_write_sequence(server.get());
Steven Valdez2c62fe92016-10-14 12:08:12 -04001351
David Benjamin0fef3052016-11-18 15:11:10 +09001352 if (is_dtls) {
1353 // Both client and server must be at epoch 1.
1354 if (EpochFromSequence(client_read_seq) != 1 ||
1355 EpochFromSequence(client_write_seq) != 1 ||
1356 EpochFromSequence(server_read_seq) != 1 ||
1357 EpochFromSequence(server_write_seq) != 1) {
1358 fprintf(stderr, "Bad epochs.\n");
1359 return false;
David Benjaminde942382016-02-11 12:02:01 -05001360 }
David Benjamin0fef3052016-11-18 15:11:10 +09001361
1362 // The next record to be written should exceed the largest received.
1363 if (client_write_seq <= server_read_seq ||
1364 server_write_seq <= client_read_seq) {
1365 fprintf(stderr, "Inconsistent sequence numbers.\n");
1366 return false;
1367 }
1368 } else {
1369 // The next record to be written should equal the next to be received.
1370 if (client_write_seq != server_read_seq ||
1371 server_write_seq != client_read_seq) {
1372 fprintf(stderr, "Inconsistent sequence numbers.\n");
1373 return false;
1374 }
1375 }
1376
1377 // Send a record from client to server.
1378 if (SSL_write(client.get(), &byte, 1) != 1 ||
1379 SSL_read(server.get(), &byte, 1) != 1) {
1380 fprintf(stderr, "Could not send byte.\n");
1381 return false;
1382 }
1383
1384 // The client write and server read sequence numbers should have
1385 // incremented.
1386 if (client_write_seq + 1 != SSL_get_write_sequence(client.get()) ||
1387 server_read_seq + 1 != SSL_get_read_sequence(server.get())) {
1388 fprintf(stderr, "Sequence numbers did not increment.\n");
1389 return false;
David Benjaminde942382016-02-11 12:02:01 -05001390 }
1391
1392 return true;
1393}
1394
David Benjamin68f37b72016-11-18 15:14:42 +09001395static bool TestOneSidedShutdown(bool is_dtls, const SSL_METHOD *method,
1396 uint16_t version) {
1397 // SSL_shutdown is a no-op in DTLS.
1398 if (is_dtls) {
1399 return true;
David Benjamin686bb192016-05-10 15:15:41 -04001400 }
1401
David Benjamin68f37b72016-11-18 15:14:42 +09001402 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(method));
1403 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(method));
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001404 bssl::UniquePtr<X509> cert = GetTestCertificate();
1405 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
David Benjamin68f37b72016-11-18 15:14:42 +09001406 if (!client_ctx || !server_ctx || !cert || !key ||
1407 !SSL_CTX_set_min_proto_version(server_ctx.get(), version) ||
1408 !SSL_CTX_set_max_proto_version(server_ctx.get(), version) ||
1409 !SSL_CTX_set_min_proto_version(client_ctx.get(), version) ||
1410 !SSL_CTX_set_max_proto_version(client_ctx.get(), version) ||
David Benjamin686bb192016-05-10 15:15:41 -04001411 !SSL_CTX_use_certificate(server_ctx.get(), cert.get()) ||
1412 !SSL_CTX_use_PrivateKey(server_ctx.get(), key.get())) {
1413 return false;
1414 }
1415
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001416 bssl::UniquePtr<SSL> client, server;
David Benjamin686bb192016-05-10 15:15:41 -04001417 if (!ConnectClientAndServer(&client, &server, client_ctx.get(),
David Benjamina20e5352016-08-02 19:09:41 -04001418 server_ctx.get(), nullptr /* no session */)) {
David Benjamin686bb192016-05-10 15:15:41 -04001419 return false;
1420 }
1421
1422 // Shut down half the connection. SSL_shutdown will return 0 to signal only
1423 // one side has shut down.
1424 if (SSL_shutdown(client.get()) != 0) {
1425 fprintf(stderr, "Could not shutdown.\n");
1426 return false;
1427 }
1428
1429 // Reading from the server should consume the EOF.
1430 uint8_t byte;
1431 if (SSL_read(server.get(), &byte, 1) != 0 ||
1432 SSL_get_error(server.get(), 0) != SSL_ERROR_ZERO_RETURN) {
1433 fprintf(stderr, "Connection was not shut down cleanly.\n");
1434 return false;
1435 }
1436
1437 // However, the server may continue to write data and then shut down the
1438 // connection.
1439 byte = 42;
1440 if (SSL_write(server.get(), &byte, 1) != 1 ||
1441 SSL_read(client.get(), &byte, 1) != 1 ||
1442 byte != 42) {
1443 fprintf(stderr, "Could not send byte.\n");
1444 return false;
1445 }
1446
1447 // The server may then shutdown the connection.
1448 if (SSL_shutdown(server.get()) != 1 ||
1449 SSL_shutdown(client.get()) != 1) {
1450 fprintf(stderr, "Could not complete shutdown.\n");
1451 return false;
1452 }
1453
1454 return true;
1455}
David Benjamin68f37b72016-11-18 15:14:42 +09001456
David Benjaminf0d8e222017-02-04 10:58:26 -05001457TEST(SSLTest, SessionDuplication) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001458 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLS_method()));
1459 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(TLS_method()));
David Benjaminf0d8e222017-02-04 10:58:26 -05001460 ASSERT_TRUE(client_ctx);
1461 ASSERT_TRUE(server_ctx);
Steven Valdez87eab492016-06-27 16:34:59 -04001462
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001463 bssl::UniquePtr<X509> cert = GetTestCertificate();
1464 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
David Benjaminf0d8e222017-02-04 10:58:26 -05001465 ASSERT_TRUE(cert);
1466 ASSERT_TRUE(key);
1467 ASSERT_TRUE(SSL_CTX_use_certificate(server_ctx.get(), cert.get()));
1468 ASSERT_TRUE(SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()));
Steven Valdez87eab492016-06-27 16:34:59 -04001469
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001470 bssl::UniquePtr<SSL> client, server;
David Benjaminf0d8e222017-02-04 10:58:26 -05001471 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx.get(),
1472 server_ctx.get(),
1473 nullptr /* no session */));
Steven Valdez87eab492016-06-27 16:34:59 -04001474
1475 SSL_SESSION *session0 = SSL_get_session(client.get());
David Benjaminf0d8e222017-02-04 10:58:26 -05001476 bssl::UniquePtr<SSL_SESSION> session1(
1477 SSL_SESSION_dup(session0, SSL_SESSION_DUP_ALL));
1478 ASSERT_TRUE(session1);
David Benjamin4501bd52016-08-01 13:39:41 -04001479
Steven Valdez84b5c002016-08-25 16:30:58 -04001480 session1->not_resumable = 0;
1481
Steven Valdez87eab492016-06-27 16:34:59 -04001482 uint8_t *s0_bytes, *s1_bytes;
1483 size_t s0_len, s1_len;
1484
David Benjaminf0d8e222017-02-04 10:58:26 -05001485 ASSERT_TRUE(SSL_SESSION_to_bytes(session0, &s0_bytes, &s0_len));
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001486 bssl::UniquePtr<uint8_t> free_s0(s0_bytes);
Steven Valdez87eab492016-06-27 16:34:59 -04001487
David Benjaminf0d8e222017-02-04 10:58:26 -05001488 ASSERT_TRUE(SSL_SESSION_to_bytes(session1.get(), &s1_bytes, &s1_len));
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001489 bssl::UniquePtr<uint8_t> free_s1(s1_bytes);
Steven Valdez87eab492016-06-27 16:34:59 -04001490
David Benjamin7d7554b2017-02-04 11:48:59 -05001491 EXPECT_EQ(Bytes(s0_bytes, s0_len), Bytes(s1_bytes, s1_len));
Steven Valdez87eab492016-06-27 16:34:59 -04001492}
David Benjamin686bb192016-05-10 15:15:41 -04001493
David Benjaminf0d8e222017-02-04 10:58:26 -05001494static void ExpectFDs(const SSL *ssl, int rfd, int wfd) {
1495 EXPECT_EQ(rfd, SSL_get_rfd(ssl));
1496 EXPECT_EQ(wfd, SSL_get_wfd(ssl));
David Benjamin5c0fb882016-06-14 14:03:51 -04001497
1498 // The wrapper BIOs are always equal when fds are equal, even if set
1499 // individually.
David Benjaminf0d8e222017-02-04 10:58:26 -05001500 if (rfd == wfd) {
1501 EXPECT_EQ(SSL_get_rbio(ssl), SSL_get_wbio(ssl));
David Benjamin5c0fb882016-06-14 14:03:51 -04001502 }
David Benjamin5c0fb882016-06-14 14:03:51 -04001503}
1504
David Benjaminf0d8e222017-02-04 10:58:26 -05001505TEST(SSLTest, SetFD) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001506 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
David Benjaminf0d8e222017-02-04 10:58:26 -05001507 ASSERT_TRUE(ctx);
David Benjamin5c0fb882016-06-14 14:03:51 -04001508
1509 // Test setting different read and write FDs.
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001510 bssl::UniquePtr<SSL> ssl(SSL_new(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05001511 ASSERT_TRUE(ssl);
1512 EXPECT_TRUE(SSL_set_rfd(ssl.get(), 1));
1513 EXPECT_TRUE(SSL_set_wfd(ssl.get(), 2));
1514 ExpectFDs(ssl.get(), 1, 2);
David Benjamin5c0fb882016-06-14 14:03:51 -04001515
1516 // Test setting the same FD.
1517 ssl.reset(SSL_new(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05001518 ASSERT_TRUE(ssl);
1519 EXPECT_TRUE(SSL_set_fd(ssl.get(), 1));
1520 ExpectFDs(ssl.get(), 1, 1);
David Benjamin5c0fb882016-06-14 14:03:51 -04001521
1522 // Test setting the same FD one side at a time.
1523 ssl.reset(SSL_new(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05001524 ASSERT_TRUE(ssl);
1525 EXPECT_TRUE(SSL_set_rfd(ssl.get(), 1));
1526 EXPECT_TRUE(SSL_set_wfd(ssl.get(), 1));
1527 ExpectFDs(ssl.get(), 1, 1);
David Benjamin5c0fb882016-06-14 14:03:51 -04001528
1529 // Test setting the same FD in the other order.
1530 ssl.reset(SSL_new(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05001531 ASSERT_TRUE(ssl);
1532 EXPECT_TRUE(SSL_set_wfd(ssl.get(), 1));
1533 EXPECT_TRUE(SSL_set_rfd(ssl.get(), 1));
1534 ExpectFDs(ssl.get(), 1, 1);
David Benjamin5c0fb882016-06-14 14:03:51 -04001535
David Benjamin5c0fb882016-06-14 14:03:51 -04001536 // Test changing the read FD partway through.
1537 ssl.reset(SSL_new(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05001538 ASSERT_TRUE(ssl);
1539 EXPECT_TRUE(SSL_set_fd(ssl.get(), 1));
1540 EXPECT_TRUE(SSL_set_rfd(ssl.get(), 2));
1541 ExpectFDs(ssl.get(), 2, 1);
David Benjamin5c0fb882016-06-14 14:03:51 -04001542
1543 // Test changing the write FD partway through.
1544 ssl.reset(SSL_new(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05001545 ASSERT_TRUE(ssl);
1546 EXPECT_TRUE(SSL_set_fd(ssl.get(), 1));
1547 EXPECT_TRUE(SSL_set_wfd(ssl.get(), 2));
1548 ExpectFDs(ssl.get(), 1, 2);
David Benjamin5c0fb882016-06-14 14:03:51 -04001549
1550 // Test a no-op change to the read FD partway through.
1551 ssl.reset(SSL_new(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05001552 ASSERT_TRUE(ssl);
1553 EXPECT_TRUE(SSL_set_fd(ssl.get(), 1));
1554 EXPECT_TRUE(SSL_set_rfd(ssl.get(), 1));
1555 ExpectFDs(ssl.get(), 1, 1);
David Benjamin5c0fb882016-06-14 14:03:51 -04001556
1557 // Test a no-op change to the write FD partway through.
1558 ssl.reset(SSL_new(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05001559 ASSERT_TRUE(ssl);
1560 EXPECT_TRUE(SSL_set_fd(ssl.get(), 1));
1561 EXPECT_TRUE(SSL_set_wfd(ssl.get(), 1));
1562 ExpectFDs(ssl.get(), 1, 1);
David Benjamin5c0fb882016-06-14 14:03:51 -04001563
1564 // ASan builds will implicitly test that the internal |BIO| reference-counting
1565 // is correct.
David Benjamin5c0fb882016-06-14 14:03:51 -04001566}
1567
David Benjaminf0d8e222017-02-04 10:58:26 -05001568TEST(SSLTest, SetBIO) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001569 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
David Benjaminf0d8e222017-02-04 10:58:26 -05001570 ASSERT_TRUE(ctx);
David Benjamin4501bd52016-08-01 13:39:41 -04001571
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001572 bssl::UniquePtr<SSL> ssl(SSL_new(ctx.get()));
1573 bssl::UniquePtr<BIO> bio1(BIO_new(BIO_s_mem())), bio2(BIO_new(BIO_s_mem())),
David Benjamin4501bd52016-08-01 13:39:41 -04001574 bio3(BIO_new(BIO_s_mem()));
David Benjaminf0d8e222017-02-04 10:58:26 -05001575 ASSERT_TRUE(ssl);
1576 ASSERT_TRUE(bio1);
1577 ASSERT_TRUE(bio2);
1578 ASSERT_TRUE(bio3);
David Benjamin4501bd52016-08-01 13:39:41 -04001579
1580 // SSL_set_bio takes one reference when the parameters are the same.
1581 BIO_up_ref(bio1.get());
1582 SSL_set_bio(ssl.get(), bio1.get(), bio1.get());
1583
1584 // Repeating the call does nothing.
1585 SSL_set_bio(ssl.get(), bio1.get(), bio1.get());
1586
1587 // It takes one reference each when the parameters are different.
1588 BIO_up_ref(bio2.get());
1589 BIO_up_ref(bio3.get());
1590 SSL_set_bio(ssl.get(), bio2.get(), bio3.get());
1591
1592 // Repeating the call does nothing.
1593 SSL_set_bio(ssl.get(), bio2.get(), bio3.get());
1594
1595 // It takes one reference when changing only wbio.
1596 BIO_up_ref(bio1.get());
1597 SSL_set_bio(ssl.get(), bio2.get(), bio1.get());
1598
1599 // It takes one reference when changing only rbio and the two are different.
1600 BIO_up_ref(bio3.get());
1601 SSL_set_bio(ssl.get(), bio3.get(), bio1.get());
1602
1603 // If setting wbio to rbio, it takes no additional references.
1604 SSL_set_bio(ssl.get(), bio3.get(), bio3.get());
1605
1606 // From there, wbio may be switched to something else.
1607 BIO_up_ref(bio1.get());
1608 SSL_set_bio(ssl.get(), bio3.get(), bio1.get());
1609
1610 // If setting rbio to wbio, it takes no additional references.
1611 SSL_set_bio(ssl.get(), bio1.get(), bio1.get());
1612
1613 // From there, rbio may be switched to something else, but, for historical
1614 // reasons, it takes a reference to both parameters.
1615 BIO_up_ref(bio1.get());
1616 BIO_up_ref(bio2.get());
1617 SSL_set_bio(ssl.get(), bio2.get(), bio1.get());
1618
1619 // ASAN builds will implicitly test that the internal |BIO| reference-counting
1620 // is correct.
David Benjamin4501bd52016-08-01 13:39:41 -04001621}
1622
David Benjamin25490f22016-07-14 00:22:54 -04001623static int VerifySucceed(X509_STORE_CTX *store_ctx, void *arg) { return 1; }
1624
David Benjamin0fef3052016-11-18 15:11:10 +09001625static bool TestGetPeerCertificate(bool is_dtls, const SSL_METHOD *method,
1626 uint16_t version) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001627 bssl::UniquePtr<X509> cert = GetTestCertificate();
1628 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
David Benjaminadd5e522016-07-14 00:33:24 -04001629 if (!cert || !key) {
1630 return false;
1631 }
1632
David Benjamin0fef3052016-11-18 15:11:10 +09001633 // Configure both client and server to accept any certificate.
1634 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(method));
1635 if (!ctx ||
1636 !SSL_CTX_use_certificate(ctx.get(), cert.get()) ||
1637 !SSL_CTX_use_PrivateKey(ctx.get(), key.get()) ||
1638 !SSL_CTX_set_min_proto_version(ctx.get(), version) ||
1639 !SSL_CTX_set_max_proto_version(ctx.get(), version)) {
1640 return false;
1641 }
1642 SSL_CTX_set_verify(
1643 ctx.get(), SSL_VERIFY_PEER | SSL_VERIFY_FAIL_IF_NO_PEER_CERT, nullptr);
1644 SSL_CTX_set_cert_verify_callback(ctx.get(), VerifySucceed, NULL);
David Benjaminadd5e522016-07-14 00:33:24 -04001645
David Benjamin0fef3052016-11-18 15:11:10 +09001646 bssl::UniquePtr<SSL> client, server;
1647 if (!ConnectClientAndServer(&client, &server, ctx.get(), ctx.get(),
1648 nullptr /* no session */)) {
1649 return false;
1650 }
David Benjaminadd5e522016-07-14 00:33:24 -04001651
David Benjamin0fef3052016-11-18 15:11:10 +09001652 // Client and server should both see the leaf certificate.
1653 bssl::UniquePtr<X509> peer(SSL_get_peer_certificate(server.get()));
1654 if (!peer || X509_cmp(cert.get(), peer.get()) != 0) {
1655 fprintf(stderr, "Server peer certificate did not match.\n");
1656 return false;
1657 }
David Benjaminadd5e522016-07-14 00:33:24 -04001658
David Benjamin0fef3052016-11-18 15:11:10 +09001659 peer.reset(SSL_get_peer_certificate(client.get()));
1660 if (!peer || X509_cmp(cert.get(), peer.get()) != 0) {
1661 fprintf(stderr, "Client peer certificate did not match.\n");
1662 return false;
1663 }
David Benjaminadd5e522016-07-14 00:33:24 -04001664
David Benjamin0fef3052016-11-18 15:11:10 +09001665 // However, for historical reasons, the chain includes the leaf on the
1666 // client, but does not on the server.
1667 if (sk_X509_num(SSL_get_peer_cert_chain(client.get())) != 1) {
1668 fprintf(stderr, "Client peer chain was incorrect.\n");
1669 return false;
1670 }
David Benjaminadd5e522016-07-14 00:33:24 -04001671
David Benjamin0fef3052016-11-18 15:11:10 +09001672 if (sk_X509_num(SSL_get_peer_cert_chain(server.get())) != 0) {
1673 fprintf(stderr, "Server peer chain was incorrect.\n");
1674 return false;
David Benjaminadd5e522016-07-14 00:33:24 -04001675 }
1676
1677 return true;
1678}
1679
David Benjamin0fef3052016-11-18 15:11:10 +09001680static bool TestRetainOnlySHA256OfCerts(bool is_dtls, const SSL_METHOD *method,
1681 uint16_t version) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001682 bssl::UniquePtr<X509> cert = GetTestCertificate();
1683 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
David Benjamin25490f22016-07-14 00:22:54 -04001684 if (!cert || !key) {
1685 return false;
1686 }
1687
1688 uint8_t *cert_der = NULL;
1689 int cert_der_len = i2d_X509(cert.get(), &cert_der);
1690 if (cert_der_len < 0) {
1691 return false;
1692 }
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001693 bssl::UniquePtr<uint8_t> free_cert_der(cert_der);
David Benjamin25490f22016-07-14 00:22:54 -04001694
1695 uint8_t cert_sha256[SHA256_DIGEST_LENGTH];
1696 SHA256(cert_der, cert_der_len, cert_sha256);
1697
David Benjamin0fef3052016-11-18 15:11:10 +09001698 // Configure both client and server to accept any certificate, but the
1699 // server must retain only the SHA-256 of the peer.
1700 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(method));
1701 if (!ctx ||
1702 !SSL_CTX_use_certificate(ctx.get(), cert.get()) ||
1703 !SSL_CTX_use_PrivateKey(ctx.get(), key.get()) ||
1704 !SSL_CTX_set_min_proto_version(ctx.get(), version) ||
1705 !SSL_CTX_set_max_proto_version(ctx.get(), version)) {
1706 return false;
1707 }
1708 SSL_CTX_set_verify(
1709 ctx.get(), SSL_VERIFY_PEER | SSL_VERIFY_FAIL_IF_NO_PEER_CERT, nullptr);
1710 SSL_CTX_set_cert_verify_callback(ctx.get(), VerifySucceed, NULL);
1711 SSL_CTX_set_retain_only_sha256_of_client_certs(ctx.get(), 1);
David Benjamin25490f22016-07-14 00:22:54 -04001712
David Benjamin0fef3052016-11-18 15:11:10 +09001713 bssl::UniquePtr<SSL> client, server;
1714 if (!ConnectClientAndServer(&client, &server, ctx.get(), ctx.get(),
1715 nullptr /* no session */)) {
1716 return false;
1717 }
David Benjamin25490f22016-07-14 00:22:54 -04001718
David Benjamin0fef3052016-11-18 15:11:10 +09001719 // The peer certificate has been dropped.
1720 bssl::UniquePtr<X509> peer(SSL_get_peer_certificate(server.get()));
1721 if (peer) {
1722 fprintf(stderr, "Peer certificate was retained.\n");
1723 return false;
1724 }
David Benjamin25490f22016-07-14 00:22:54 -04001725
David Benjamin0fef3052016-11-18 15:11:10 +09001726 SSL_SESSION *session = SSL_get_session(server.get());
1727 if (!session->peer_sha256_valid) {
1728 fprintf(stderr, "peer_sha256_valid was not set.\n");
1729 return false;
1730 }
David Benjamin25490f22016-07-14 00:22:54 -04001731
David Benjamin17cf2cb2016-12-13 01:07:13 -05001732 if (OPENSSL_memcmp(cert_sha256, session->peer_sha256, SHA256_DIGEST_LENGTH) !=
1733 0) {
David Benjamin0fef3052016-11-18 15:11:10 +09001734 fprintf(stderr, "peer_sha256 did not match.\n");
1735 return false;
David Benjamin25490f22016-07-14 00:22:54 -04001736 }
1737
1738 return true;
1739}
1740
David Benjaminafc64de2016-07-19 17:12:41 +02001741static bool ClientHelloMatches(uint16_t version, const uint8_t *expected,
1742 size_t expected_len) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001743 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
Matthew Braithwaitecedc6f12017-03-15 19:20:23 -07001744 // Our default cipher list varies by CPU capabilities, so manually place the
1745 // ChaCha20 ciphers in front.
Matthew Braithwaite7e06de52017-04-10 15:52:14 -07001746 const char* cipher_list = "CHACHA20:ALL";
David Benjamin2dc02042016-09-19 19:57:37 -04001747 if (!ctx ||
David Benjamin3cfeb952017-03-01 16:48:38 -05001748 // SSLv3 is off by default.
1749 !SSL_CTX_set_min_proto_version(ctx.get(), SSL3_VERSION) ||
David Benjamine4706902016-09-20 15:12:23 -04001750 !SSL_CTX_set_max_proto_version(ctx.get(), version) ||
Matthew Braithwaitecedc6f12017-03-15 19:20:23 -07001751 !SSL_CTX_set_strict_cipher_list(ctx.get(), cipher_list)) {
David Benjaminafc64de2016-07-19 17:12:41 +02001752 return false;
1753 }
David Benjamin2dc02042016-09-19 19:57:37 -04001754
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001755 bssl::UniquePtr<SSL> ssl(SSL_new(ctx.get()));
David Benjaminafc64de2016-07-19 17:12:41 +02001756 if (!ssl) {
1757 return false;
1758 }
1759 std::vector<uint8_t> client_hello;
1760 if (!GetClientHello(ssl.get(), &client_hello)) {
1761 return false;
1762 }
1763
1764 // Zero the client_random.
1765 constexpr size_t kRandomOffset = 1 + 2 + 2 + // record header
1766 1 + 3 + // handshake message header
1767 2; // client_version
1768 if (client_hello.size() < kRandomOffset + SSL3_RANDOM_SIZE) {
1769 fprintf(stderr, "ClientHello for version %04x too short.\n", version);
1770 return false;
1771 }
David Benjamin17cf2cb2016-12-13 01:07:13 -05001772 OPENSSL_memset(client_hello.data() + kRandomOffset, 0, SSL3_RANDOM_SIZE);
David Benjaminafc64de2016-07-19 17:12:41 +02001773
1774 if (client_hello.size() != expected_len ||
David Benjamin17cf2cb2016-12-13 01:07:13 -05001775 OPENSSL_memcmp(client_hello.data(), expected, expected_len) != 0) {
David Benjaminafc64de2016-07-19 17:12:41 +02001776 fprintf(stderr, "ClientHello for version %04x did not match:\n", version);
1777 fprintf(stderr, "Got:\n\t");
1778 for (size_t i = 0; i < client_hello.size(); i++) {
1779 fprintf(stderr, "0x%02x, ", client_hello[i]);
1780 }
1781 fprintf(stderr, "\nWanted:\n\t");
1782 for (size_t i = 0; i < expected_len; i++) {
1783 fprintf(stderr, "0x%02x, ", expected[i]);
1784 }
1785 fprintf(stderr, "\n");
1786 return false;
1787 }
1788
1789 return true;
1790}
1791
1792// Tests that our ClientHellos do not change unexpectedly.
1793static bool TestClientHello() {
1794 static const uint8_t kSSL3ClientHello[] = {
Matt Braithwaite9c8c4182016-08-24 14:36:54 -07001795 0x16,
1796 0x03, 0x00,
Matthew Braithwaitecedc6f12017-03-15 19:20:23 -07001797 0x00, 0x3b,
Matt Braithwaite9c8c4182016-08-24 14:36:54 -07001798 0x01,
Matthew Braithwaitecedc6f12017-03-15 19:20:23 -07001799 0x00, 0x00, 0x37,
Matt Braithwaite9c8c4182016-08-24 14:36:54 -07001800 0x03, 0x00,
1801 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1802 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1803 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1804 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1805 0x00,
Matthew Braithwaitecedc6f12017-03-15 19:20:23 -07001806 0x00, 0x10,
Matt Braithwaite9c8c4182016-08-24 14:36:54 -07001807 0xc0, 0x09,
1808 0xc0, 0x13,
Matt Braithwaite9c8c4182016-08-24 14:36:54 -07001809 0xc0, 0x0a,
1810 0xc0, 0x14,
Matt Braithwaite9c8c4182016-08-24 14:36:54 -07001811 0x00, 0x2f,
1812 0x00, 0x35,
1813 0x00, 0x0a,
1814 0x00, 0xff, 0x01, 0x00,
David Benjaminafc64de2016-07-19 17:12:41 +02001815 };
1816 if (!ClientHelloMatches(SSL3_VERSION, kSSL3ClientHello,
1817 sizeof(kSSL3ClientHello))) {
1818 return false;
1819 }
1820
1821 static const uint8_t kTLS1ClientHello[] = {
Matt Braithwaite9c8c4182016-08-24 14:36:54 -07001822 0x16,
1823 0x03, 0x01,
Matthew Braithwaitecedc6f12017-03-15 19:20:23 -07001824 0x00, 0x5a,
Matt Braithwaite9c8c4182016-08-24 14:36:54 -07001825 0x01,
Matthew Braithwaitecedc6f12017-03-15 19:20:23 -07001826 0x00, 0x00, 0x56,
Matt Braithwaite9c8c4182016-08-24 14:36:54 -07001827 0x03, 0x01,
1828 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1829 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1830 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1831 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1832 0x00,
Matthew Braithwaitecedc6f12017-03-15 19:20:23 -07001833 0x00, 0x0e,
Matt Braithwaite9c8c4182016-08-24 14:36:54 -07001834 0xc0, 0x09,
1835 0xc0, 0x13,
Matt Braithwaite9c8c4182016-08-24 14:36:54 -07001836 0xc0, 0x0a,
1837 0xc0, 0x14,
Matt Braithwaite9c8c4182016-08-24 14:36:54 -07001838 0x00, 0x2f,
1839 0x00, 0x35,
1840 0x00, 0x0a,
David Benjaminafc64de2016-07-19 17:12:41 +02001841 0x01, 0x00, 0x00, 0x1f, 0xff, 0x01, 0x00, 0x01, 0x00, 0x00, 0x17, 0x00,
1842 0x00, 0x00, 0x23, 0x00, 0x00, 0x00, 0x0b, 0x00, 0x02, 0x01, 0x00, 0x00,
1843 0x0a, 0x00, 0x08, 0x00, 0x06, 0x00, 0x1d, 0x00, 0x17, 0x00, 0x18,
1844 };
1845 if (!ClientHelloMatches(TLS1_VERSION, kTLS1ClientHello,
1846 sizeof(kTLS1ClientHello))) {
1847 return false;
1848 }
1849
1850 static const uint8_t kTLS11ClientHello[] = {
Matt Braithwaite9c8c4182016-08-24 14:36:54 -07001851 0x16,
1852 0x03, 0x01,
Matthew Braithwaitecedc6f12017-03-15 19:20:23 -07001853 0x00, 0x5a,
Matt Braithwaite9c8c4182016-08-24 14:36:54 -07001854 0x01,
Matthew Braithwaitecedc6f12017-03-15 19:20:23 -07001855 0x00, 0x00, 0x56,
Matt Braithwaite9c8c4182016-08-24 14:36:54 -07001856 0x03, 0x02,
1857 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1858 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1859 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1860 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1861 0x00,
Matthew Braithwaitecedc6f12017-03-15 19:20:23 -07001862 0x00, 0x0e,
Matt Braithwaite9c8c4182016-08-24 14:36:54 -07001863 0xc0, 0x09,
1864 0xc0, 0x13,
Matt Braithwaite9c8c4182016-08-24 14:36:54 -07001865 0xc0, 0x0a,
1866 0xc0, 0x14,
Matt Braithwaite9c8c4182016-08-24 14:36:54 -07001867 0x00, 0x2f,
1868 0x00, 0x35,
1869 0x00, 0x0a,
David Benjaminafc64de2016-07-19 17:12:41 +02001870 0x01, 0x00, 0x00, 0x1f, 0xff, 0x01, 0x00, 0x01, 0x00, 0x00, 0x17, 0x00,
1871 0x00, 0x00, 0x23, 0x00, 0x00, 0x00, 0x0b, 0x00, 0x02, 0x01, 0x00, 0x00,
1872 0x0a, 0x00, 0x08, 0x00, 0x06, 0x00, 0x1d, 0x00, 0x17, 0x00, 0x18,
1873 };
1874 if (!ClientHelloMatches(TLS1_1_VERSION, kTLS11ClientHello,
1875 sizeof(kTLS11ClientHello))) {
1876 return false;
1877 }
1878
David Benjamin3b584332017-01-24 22:47:18 -05001879 // kTLS12ClientHello assumes RSA-PSS, which is disabled for Android system
1880 // builds.
1881#if defined(BORINGSSL_ANDROID_SYSTEM)
1882 return true;
1883#endif
1884
David Benjaminafc64de2016-07-19 17:12:41 +02001885 static const uint8_t kTLS12ClientHello[] = {
Matthew Braithwaitecedc6f12017-03-15 19:20:23 -07001886 0x16,
1887 0x03, 0x01,
1888 0x00, 0x8e,
1889 0x01,
1890 0x00, 0x00, 0x8a,
1891 0x03, 0x03,
David Benjamin57e929f2016-08-30 00:30:38 -04001892 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1893 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
Matthew Braithwaitecedc6f12017-03-15 19:20:23 -07001894 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1895 0x00, 0x2a,
1896 0xcc, 0xa9,
1897 0xcc, 0xa8,
1898 0xc0, 0x2b,
1899 0xc0, 0x2f,
1900 0xc0, 0x2c,
1901 0xc0, 0x30,
1902 0xc0, 0x09,
1903 0xc0, 0x23,
1904 0xc0, 0x13,
1905 0xc0, 0x27,
1906 0xc0, 0x0a,
1907 0xc0, 0x24,
1908 0xc0, 0x14,
1909 0xc0, 0x28,
1910 0x00, 0x9c,
1911 0x00, 0x9d,
1912 0x00, 0x2f,
1913 0x00, 0x3c,
1914 0x00, 0x35,
1915 0x00, 0x3d,
1916 0x00, 0x0a,
1917 0x01, 0x00, 0x00, 0x37, 0xff, 0x01, 0x00, 0x01, 0x00, 0x00, 0x17, 0x00,
1918 0x00, 0x00, 0x23, 0x00, 0x00, 0x00, 0x0d, 0x00, 0x14, 0x00, 0x12, 0x04,
1919 0x03, 0x08, 0x04, 0x04, 0x01, 0x05, 0x03, 0x08, 0x05, 0x05, 0x01, 0x08,
1920 0x06, 0x06, 0x01, 0x02, 0x01, 0x00, 0x0b, 0x00, 0x02, 0x01, 0x00, 0x00,
1921 0x0a, 0x00, 0x08, 0x00, 0x06, 0x00, 0x1d, 0x00, 0x17, 0x00, 0x18,
David Benjaminafc64de2016-07-19 17:12:41 +02001922 };
1923 if (!ClientHelloMatches(TLS1_2_VERSION, kTLS12ClientHello,
1924 sizeof(kTLS12ClientHello))) {
1925 return false;
1926 }
1927
1928 // TODO(davidben): Add a change detector for TLS 1.3 once the spec and our
1929 // implementation has settled enough that it won't change.
1930
1931 return true;
1932}
1933
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001934static bssl::UniquePtr<SSL_SESSION> g_last_session;
David Benjamina20e5352016-08-02 19:09:41 -04001935
1936static int SaveLastSession(SSL *ssl, SSL_SESSION *session) {
1937 // Save the most recent session.
1938 g_last_session.reset(session);
1939 return 1;
1940}
1941
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001942static bssl::UniquePtr<SSL_SESSION> CreateClientSession(SSL_CTX *client_ctx,
David Benjamina20e5352016-08-02 19:09:41 -04001943 SSL_CTX *server_ctx) {
1944 g_last_session = nullptr;
1945 SSL_CTX_sess_set_new_cb(client_ctx, SaveLastSession);
1946
1947 // Connect client and server to get a session.
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001948 bssl::UniquePtr<SSL> client, server;
David Benjamina20e5352016-08-02 19:09:41 -04001949 if (!ConnectClientAndServer(&client, &server, client_ctx, server_ctx,
1950 nullptr /* no session */)) {
1951 fprintf(stderr, "Failed to connect client and server.\n");
1952 return nullptr;
1953 }
1954
1955 // Run the read loop to account for post-handshake tickets in TLS 1.3.
1956 SSL_read(client.get(), nullptr, 0);
1957
1958 SSL_CTX_sess_set_new_cb(client_ctx, nullptr);
1959
1960 if (!g_last_session) {
1961 fprintf(stderr, "Client did not receive a session.\n");
1962 return nullptr;
1963 }
1964 return std::move(g_last_session);
1965}
1966
1967static bool ExpectSessionReused(SSL_CTX *client_ctx, SSL_CTX *server_ctx,
1968 SSL_SESSION *session,
1969 bool reused) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001970 bssl::UniquePtr<SSL> client, server;
David Benjamina20e5352016-08-02 19:09:41 -04001971 if (!ConnectClientAndServer(&client, &server, client_ctx,
1972 server_ctx, session)) {
1973 fprintf(stderr, "Failed to connect client and server.\n");
1974 return false;
1975 }
1976
1977 if (SSL_session_reused(client.get()) != SSL_session_reused(server.get())) {
1978 fprintf(stderr, "Client and server were inconsistent.\n");
1979 return false;
1980 }
1981
1982 bool was_reused = !!SSL_session_reused(client.get());
1983 if (was_reused != reused) {
1984 fprintf(stderr, "Session was%s reused, but we expected the opposite.\n",
1985 was_reused ? "" : " not");
1986 return false;
1987 }
1988
1989 return true;
1990}
1991
David Benjamin3c51d9b2016-11-01 17:50:42 -04001992static bssl::UniquePtr<SSL_SESSION> ExpectSessionRenewed(SSL_CTX *client_ctx,
1993 SSL_CTX *server_ctx,
1994 SSL_SESSION *session) {
1995 g_last_session = nullptr;
1996 SSL_CTX_sess_set_new_cb(client_ctx, SaveLastSession);
1997
1998 bssl::UniquePtr<SSL> client, server;
1999 if (!ConnectClientAndServer(&client, &server, client_ctx,
2000 server_ctx, session)) {
2001 fprintf(stderr, "Failed to connect client and server.\n");
2002 return nullptr;
2003 }
2004
2005 if (SSL_session_reused(client.get()) != SSL_session_reused(server.get())) {
2006 fprintf(stderr, "Client and server were inconsistent.\n");
2007 return nullptr;
2008 }
2009
2010 if (!SSL_session_reused(client.get())) {
2011 fprintf(stderr, "Session was not reused.\n");
2012 return nullptr;
2013 }
2014
2015 // Run the read loop to account for post-handshake tickets in TLS 1.3.
2016 SSL_read(client.get(), nullptr, 0);
2017
2018 SSL_CTX_sess_set_new_cb(client_ctx, nullptr);
2019
2020 if (!g_last_session) {
2021 fprintf(stderr, "Client did not receive a renewed session.\n");
2022 return nullptr;
2023 }
2024 return std::move(g_last_session);
2025}
2026
David Benjamina933c382016-10-28 00:10:03 -04002027static int SwitchSessionIDContextSNI(SSL *ssl, int *out_alert, void *arg) {
2028 static const uint8_t kContext[] = {3};
2029
2030 if (!SSL_set_session_id_context(ssl, kContext, sizeof(kContext))) {
2031 return SSL_TLSEXT_ERR_ALERT_FATAL;
2032 }
2033
2034 return SSL_TLSEXT_ERR_OK;
2035}
2036
David Benjamin0fef3052016-11-18 15:11:10 +09002037static bool TestSessionIDContext(bool is_dtls, const SSL_METHOD *method,
2038 uint16_t version) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002039 bssl::UniquePtr<X509> cert = GetTestCertificate();
2040 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
David Benjamina20e5352016-08-02 19:09:41 -04002041 if (!cert || !key) {
2042 return false;
2043 }
2044
2045 static const uint8_t kContext1[] = {1};
2046 static const uint8_t kContext2[] = {2};
2047
David Benjamin0fef3052016-11-18 15:11:10 +09002048 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(method));
2049 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(method));
2050 if (!server_ctx || !client_ctx ||
2051 !SSL_CTX_use_certificate(server_ctx.get(), cert.get()) ||
2052 !SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()) ||
2053 !SSL_CTX_set_session_id_context(server_ctx.get(), kContext1,
2054 sizeof(kContext1)) ||
2055 !SSL_CTX_set_min_proto_version(client_ctx.get(), version) ||
2056 !SSL_CTX_set_max_proto_version(client_ctx.get(), version) ||
2057 !SSL_CTX_set_min_proto_version(server_ctx.get(), version) ||
2058 !SSL_CTX_set_max_proto_version(server_ctx.get(), version)) {
2059 return false;
2060 }
David Benjamina20e5352016-08-02 19:09:41 -04002061
David Benjamin0fef3052016-11-18 15:11:10 +09002062 SSL_CTX_set_session_cache_mode(client_ctx.get(), SSL_SESS_CACHE_BOTH);
2063 SSL_CTX_set_session_cache_mode(server_ctx.get(), SSL_SESS_CACHE_BOTH);
David Benjamina20e5352016-08-02 19:09:41 -04002064
David Benjamin0fef3052016-11-18 15:11:10 +09002065 bssl::UniquePtr<SSL_SESSION> session =
2066 CreateClientSession(client_ctx.get(), server_ctx.get());
2067 if (!session) {
2068 fprintf(stderr, "Error getting session.\n");
2069 return false;
2070 }
David Benjamina20e5352016-08-02 19:09:41 -04002071
David Benjamin0fef3052016-11-18 15:11:10 +09002072 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(), session.get(),
2073 true /* expect session reused */)) {
2074 fprintf(stderr, "Error resuming session.\n");
2075 return false;
2076 }
David Benjamina20e5352016-08-02 19:09:41 -04002077
David Benjamin0fef3052016-11-18 15:11:10 +09002078 // Change the session ID context.
2079 if (!SSL_CTX_set_session_id_context(server_ctx.get(), kContext2,
2080 sizeof(kContext2))) {
2081 return false;
2082 }
David Benjamina20e5352016-08-02 19:09:41 -04002083
David Benjamin0fef3052016-11-18 15:11:10 +09002084 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(), session.get(),
2085 false /* expect session not reused */)) {
2086 fprintf(stderr, "Error connecting with a different context.\n");
2087 return false;
2088 }
David Benjamina933c382016-10-28 00:10:03 -04002089
David Benjamin0fef3052016-11-18 15:11:10 +09002090 // Change the session ID context back and install an SNI callback to switch
2091 // it.
2092 if (!SSL_CTX_set_session_id_context(server_ctx.get(), kContext1,
2093 sizeof(kContext1))) {
2094 return false;
2095 }
David Benjamina933c382016-10-28 00:10:03 -04002096
David Benjamin0fef3052016-11-18 15:11:10 +09002097 SSL_CTX_set_tlsext_servername_callback(server_ctx.get(),
2098 SwitchSessionIDContextSNI);
David Benjamina933c382016-10-28 00:10:03 -04002099
David Benjamin0fef3052016-11-18 15:11:10 +09002100 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(), session.get(),
2101 false /* expect session not reused */)) {
2102 fprintf(stderr, "Error connecting with a context switch on SNI callback.\n");
2103 return false;
2104 }
David Benjamina933c382016-10-28 00:10:03 -04002105
David Benjamin0fef3052016-11-18 15:11:10 +09002106 // Switch the session ID context with the early callback instead.
2107 SSL_CTX_set_tlsext_servername_callback(server_ctx.get(), nullptr);
Alessandro Ghedini57e81e62017-03-14 23:36:00 +00002108 SSL_CTX_set_select_certificate_cb(
2109 server_ctx.get(),
2110 [](const SSL_CLIENT_HELLO *client_hello) -> ssl_select_cert_result_t {
2111 static const uint8_t kContext[] = {3};
2112
2113 if (!SSL_set_session_id_context(client_hello->ssl, kContext,
2114 sizeof(kContext))) {
2115 return ssl_select_cert_error;
2116 }
2117
2118 return ssl_select_cert_success;
2119 });
David Benjamina933c382016-10-28 00:10:03 -04002120
David Benjamin0fef3052016-11-18 15:11:10 +09002121 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(), session.get(),
2122 false /* expect session not reused */)) {
2123 fprintf(stderr,
2124 "Error connecting with a context switch on early callback.\n");
2125 return false;
David Benjamina20e5352016-08-02 19:09:41 -04002126 }
2127
2128 return true;
2129}
2130
David Benjamin721e8b72016-08-03 13:13:17 -04002131static timeval g_current_time;
2132
2133static void CurrentTimeCallback(const SSL *ssl, timeval *out_clock) {
2134 *out_clock = g_current_time;
2135}
2136
David Benjamin17b30832017-01-28 14:00:32 -05002137static void FrozenTimeCallback(const SSL *ssl, timeval *out_clock) {
2138 out_clock->tv_sec = 1000;
2139 out_clock->tv_usec = 0;
2140}
2141
David Benjamin3c51d9b2016-11-01 17:50:42 -04002142static int RenewTicketCallback(SSL *ssl, uint8_t *key_name, uint8_t *iv,
2143 EVP_CIPHER_CTX *ctx, HMAC_CTX *hmac_ctx,
2144 int encrypt) {
2145 static const uint8_t kZeros[16] = {0};
2146
2147 if (encrypt) {
David Benjamin17cf2cb2016-12-13 01:07:13 -05002148 OPENSSL_memcpy(key_name, kZeros, sizeof(kZeros));
David Benjamin3c51d9b2016-11-01 17:50:42 -04002149 RAND_bytes(iv, 16);
David Benjamin17cf2cb2016-12-13 01:07:13 -05002150 } else if (OPENSSL_memcmp(key_name, kZeros, 16) != 0) {
David Benjamin3c51d9b2016-11-01 17:50:42 -04002151 return 0;
2152 }
2153
2154 if (!HMAC_Init_ex(hmac_ctx, kZeros, sizeof(kZeros), EVP_sha256(), NULL) ||
2155 !EVP_CipherInit_ex(ctx, EVP_aes_128_cbc(), NULL, kZeros, iv, encrypt)) {
2156 return -1;
2157 }
2158
2159 // Returning two from the callback in decrypt mode renews the
2160 // session in TLS 1.2 and below.
2161 return encrypt ? 1 : 2;
2162}
2163
David Benjamin123db572016-11-03 16:59:25 -04002164static bool GetServerTicketTime(long *out, const SSL_SESSION *session) {
David Benjamin123db572016-11-03 16:59:25 -04002165 if (session->tlsext_ticklen < 16 + 16 + SHA256_DIGEST_LENGTH) {
2166 return false;
2167 }
2168
David Benjamin123db572016-11-03 16:59:25 -04002169 const uint8_t *ciphertext = session->tlsext_tick + 16 + 16;
2170 size_t len = session->tlsext_ticklen - 16 - 16 - SHA256_DIGEST_LENGTH;
2171 std::unique_ptr<uint8_t[]> plaintext(new uint8_t[len]);
2172
David Benjamin9b63f292016-11-15 00:44:05 -05002173#if defined(BORINGSSL_UNSAFE_FUZZER_MODE)
2174 // Fuzzer-mode tickets are unencrypted.
David Benjamin17cf2cb2016-12-13 01:07:13 -05002175 OPENSSL_memcpy(plaintext.get(), ciphertext, len);
David Benjamin9b63f292016-11-15 00:44:05 -05002176#else
2177 static const uint8_t kZeros[16] = {0};
2178 const uint8_t *iv = session->tlsext_tick + 16;
David Benjamin123db572016-11-03 16:59:25 -04002179 bssl::ScopedEVP_CIPHER_CTX ctx;
2180 int len1, len2;
2181 if (!EVP_DecryptInit_ex(ctx.get(), EVP_aes_128_cbc(), nullptr, kZeros, iv) ||
2182 !EVP_DecryptUpdate(ctx.get(), plaintext.get(), &len1, ciphertext, len) ||
2183 !EVP_DecryptFinal_ex(ctx.get(), plaintext.get() + len1, &len2)) {
2184 return false;
2185 }
2186
2187 len = static_cast<size_t>(len1 + len2);
David Benjamin9b63f292016-11-15 00:44:05 -05002188#endif
David Benjamin123db572016-11-03 16:59:25 -04002189
Adam Langley46db7af2017-02-01 15:49:37 -08002190 bssl::UniquePtr<SSL_CTX> ssl_ctx(SSL_CTX_new(TLS_method()));
2191 if (!ssl_ctx) {
2192 return false;
2193 }
David Benjamin123db572016-11-03 16:59:25 -04002194 bssl::UniquePtr<SSL_SESSION> server_session(
Adam Langley46db7af2017-02-01 15:49:37 -08002195 SSL_SESSION_from_bytes(plaintext.get(), len, ssl_ctx.get()));
David Benjamin123db572016-11-03 16:59:25 -04002196 if (!server_session) {
2197 return false;
2198 }
2199
2200 *out = server_session->time;
2201 return true;
2202}
2203
David Benjamin0fef3052016-11-18 15:11:10 +09002204static bool TestSessionTimeout(bool is_dtls, const SSL_METHOD *method,
2205 uint16_t version) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002206 bssl::UniquePtr<X509> cert = GetTestCertificate();
2207 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
David Benjamin721e8b72016-08-03 13:13:17 -04002208 if (!cert || !key) {
2209 return false;
2210 }
2211
David Benjamin0fef3052016-11-18 15:11:10 +09002212 for (bool server_test : std::vector<bool>{false, true}) {
David Benjamin17b30832017-01-28 14:00:32 -05002213 static const time_t kStartTime = 1000;
David Benjamin0fef3052016-11-18 15:11:10 +09002214 g_current_time.tv_sec = kStartTime;
David Benjamin1b22f852016-10-27 16:36:32 -04002215
David Benjamin17b30832017-01-28 14:00:32 -05002216 // We are willing to use a longer lifetime for TLS 1.3 sessions as
2217 // resumptions still perform ECDHE.
2218 const time_t timeout = version == TLS1_3_VERSION
2219 ? SSL_DEFAULT_SESSION_PSK_DHE_TIMEOUT
2220 : SSL_DEFAULT_SESSION_TIMEOUT;
2221
David Benjamin0fef3052016-11-18 15:11:10 +09002222 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(method));
2223 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(method));
2224 if (!server_ctx || !client_ctx ||
2225 !SSL_CTX_use_certificate(server_ctx.get(), cert.get()) ||
2226 !SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()) ||
2227 !SSL_CTX_set_min_proto_version(client_ctx.get(), version) ||
2228 !SSL_CTX_set_max_proto_version(client_ctx.get(), version) ||
2229 !SSL_CTX_set_min_proto_version(server_ctx.get(), version) ||
2230 !SSL_CTX_set_max_proto_version(server_ctx.get(), version)) {
2231 return false;
2232 }
2233
2234 SSL_CTX_set_session_cache_mode(client_ctx.get(), SSL_SESS_CACHE_BOTH);
2235 SSL_CTX_set_session_cache_mode(server_ctx.get(), SSL_SESS_CACHE_BOTH);
2236
David Benjamin17b30832017-01-28 14:00:32 -05002237 // Both client and server must enforce session timeouts. We configure the
2238 // other side with a frozen clock so it never expires tickets.
David Benjamin0fef3052016-11-18 15:11:10 +09002239 if (server_test) {
David Benjamin17b30832017-01-28 14:00:32 -05002240 SSL_CTX_set_current_time_cb(client_ctx.get(), FrozenTimeCallback);
David Benjamin0fef3052016-11-18 15:11:10 +09002241 SSL_CTX_set_current_time_cb(server_ctx.get(), CurrentTimeCallback);
2242 } else {
2243 SSL_CTX_set_current_time_cb(client_ctx.get(), CurrentTimeCallback);
David Benjamin17b30832017-01-28 14:00:32 -05002244 SSL_CTX_set_current_time_cb(server_ctx.get(), FrozenTimeCallback);
David Benjamin0fef3052016-11-18 15:11:10 +09002245 }
2246
2247 // Configure a ticket callback which renews tickets.
2248 SSL_CTX_set_tlsext_ticket_key_cb(server_ctx.get(), RenewTicketCallback);
2249
2250 bssl::UniquePtr<SSL_SESSION> session =
2251 CreateClientSession(client_ctx.get(), server_ctx.get());
2252 if (!session) {
2253 fprintf(stderr, "Error getting session.\n");
2254 return false;
2255 }
2256
2257 // Advance the clock just behind the timeout.
David Benjamin17b30832017-01-28 14:00:32 -05002258 g_current_time.tv_sec += timeout - 1;
David Benjamin0fef3052016-11-18 15:11:10 +09002259
2260 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(), session.get(),
2261 true /* expect session reused */)) {
2262 fprintf(stderr, "Error resuming session.\n");
2263 return false;
2264 }
2265
2266 // Advance the clock one more second.
2267 g_current_time.tv_sec++;
2268
2269 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(), session.get(),
2270 false /* expect session not reused */)) {
2271 fprintf(stderr, "Error resuming session.\n");
2272 return false;
2273 }
2274
2275 // Rewind the clock to before the session was minted.
2276 g_current_time.tv_sec = kStartTime - 1;
2277
2278 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(), session.get(),
2279 false /* expect session not reused */)) {
2280 fprintf(stderr, "Error resuming session.\n");
2281 return false;
2282 }
2283
2284 // SSL 3.0 cannot renew sessions.
2285 if (version == SSL3_VERSION) {
2286 continue;
2287 }
2288
2289 // Renew the session 10 seconds before expiration.
David Benjamin17b30832017-01-28 14:00:32 -05002290 time_t new_start_time = kStartTime + timeout - 10;
2291 g_current_time.tv_sec = new_start_time;
David Benjamin0fef3052016-11-18 15:11:10 +09002292 bssl::UniquePtr<SSL_SESSION> new_session =
2293 ExpectSessionRenewed(client_ctx.get(), server_ctx.get(), session.get());
2294 if (!new_session) {
2295 fprintf(stderr, "Error renewing session.\n");
2296 return false;
2297 }
2298
2299 // This new session is not the same object as before.
2300 if (session.get() == new_session.get()) {
2301 fprintf(stderr, "New and old sessions alias.\n");
2302 return false;
2303 }
2304
2305 // Check the sessions have timestamps measured from issuance.
2306 long session_time = 0;
2307 if (server_test) {
2308 if (!GetServerTicketTime(&session_time, new_session.get())) {
2309 fprintf(stderr, "Failed to decode session ticket.\n");
David Benjaminb2e2e322016-11-01 17:32:54 -04002310 return false;
2311 }
David Benjamin0fef3052016-11-18 15:11:10 +09002312 } else {
2313 session_time = new_session->time;
2314 }
David Benjamin721e8b72016-08-03 13:13:17 -04002315
David Benjamin0fef3052016-11-18 15:11:10 +09002316 if (session_time != g_current_time.tv_sec) {
2317 fprintf(stderr, "New session is not measured from issuance.\n");
2318 return false;
2319 }
David Benjamin721e8b72016-08-03 13:13:17 -04002320
David Benjamin17b30832017-01-28 14:00:32 -05002321 if (version == TLS1_3_VERSION) {
2322 // Renewal incorporates fresh key material in TLS 1.3, so we extend the
2323 // lifetime TLS 1.3.
2324 g_current_time.tv_sec = new_start_time + timeout - 1;
2325 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(),
2326 new_session.get(),
2327 true /* expect session reused */)) {
2328 fprintf(stderr, "Error resuming renewed session.\n");
2329 return false;
2330 }
David Benjamin721e8b72016-08-03 13:13:17 -04002331
David Benjamin17b30832017-01-28 14:00:32 -05002332 // The new session expires after the new timeout.
2333 g_current_time.tv_sec = new_start_time + timeout + 1;
2334 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(),
2335 new_session.get(),
2336 false /* expect session ot reused */)) {
2337 fprintf(stderr, "Renewed session's lifetime is too long.\n");
2338 return false;
2339 }
2340
2341 // Renew the session until it begins just past the auth timeout.
2342 time_t auth_end_time = kStartTime + SSL_DEFAULT_SESSION_AUTH_TIMEOUT;
2343 while (new_start_time < auth_end_time - 1000) {
2344 // Get as close as possible to target start time.
2345 new_start_time =
2346 std::min(auth_end_time - 1000, new_start_time + timeout - 1);
2347 g_current_time.tv_sec = new_start_time;
2348 new_session = ExpectSessionRenewed(client_ctx.get(), server_ctx.get(),
2349 new_session.get());
2350 if (!new_session) {
2351 fprintf(stderr, "Error renewing session.\n");
2352 return false;
2353 }
2354 }
2355
2356 // Now the session's lifetime is bound by the auth timeout.
2357 g_current_time.tv_sec = auth_end_time - 1;
2358 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(),
2359 new_session.get(),
2360 true /* expect session reused */)) {
2361 fprintf(stderr, "Error resuming renewed session.\n");
2362 return false;
2363 }
2364
2365 g_current_time.tv_sec = auth_end_time + 1;
2366 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(),
2367 new_session.get(),
2368 false /* expect session ot reused */)) {
2369 fprintf(stderr, "Renewed session's lifetime is too long.\n");
2370 return false;
2371 }
2372 } else {
2373 // The new session is usable just before the old expiration.
2374 g_current_time.tv_sec = kStartTime + timeout - 1;
2375 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(),
2376 new_session.get(),
2377 true /* expect session reused */)) {
2378 fprintf(stderr, "Error resuming renewed session.\n");
2379 return false;
2380 }
2381
2382 // Renewal does not extend the lifetime, so it is not usable beyond the
2383 // old expiration.
2384 g_current_time.tv_sec = kStartTime + timeout + 1;
2385 if (!ExpectSessionReused(client_ctx.get(), server_ctx.get(),
2386 new_session.get(),
2387 false /* expect session not reused */)) {
2388 fprintf(stderr, "Renewed session's lifetime is too long.\n");
2389 return false;
2390 }
David Benjamin1b22f852016-10-27 16:36:32 -04002391 }
David Benjamin721e8b72016-08-03 13:13:17 -04002392 }
2393
2394 return true;
2395}
2396
David Benjamin0fc37ef2016-08-17 15:29:46 -04002397static int SwitchContext(SSL *ssl, int *out_alert, void *arg) {
2398 SSL_CTX *ctx = reinterpret_cast<SSL_CTX*>(arg);
2399 SSL_set_SSL_CTX(ssl, ctx);
2400 return SSL_TLSEXT_ERR_OK;
2401}
2402
David Benjamin0fef3052016-11-18 15:11:10 +09002403static bool TestSNICallback(bool is_dtls, const SSL_METHOD *method,
2404 uint16_t version) {
2405 // SSL 3.0 lacks extensions.
2406 if (version == SSL3_VERSION) {
2407 return true;
2408 }
2409
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002410 bssl::UniquePtr<X509> cert = GetTestCertificate();
2411 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
2412 bssl::UniquePtr<X509> cert2 = GetECDSATestCertificate();
2413 bssl::UniquePtr<EVP_PKEY> key2 = GetECDSATestKey();
David Benjamin0fc37ef2016-08-17 15:29:46 -04002414 if (!cert || !key || !cert2 || !key2) {
2415 return false;
2416 }
2417
David Benjamin0fef3052016-11-18 15:11:10 +09002418 // Test that switching the |SSL_CTX| at the SNI callback behaves correctly.
2419 static const uint16_t kECDSAWithSHA256 = SSL_SIGN_ECDSA_SECP256R1_SHA256;
David Benjamin0fc37ef2016-08-17 15:29:46 -04002420
David Benjamin83a32122017-02-14 18:34:54 -05002421 static const uint8_t kSCTList[] = {0, 6, 0, 4, 5, 6, 7, 8};
2422 static const uint8_t kOCSPResponse[] = {1, 2, 3, 4};
2423
David Benjamin0fef3052016-11-18 15:11:10 +09002424 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(method));
2425 bssl::UniquePtr<SSL_CTX> server_ctx2(SSL_CTX_new(method));
2426 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(method));
2427 if (!server_ctx || !server_ctx2 || !client_ctx ||
2428 !SSL_CTX_use_certificate(server_ctx.get(), cert.get()) ||
2429 !SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()) ||
2430 !SSL_CTX_use_certificate(server_ctx2.get(), cert2.get()) ||
2431 !SSL_CTX_use_PrivateKey(server_ctx2.get(), key2.get()) ||
David Benjamin83a32122017-02-14 18:34:54 -05002432 !SSL_CTX_set_signed_cert_timestamp_list(server_ctx2.get(), kSCTList,
2433 sizeof(kSCTList)) ||
2434 !SSL_CTX_set_ocsp_response(server_ctx2.get(), kOCSPResponse,
2435 sizeof(kOCSPResponse)) ||
David Benjamin0fef3052016-11-18 15:11:10 +09002436 // Historically signing preferences would be lost in some cases with the
2437 // SNI callback, which triggers the TLS 1.2 SHA-1 default. To ensure
2438 // this doesn't happen when |version| is TLS 1.2, configure the private
2439 // key to only sign SHA-256.
2440 !SSL_CTX_set_signing_algorithm_prefs(server_ctx2.get(), &kECDSAWithSHA256,
2441 1) ||
2442 !SSL_CTX_set_min_proto_version(client_ctx.get(), version) ||
2443 !SSL_CTX_set_max_proto_version(client_ctx.get(), version) ||
2444 !SSL_CTX_set_min_proto_version(server_ctx.get(), version) ||
2445 !SSL_CTX_set_max_proto_version(server_ctx.get(), version) ||
2446 !SSL_CTX_set_min_proto_version(server_ctx2.get(), version) ||
2447 !SSL_CTX_set_max_proto_version(server_ctx2.get(), version)) {
2448 return false;
2449 }
David Benjamin0fc37ef2016-08-17 15:29:46 -04002450
David Benjamin0fef3052016-11-18 15:11:10 +09002451 SSL_CTX_set_tlsext_servername_callback(server_ctx.get(), SwitchContext);
2452 SSL_CTX_set_tlsext_servername_arg(server_ctx.get(), server_ctx2.get());
David Benjamin0fc37ef2016-08-17 15:29:46 -04002453
David Benjamin83a32122017-02-14 18:34:54 -05002454 SSL_CTX_enable_signed_cert_timestamps(client_ctx.get());
2455 SSL_CTX_enable_ocsp_stapling(client_ctx.get());
2456
David Benjamin0fef3052016-11-18 15:11:10 +09002457 bssl::UniquePtr<SSL> client, server;
2458 if (!ConnectClientAndServer(&client, &server, client_ctx.get(),
2459 server_ctx.get(), nullptr)) {
2460 fprintf(stderr, "Handshake failed.\n");
2461 return false;
2462 }
David Benjamin0fc37ef2016-08-17 15:29:46 -04002463
David Benjamin0fef3052016-11-18 15:11:10 +09002464 // The client should have received |cert2|.
2465 bssl::UniquePtr<X509> peer(SSL_get_peer_certificate(client.get()));
2466 if (!peer || X509_cmp(peer.get(), cert2.get()) != 0) {
2467 fprintf(stderr, "Incorrect certificate received.\n");
2468 return false;
David Benjamin0fc37ef2016-08-17 15:29:46 -04002469 }
2470
David Benjamin83a32122017-02-14 18:34:54 -05002471 // The client should have received |server_ctx2|'s SCT list.
2472 const uint8_t *data;
2473 size_t len;
2474 SSL_get0_signed_cert_timestamp_list(client.get(), &data, &len);
2475 if (Bytes(kSCTList) != Bytes(data, len)) {
2476 fprintf(stderr, "Incorrect SCT list received.\n");
2477 return false;
2478 }
2479
2480 // The client should have received |server_ctx2|'s OCSP response.
2481 SSL_get0_ocsp_response(client.get(), &data, &len);
2482 if (Bytes(kOCSPResponse) != Bytes(data, len)) {
2483 fprintf(stderr, "Incorrect OCSP response received.\n");
2484 return false;
2485 }
2486
David Benjamin0fc37ef2016-08-17 15:29:46 -04002487 return true;
2488}
2489
David Benjaminf0d8e222017-02-04 10:58:26 -05002490// Test that the early callback can swap the maximum version.
2491TEST(SSLTest, EarlyCallbackVersionSwitch) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002492 bssl::UniquePtr<X509> cert = GetTestCertificate();
2493 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
2494 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(TLS_method()));
2495 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLS_method()));
David Benjaminf0d8e222017-02-04 10:58:26 -05002496 ASSERT_TRUE(cert);
2497 ASSERT_TRUE(key);
2498 ASSERT_TRUE(server_ctx);
2499 ASSERT_TRUE(client_ctx);
2500 ASSERT_TRUE(SSL_CTX_use_certificate(server_ctx.get(), cert.get()));
2501 ASSERT_TRUE(SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()));
2502 ASSERT_TRUE(SSL_CTX_set_max_proto_version(client_ctx.get(), TLS1_3_VERSION));
2503 ASSERT_TRUE(SSL_CTX_set_max_proto_version(server_ctx.get(), TLS1_3_VERSION));
David Benjamin99620572016-08-30 00:35:36 -04002504
David Benjaminf0d8e222017-02-04 10:58:26 -05002505 SSL_CTX_set_select_certificate_cb(
Alessandro Ghedini57e81e62017-03-14 23:36:00 +00002506 server_ctx.get(),
2507 [](const SSL_CLIENT_HELLO *client_hello) -> ssl_select_cert_result_t {
David Benjaminf0d8e222017-02-04 10:58:26 -05002508 if (!SSL_set_max_proto_version(client_hello->ssl, TLS1_2_VERSION)) {
Alessandro Ghedini57e81e62017-03-14 23:36:00 +00002509 return ssl_select_cert_error;
David Benjaminf0d8e222017-02-04 10:58:26 -05002510 }
2511
Alessandro Ghedini57e81e62017-03-14 23:36:00 +00002512 return ssl_select_cert_success;
David Benjaminf0d8e222017-02-04 10:58:26 -05002513 });
David Benjamin99620572016-08-30 00:35:36 -04002514
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002515 bssl::UniquePtr<SSL> client, server;
David Benjaminf0d8e222017-02-04 10:58:26 -05002516 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx.get(),
2517 server_ctx.get(), nullptr));
2518 EXPECT_EQ(TLS1_2_VERSION, SSL_version(client.get()));
David Benjamin99620572016-08-30 00:35:36 -04002519}
2520
David Benjaminf0d8e222017-02-04 10:58:26 -05002521TEST(SSLTest, SetVersion) {
David Benjamin2dc02042016-09-19 19:57:37 -04002522 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
David Benjaminf0d8e222017-02-04 10:58:26 -05002523 ASSERT_TRUE(ctx);
David Benjamin2dc02042016-09-19 19:57:37 -04002524
David Benjaminf0d8e222017-02-04 10:58:26 -05002525 // Set valid TLS versions.
2526 EXPECT_TRUE(SSL_CTX_set_max_proto_version(ctx.get(), TLS1_VERSION));
2527 EXPECT_TRUE(SSL_CTX_set_max_proto_version(ctx.get(), TLS1_1_VERSION));
2528 EXPECT_TRUE(SSL_CTX_set_min_proto_version(ctx.get(), TLS1_VERSION));
2529 EXPECT_TRUE(SSL_CTX_set_min_proto_version(ctx.get(), TLS1_1_VERSION));
David Benjamin2dc02042016-09-19 19:57:37 -04002530
David Benjaminf0d8e222017-02-04 10:58:26 -05002531 // Invalid TLS versions are rejected.
2532 EXPECT_FALSE(SSL_CTX_set_max_proto_version(ctx.get(), DTLS1_VERSION));
2533 EXPECT_FALSE(SSL_CTX_set_max_proto_version(ctx.get(), 0x0200));
2534 EXPECT_FALSE(SSL_CTX_set_max_proto_version(ctx.get(), 0x1234));
2535 EXPECT_FALSE(SSL_CTX_set_min_proto_version(ctx.get(), DTLS1_VERSION));
2536 EXPECT_FALSE(SSL_CTX_set_min_proto_version(ctx.get(), 0x0200));
2537 EXPECT_FALSE(SSL_CTX_set_min_proto_version(ctx.get(), 0x1234));
David Benjamin2dc02042016-09-19 19:57:37 -04002538
David Benjaminf0d8e222017-02-04 10:58:26 -05002539 // Zero is the default version.
2540 EXPECT_TRUE(SSL_CTX_set_max_proto_version(ctx.get(), 0));
2541 EXPECT_EQ(TLS1_2_VERSION, ctx->max_version);
2542 EXPECT_TRUE(SSL_CTX_set_min_proto_version(ctx.get(), 0));
David Benjamin3cfeb952017-03-01 16:48:38 -05002543 EXPECT_EQ(TLS1_VERSION, ctx->min_version);
2544
2545 // SSL 3.0 and TLS 1.3 are available, but not by default.
2546 EXPECT_TRUE(SSL_CTX_set_min_proto_version(ctx.get(), SSL3_VERSION));
David Benjaminf0d8e222017-02-04 10:58:26 -05002547 EXPECT_EQ(SSL3_VERSION, ctx->min_version);
David Benjamin3cfeb952017-03-01 16:48:38 -05002548 EXPECT_TRUE(SSL_CTX_set_max_proto_version(ctx.get(), TLS1_3_VERSION));
2549 EXPECT_EQ(TLS1_3_VERSION, ctx->max_version);
David Benjamine34bcc92016-09-21 16:53:09 -04002550
David Benjamin2dc02042016-09-19 19:57:37 -04002551 ctx.reset(SSL_CTX_new(DTLS_method()));
David Benjaminf0d8e222017-02-04 10:58:26 -05002552 ASSERT_TRUE(ctx);
David Benjamin2dc02042016-09-19 19:57:37 -04002553
David Benjaminf0d8e222017-02-04 10:58:26 -05002554 EXPECT_TRUE(SSL_CTX_set_max_proto_version(ctx.get(), DTLS1_VERSION));
2555 EXPECT_TRUE(SSL_CTX_set_max_proto_version(ctx.get(), DTLS1_2_VERSION));
2556 EXPECT_TRUE(SSL_CTX_set_min_proto_version(ctx.get(), DTLS1_VERSION));
2557 EXPECT_TRUE(SSL_CTX_set_min_proto_version(ctx.get(), DTLS1_2_VERSION));
David Benjamin2dc02042016-09-19 19:57:37 -04002558
David Benjaminf0d8e222017-02-04 10:58:26 -05002559 EXPECT_FALSE(SSL_CTX_set_max_proto_version(ctx.get(), TLS1_VERSION));
2560 EXPECT_FALSE(SSL_CTX_set_max_proto_version(ctx.get(), 0xfefe /* DTLS 1.1 */));
2561 EXPECT_FALSE(SSL_CTX_set_max_proto_version(ctx.get(), 0xfffe /* DTLS 0.1 */));
2562 EXPECT_FALSE(SSL_CTX_set_max_proto_version(ctx.get(), 0x1234));
2563 EXPECT_FALSE(SSL_CTX_set_min_proto_version(ctx.get(), TLS1_VERSION));
2564 EXPECT_FALSE(SSL_CTX_set_min_proto_version(ctx.get(), 0xfefe /* DTLS 1.1 */));
2565 EXPECT_FALSE(SSL_CTX_set_min_proto_version(ctx.get(), 0xfffe /* DTLS 0.1 */));
2566 EXPECT_FALSE(SSL_CTX_set_min_proto_version(ctx.get(), 0x1234));
David Benjamin2dc02042016-09-19 19:57:37 -04002567
David Benjaminf0d8e222017-02-04 10:58:26 -05002568 EXPECT_TRUE(SSL_CTX_set_max_proto_version(ctx.get(), 0));
2569 EXPECT_EQ(TLS1_2_VERSION, ctx->max_version);
2570 EXPECT_TRUE(SSL_CTX_set_min_proto_version(ctx.get(), 0));
2571 EXPECT_EQ(TLS1_1_VERSION, ctx->min_version);
David Benjamin2dc02042016-09-19 19:57:37 -04002572}
2573
David Benjamin458334a2016-12-15 13:53:25 -05002574static const char *GetVersionName(uint16_t version) {
2575 switch (version) {
2576 case SSL3_VERSION:
2577 return "SSLv3";
2578 case TLS1_VERSION:
2579 return "TLSv1";
2580 case TLS1_1_VERSION:
2581 return "TLSv1.1";
2582 case TLS1_2_VERSION:
2583 return "TLSv1.2";
2584 case TLS1_3_VERSION:
2585 return "TLSv1.3";
2586 case DTLS1_VERSION:
2587 return "DTLSv1";
2588 case DTLS1_2_VERSION:
2589 return "DTLSv1.2";
2590 default:
2591 return "???";
2592 }
2593}
2594
David Benjamin0fef3052016-11-18 15:11:10 +09002595static bool TestVersion(bool is_dtls, const SSL_METHOD *method,
2596 uint16_t version) {
David Benjamincb18ac22016-09-27 14:09:15 -04002597 bssl::UniquePtr<X509> cert = GetTestCertificate();
2598 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
2599 if (!cert || !key) {
2600 return false;
2601 }
2602
David Benjamin0fef3052016-11-18 15:11:10 +09002603 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(method));
2604 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(method));
2605 bssl::UniquePtr<SSL> client, server;
2606 if (!server_ctx || !client_ctx ||
2607 !SSL_CTX_use_certificate(server_ctx.get(), cert.get()) ||
2608 !SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()) ||
2609 !SSL_CTX_set_min_proto_version(client_ctx.get(), version) ||
2610 !SSL_CTX_set_max_proto_version(client_ctx.get(), version) ||
2611 !SSL_CTX_set_min_proto_version(server_ctx.get(), version) ||
2612 !SSL_CTX_set_max_proto_version(server_ctx.get(), version) ||
2613 !ConnectClientAndServer(&client, &server, client_ctx.get(),
2614 server_ctx.get(), nullptr /* no session */)) {
2615 fprintf(stderr, "Failed to connect.\n");
2616 return false;
2617 }
David Benjamincb18ac22016-09-27 14:09:15 -04002618
David Benjamin0fef3052016-11-18 15:11:10 +09002619 if (SSL_version(client.get()) != version ||
2620 SSL_version(server.get()) != version) {
2621 fprintf(stderr, "Version mismatch. Got %04x and %04x, wanted %04x.\n",
2622 SSL_version(client.get()), SSL_version(server.get()), version);
2623 return false;
David Benjamincb18ac22016-09-27 14:09:15 -04002624 }
2625
David Benjamin458334a2016-12-15 13:53:25 -05002626 // Test the version name is reported as expected.
2627 const char *version_name = GetVersionName(version);
2628 if (strcmp(version_name, SSL_get_version(client.get())) != 0 ||
2629 strcmp(version_name, SSL_get_version(server.get())) != 0) {
2630 fprintf(stderr, "Version name mismatch. Got '%s' and '%s', wanted '%s'.\n",
2631 SSL_get_version(client.get()), SSL_get_version(server.get()),
2632 version_name);
2633 return false;
2634 }
2635
2636 // Test SSL_SESSION reports the same name.
2637 const char *client_name =
2638 SSL_SESSION_get_version(SSL_get_session(client.get()));
2639 const char *server_name =
2640 SSL_SESSION_get_version(SSL_get_session(server.get()));
2641 if (strcmp(version_name, client_name) != 0 ||
2642 strcmp(version_name, server_name) != 0) {
2643 fprintf(stderr,
2644 "Session version name mismatch. Got '%s' and '%s', wanted '%s'.\n",
2645 client_name, server_name, version_name);
2646 return false;
2647 }
2648
David Benjamincb18ac22016-09-27 14:09:15 -04002649 return true;
2650}
2651
David Benjamin9ef31f02016-10-31 18:01:13 -04002652// Tests that that |SSL_get_pending_cipher| is available during the ALPN
2653// selection callback.
David Benjamin0fef3052016-11-18 15:11:10 +09002654static bool TestALPNCipherAvailable(bool is_dtls, const SSL_METHOD *method,
2655 uint16_t version) {
2656 // SSL 3.0 lacks extensions.
2657 if (version == SSL3_VERSION) {
2658 return true;
2659 }
2660
David Benjamin9ef31f02016-10-31 18:01:13 -04002661 static const uint8_t kALPNProtos[] = {0x03, 'f', 'o', 'o'};
2662
2663 bssl::UniquePtr<X509> cert = GetTestCertificate();
2664 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
2665 if (!cert || !key) {
2666 return false;
2667 }
2668
David Benjamin0fef3052016-11-18 15:11:10 +09002669 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(method));
2670 if (!ctx || !SSL_CTX_use_certificate(ctx.get(), cert.get()) ||
2671 !SSL_CTX_use_PrivateKey(ctx.get(), key.get()) ||
2672 !SSL_CTX_set_min_proto_version(ctx.get(), version) ||
2673 !SSL_CTX_set_max_proto_version(ctx.get(), version) ||
2674 SSL_CTX_set_alpn_protos(ctx.get(), kALPNProtos, sizeof(kALPNProtos)) !=
2675 0) {
2676 return false;
2677 }
2678
2679 // The ALPN callback does not fail the handshake on error, so have the
2680 // callback write a boolean.
2681 std::pair<uint16_t, bool> callback_state(version, false);
2682 SSL_CTX_set_alpn_select_cb(
2683 ctx.get(),
2684 [](SSL *ssl, const uint8_t **out, uint8_t *out_len, const uint8_t *in,
2685 unsigned in_len, void *arg) -> int {
2686 auto state = reinterpret_cast<std::pair<uint16_t, bool> *>(arg);
2687 if (SSL_get_pending_cipher(ssl) != nullptr &&
2688 SSL_version(ssl) == state->first) {
2689 state->second = true;
2690 }
2691 return SSL_TLSEXT_ERR_NOACK;
2692 },
2693 &callback_state);
2694
2695 bssl::UniquePtr<SSL> client, server;
2696 if (!ConnectClientAndServer(&client, &server, ctx.get(), ctx.get(),
2697 nullptr /* no session */)) {
2698 return false;
2699 }
2700
2701 if (!callback_state.second) {
2702 fprintf(stderr, "The pending cipher was not known in the ALPN callback.\n");
2703 return false;
2704 }
2705
2706 return true;
2707}
2708
David Benjaminb79cc842016-12-07 15:57:14 -05002709static bool TestSSLClearSessionResumption(bool is_dtls,
2710 const SSL_METHOD *method,
2711 uint16_t version) {
2712 // Skip this for TLS 1.3. TLS 1.3's ticket mechanism is incompatible with this
2713 // API pattern.
2714 if (version == TLS1_3_VERSION) {
2715 return true;
2716 }
2717
2718 bssl::UniquePtr<X509> cert = GetTestCertificate();
2719 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
2720 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(method));
2721 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(method));
2722 if (!cert || !key || !server_ctx || !client_ctx ||
2723 !SSL_CTX_use_certificate(server_ctx.get(), cert.get()) ||
2724 !SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()) ||
2725 !SSL_CTX_set_min_proto_version(client_ctx.get(), version) ||
2726 !SSL_CTX_set_max_proto_version(client_ctx.get(), version) ||
2727 !SSL_CTX_set_min_proto_version(server_ctx.get(), version) ||
2728 !SSL_CTX_set_max_proto_version(server_ctx.get(), version)) {
2729 return false;
2730 }
2731
2732 // Connect a client and a server.
2733 bssl::UniquePtr<SSL> client, server;
2734 if (!ConnectClientAndServer(&client, &server, client_ctx.get(),
2735 server_ctx.get(), nullptr /* no session */)) {
2736 return false;
2737 }
2738
2739 if (SSL_session_reused(client.get()) ||
2740 SSL_session_reused(server.get())) {
2741 fprintf(stderr, "Session unexpectedly reused.\n");
2742 return false;
2743 }
2744
2745 // Reset everything.
2746 if (!SSL_clear(client.get()) ||
2747 !SSL_clear(server.get())) {
2748 fprintf(stderr, "SSL_clear failed.\n");
2749 return false;
2750 }
2751
2752 // Attempt to connect a second time.
2753 if (!CompleteHandshakes(client.get(), server.get())) {
2754 fprintf(stderr, "Could not reuse SSL objects.\n");
2755 return false;
2756 }
2757
2758 // |SSL_clear| should implicitly offer the previous session to the server.
2759 if (!SSL_session_reused(client.get()) ||
2760 !SSL_session_reused(server.get())) {
2761 fprintf(stderr, "Session was not reused in second try.\n");
2762 return false;
2763 }
2764
2765 return true;
2766}
2767
David Benjamin1444c3a2016-12-20 17:23:11 -05002768static bool ChainsEqual(STACK_OF(X509) *chain,
2769 const std::vector<X509 *> &expected) {
2770 if (sk_X509_num(chain) != expected.size()) {
2771 return false;
2772 }
2773
2774 for (size_t i = 0; i < expected.size(); i++) {
2775 if (X509_cmp(sk_X509_value(chain, i), expected[i]) != 0) {
2776 return false;
2777 }
2778 }
2779
2780 return true;
2781}
2782
2783static bool TestAutoChain(bool is_dtls, const SSL_METHOD *method,
2784 uint16_t version) {
David Benjamin1444c3a2016-12-20 17:23:11 -05002785 bssl::UniquePtr<X509> cert = GetChainTestCertificate();
2786 bssl::UniquePtr<X509> intermediate = GetChainTestIntermediate();
2787 bssl::UniquePtr<EVP_PKEY> key = GetChainTestKey();
2788 if (!cert || !intermediate || !key) {
2789 return false;
2790 }
2791
2792 // Configure both client and server to accept any certificate. Add
2793 // |intermediate| to the cert store.
2794 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(method));
2795 if (!ctx ||
2796 !SSL_CTX_use_certificate(ctx.get(), cert.get()) ||
2797 !SSL_CTX_use_PrivateKey(ctx.get(), key.get()) ||
2798 !SSL_CTX_set_min_proto_version(ctx.get(), version) ||
2799 !SSL_CTX_set_max_proto_version(ctx.get(), version) ||
2800 !X509_STORE_add_cert(SSL_CTX_get_cert_store(ctx.get()),
2801 intermediate.get())) {
2802 return false;
2803 }
2804 SSL_CTX_set_verify(
2805 ctx.get(), SSL_VERIFY_PEER | SSL_VERIFY_FAIL_IF_NO_PEER_CERT, nullptr);
2806 SSL_CTX_set_cert_verify_callback(ctx.get(), VerifySucceed, NULL);
2807
2808 // By default, the client and server should each only send the leaf.
2809 bssl::UniquePtr<SSL> client, server;
2810 if (!ConnectClientAndServer(&client, &server, ctx.get(), ctx.get(),
2811 nullptr /* no session */)) {
2812 return false;
2813 }
2814
2815 if (!ChainsEqual(SSL_get_peer_full_cert_chain(client.get()), {cert.get()})) {
2816 fprintf(stderr, "Client-received chain did not match.\n");
2817 return false;
2818 }
2819
2820 if (!ChainsEqual(SSL_get_peer_full_cert_chain(server.get()), {cert.get()})) {
2821 fprintf(stderr, "Server-received chain did not match.\n");
2822 return false;
2823 }
2824
2825 // If auto-chaining is enabled, then the intermediate is sent.
2826 SSL_CTX_clear_mode(ctx.get(), SSL_MODE_NO_AUTO_CHAIN);
2827 if (!ConnectClientAndServer(&client, &server, ctx.get(), ctx.get(),
2828 nullptr /* no session */)) {
2829 return false;
2830 }
2831
2832 if (!ChainsEqual(SSL_get_peer_full_cert_chain(client.get()),
2833 {cert.get(), intermediate.get()})) {
2834 fprintf(stderr, "Client-received chain did not match (auto-chaining).\n");
2835 return false;
2836 }
2837
2838 if (!ChainsEqual(SSL_get_peer_full_cert_chain(server.get()),
2839 {cert.get(), intermediate.get()})) {
2840 fprintf(stderr, "Server-received chain did not match (auto-chaining).\n");
2841 return false;
2842 }
2843
2844 // Auto-chaining does not override explicitly-configured intermediates.
2845 if (!SSL_CTX_add1_chain_cert(ctx.get(), cert.get()) ||
2846 !ConnectClientAndServer(&client, &server, ctx.get(), ctx.get(),
2847 nullptr /* no session */)) {
2848 return false;
2849 }
2850
2851 if (!ChainsEqual(SSL_get_peer_full_cert_chain(client.get()),
2852 {cert.get(), cert.get()})) {
2853 fprintf(stderr,
2854 "Client-received chain did not match (auto-chaining, explicit "
2855 "intermediate).\n");
2856 return false;
2857 }
2858
2859 if (!ChainsEqual(SSL_get_peer_full_cert_chain(server.get()),
2860 {cert.get(), cert.get()})) {
2861 fprintf(stderr,
2862 "Server-received chain did not match (auto-chaining, explicit "
2863 "intermediate).\n");
2864 return false;
2865 }
2866
2867 return true;
2868}
2869
David Benjamin48063c22017-01-01 23:56:36 -05002870static bool ExpectBadWriteRetry() {
2871 int err = ERR_get_error();
2872 if (ERR_GET_LIB(err) != ERR_LIB_SSL ||
2873 ERR_GET_REASON(err) != SSL_R_BAD_WRITE_RETRY) {
2874 char buf[ERR_ERROR_STRING_BUF_LEN];
2875 ERR_error_string_n(err, buf, sizeof(buf));
2876 fprintf(stderr, "Wanted SSL_R_BAD_WRITE_RETRY, got: %s.\n", buf);
2877 return false;
2878 }
2879
2880 if (ERR_peek_error() != 0) {
2881 fprintf(stderr, "Unexpected error following SSL_R_BAD_WRITE_RETRY.\n");
2882 return false;
2883 }
2884
2885 return true;
2886}
2887
2888static bool TestSSLWriteRetry(bool is_dtls, const SSL_METHOD *method,
2889 uint16_t version) {
2890 if (is_dtls) {
2891 return true;
2892 }
2893
2894 for (bool enable_partial_write : std::vector<bool>{false, true}) {
2895 // Connect a client and server.
2896 bssl::UniquePtr<X509> cert = GetTestCertificate();
2897 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
2898 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(method));
2899 bssl::UniquePtr<SSL> client, server;
2900 if (!cert || !key || !ctx ||
2901 !SSL_CTX_use_certificate(ctx.get(), cert.get()) ||
2902 !SSL_CTX_use_PrivateKey(ctx.get(), key.get()) ||
2903 !SSL_CTX_set_min_proto_version(ctx.get(), version) ||
2904 !SSL_CTX_set_max_proto_version(ctx.get(), version) ||
2905 !ConnectClientAndServer(&client, &server, ctx.get(), ctx.get(),
2906 nullptr /* no session */)) {
2907 return false;
2908 }
2909
2910 if (enable_partial_write) {
2911 SSL_set_mode(client.get(), SSL_MODE_ENABLE_PARTIAL_WRITE);
2912 }
2913
2914 // Write without reading until the buffer is full and we have an unfinished
2915 // write. Keep a count so we may reread it again later. "hello!" will be
2916 // written in two chunks, "hello" and "!".
2917 char data[] = "hello!";
2918 static const int kChunkLen = 5; // The length of "hello".
2919 unsigned count = 0;
2920 for (;;) {
2921 int ret = SSL_write(client.get(), data, kChunkLen);
2922 if (ret <= 0) {
2923 int err = SSL_get_error(client.get(), ret);
2924 if (SSL_get_error(client.get(), ret) == SSL_ERROR_WANT_WRITE) {
2925 break;
2926 }
2927 fprintf(stderr, "SSL_write failed in unexpected way: %d\n", err);
2928 return false;
2929 }
2930
2931 if (ret != 5) {
2932 fprintf(stderr, "SSL_write wrote %d bytes, expected 5.\n", ret);
2933 return false;
2934 }
2935
2936 count++;
2937 }
2938
2939 // Retrying with the same parameters is legal.
2940 if (SSL_get_error(client.get(), SSL_write(client.get(), data, kChunkLen)) !=
2941 SSL_ERROR_WANT_WRITE) {
2942 fprintf(stderr, "SSL_write retry unexpectedly failed.\n");
2943 return false;
2944 }
2945
2946 // Retrying with the same buffer but shorter length is not legal.
2947 if (SSL_get_error(client.get(),
2948 SSL_write(client.get(), data, kChunkLen - 1)) !=
2949 SSL_ERROR_SSL ||
2950 !ExpectBadWriteRetry()) {
2951 fprintf(stderr, "SSL_write retry did not fail as expected.\n");
2952 return false;
2953 }
2954
2955 // Retrying with a different buffer pointer is not legal.
2956 char data2[] = "hello";
2957 if (SSL_get_error(client.get(), SSL_write(client.get(), data2,
2958 kChunkLen)) != SSL_ERROR_SSL ||
2959 !ExpectBadWriteRetry()) {
2960 fprintf(stderr, "SSL_write retry did not fail as expected.\n");
2961 return false;
2962 }
2963
2964 // With |SSL_MODE_ACCEPT_MOVING_WRITE_BUFFER|, the buffer may move.
2965 SSL_set_mode(client.get(), SSL_MODE_ACCEPT_MOVING_WRITE_BUFFER);
2966 if (SSL_get_error(client.get(),
2967 SSL_write(client.get(), data2, kChunkLen)) !=
2968 SSL_ERROR_WANT_WRITE) {
2969 fprintf(stderr, "SSL_write retry unexpectedly failed.\n");
2970 return false;
2971 }
2972
2973 // |SSL_MODE_ACCEPT_MOVING_WRITE_BUFFER| does not disable length checks.
2974 if (SSL_get_error(client.get(),
2975 SSL_write(client.get(), data2, kChunkLen - 1)) !=
2976 SSL_ERROR_SSL ||
2977 !ExpectBadWriteRetry()) {
2978 fprintf(stderr, "SSL_write retry did not fail as expected.\n");
2979 return false;
2980 }
2981
2982 // Retrying with a larger buffer is legal.
2983 if (SSL_get_error(client.get(),
2984 SSL_write(client.get(), data, kChunkLen + 1)) !=
2985 SSL_ERROR_WANT_WRITE) {
2986 fprintf(stderr, "SSL_write retry unexpectedly failed.\n");
2987 return false;
2988 }
2989
2990 // Drain the buffer.
2991 char buf[20];
2992 for (unsigned i = 0; i < count; i++) {
2993 if (SSL_read(server.get(), buf, sizeof(buf)) != kChunkLen ||
2994 OPENSSL_memcmp(buf, "hello", kChunkLen) != 0) {
2995 fprintf(stderr, "Failed to read initial records.\n");
2996 return false;
2997 }
2998 }
2999
3000 // Now that there is space, a retry with a larger buffer should flush the
3001 // pending record, skip over that many bytes of input (on assumption they
3002 // are the same), and write the remainder. If SSL_MODE_ENABLE_PARTIAL_WRITE
3003 // is set, this will complete in two steps.
3004 char data3[] = "_____!";
3005 if (enable_partial_write) {
3006 if (SSL_write(client.get(), data3, kChunkLen + 1) != kChunkLen ||
3007 SSL_write(client.get(), data3 + kChunkLen, 1) != 1) {
3008 fprintf(stderr, "SSL_write retry failed.\n");
3009 return false;
3010 }
3011 } else if (SSL_write(client.get(), data3, kChunkLen + 1) != kChunkLen + 1) {
3012 fprintf(stderr, "SSL_write retry failed.\n");
3013 return false;
3014 }
3015
3016 // Check the last write was correct. The data will be spread over two
3017 // records, so SSL_read returns twice.
3018 if (SSL_read(server.get(), buf, sizeof(buf)) != kChunkLen ||
3019 OPENSSL_memcmp(buf, "hello", kChunkLen) != 0 ||
3020 SSL_read(server.get(), buf, sizeof(buf)) != 1 ||
3021 buf[0] != '!') {
3022 fprintf(stderr, "Failed to read write retry.\n");
3023 return false;
3024 }
3025 }
3026
3027 return true;
3028}
3029
David Benjamin0fef3052016-11-18 15:11:10 +09003030static bool ForEachVersion(bool (*test_func)(bool is_dtls,
3031 const SSL_METHOD *method,
3032 uint16_t version)) {
3033 static uint16_t kTLSVersions[] = {
David Benjamin3b584332017-01-24 22:47:18 -05003034 SSL3_VERSION,
3035 TLS1_VERSION,
3036 TLS1_1_VERSION,
3037 TLS1_2_VERSION,
3038// TLS 1.3 requires RSA-PSS, which is disabled for Android system builds.
3039#if !defined(BORINGSSL_ANDROID_SYSTEM)
3040 TLS1_3_VERSION,
3041#endif
David Benjamin0fef3052016-11-18 15:11:10 +09003042 };
3043
3044 static uint16_t kDTLSVersions[] = {
3045 DTLS1_VERSION, DTLS1_2_VERSION,
3046 };
3047
David Benjamin9ef31f02016-10-31 18:01:13 -04003048 for (uint16_t version : kTLSVersions) {
David Benjamin0fef3052016-11-18 15:11:10 +09003049 if (!test_func(false, TLS_method(), version)) {
3050 fprintf(stderr, "Test failed at TLS version %04x.\n", version);
David Benjamin9ef31f02016-10-31 18:01:13 -04003051 return false;
3052 }
David Benjamin0fef3052016-11-18 15:11:10 +09003053 }
David Benjamin9ef31f02016-10-31 18:01:13 -04003054
David Benjamin0fef3052016-11-18 15:11:10 +09003055 for (uint16_t version : kDTLSVersions) {
3056 if (!test_func(true, DTLS_method(), version)) {
3057 fprintf(stderr, "Test failed at DTLS version %04x.\n", version);
David Benjamin9ef31f02016-10-31 18:01:13 -04003058 return false;
3059 }
3060 }
3061
3062 return true;
3063}
3064
Adam Langleye1e78132017-01-31 15:24:31 -08003065TEST(SSLTest, AddChainCertHack) {
3066 // Ensure that we don't accidently break the hack that we have in place to
3067 // keep curl and serf happy when they use an |X509| even after transfering
3068 // ownership.
3069
3070 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
3071 ASSERT_TRUE(ctx);
3072 X509 *cert = GetTestCertificate().release();
3073 ASSERT_TRUE(cert);
3074 SSL_CTX_add0_chain_cert(ctx.get(), cert);
3075
3076 // This should not trigger a use-after-free.
3077 X509_cmp(cert, cert);
3078}
3079
David Benjaminb2ff2622017-02-03 17:06:18 -05003080TEST(SSLTest, GetCertificate) {
3081 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
3082 ASSERT_TRUE(ctx);
3083 bssl::UniquePtr<X509> cert = GetTestCertificate();
3084 ASSERT_TRUE(cert);
3085 ASSERT_TRUE(SSL_CTX_use_certificate(ctx.get(), cert.get()));
3086 bssl::UniquePtr<SSL> ssl(SSL_new(ctx.get()));
3087 ASSERT_TRUE(ssl);
3088
3089 X509 *cert2 = SSL_CTX_get0_certificate(ctx.get());
3090 ASSERT_TRUE(cert2);
3091 X509 *cert3 = SSL_get_certificate(ssl.get());
3092 ASSERT_TRUE(cert3);
3093
3094 // The old and new certificates must be identical.
3095 EXPECT_EQ(0, X509_cmp(cert.get(), cert2));
3096 EXPECT_EQ(0, X509_cmp(cert.get(), cert3));
3097
3098 uint8_t *der = nullptr;
3099 long der_len = i2d_X509(cert.get(), &der);
3100 ASSERT_LT(0, der_len);
3101 bssl::UniquePtr<uint8_t> free_der(der);
3102
3103 uint8_t *der2 = nullptr;
3104 long der2_len = i2d_X509(cert2, &der2);
3105 ASSERT_LT(0, der2_len);
3106 bssl::UniquePtr<uint8_t> free_der2(der2);
3107
3108 uint8_t *der3 = nullptr;
3109 long der3_len = i2d_X509(cert3, &der3);
3110 ASSERT_LT(0, der3_len);
3111 bssl::UniquePtr<uint8_t> free_der3(der3);
3112
3113 // They must also encode identically.
David Benjamin7d7554b2017-02-04 11:48:59 -05003114 EXPECT_EQ(Bytes(der, der_len), Bytes(der2, der2_len));
3115 EXPECT_EQ(Bytes(der, der_len), Bytes(der3, der3_len));
David Benjaminb2ff2622017-02-03 17:06:18 -05003116}
3117
Adam Langleyd04ca952017-02-28 11:26:51 -08003118TEST(SSLTest, SetChainAndKeyMismatch) {
3119 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_with_buffers_method()));
3120 ASSERT_TRUE(ctx);
3121
3122 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
3123 ASSERT_TRUE(key);
3124 bssl::UniquePtr<CRYPTO_BUFFER> leaf = GetChainTestCertificateBuffer();
3125 ASSERT_TRUE(leaf);
3126 std::vector<CRYPTO_BUFFER*> chain = {
3127 leaf.get(),
3128 };
3129
3130 // Should fail because |GetTestKey| doesn't match the chain-test certificate.
3131 ASSERT_FALSE(SSL_CTX_set_chain_and_key(ctx.get(), &chain[0], chain.size(),
3132 key.get(), nullptr));
3133 ERR_clear_error();
3134}
3135
3136TEST(SSLTest, SetChainAndKey) {
3137 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLS_with_buffers_method()));
3138 ASSERT_TRUE(client_ctx);
3139 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(TLS_with_buffers_method()));
3140 ASSERT_TRUE(server_ctx);
3141
3142 bssl::UniquePtr<EVP_PKEY> key = GetChainTestKey();
3143 ASSERT_TRUE(key);
3144 bssl::UniquePtr<CRYPTO_BUFFER> leaf = GetChainTestCertificateBuffer();
3145 ASSERT_TRUE(leaf);
3146 bssl::UniquePtr<CRYPTO_BUFFER> intermediate =
3147 GetChainTestIntermediateBuffer();
3148 ASSERT_TRUE(intermediate);
3149 std::vector<CRYPTO_BUFFER*> chain = {
3150 leaf.get(), intermediate.get(),
3151 };
3152 ASSERT_TRUE(SSL_CTX_set_chain_and_key(server_ctx.get(), &chain[0],
3153 chain.size(), key.get(), nullptr));
3154
3155 SSL_CTX_i_promise_to_verify_certs_after_the_handshake(client_ctx.get());
3156
3157 bssl::UniquePtr<SSL> client, server;
3158 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx.get(),
3159 server_ctx.get(),
3160 nullptr /* no session */));
3161}
3162
David Benjamin91222b82017-03-09 20:10:56 -05003163// Configuring the empty cipher list, though an error, should still modify the
3164// configuration.
3165TEST(SSLTest, EmptyCipherList) {
3166 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
3167 ASSERT_TRUE(ctx);
3168
3169 // Initially, the cipher list is not empty.
3170 EXPECT_NE(0u, sk_SSL_CIPHER_num(SSL_CTX_get_ciphers(ctx.get())));
3171
3172 // Configuring the empty cipher list fails.
3173 EXPECT_FALSE(SSL_CTX_set_cipher_list(ctx.get(), ""));
3174 ERR_clear_error();
3175
3176 // But the cipher list is still updated to empty.
3177 EXPECT_EQ(0u, sk_SSL_CIPHER_num(SSL_CTX_get_ciphers(ctx.get())));
3178}
3179
Adam Langley4c341d02017-03-08 19:33:21 -08003180// ssl_test_ticket_aead_failure_mode enumerates the possible ways in which the
3181// test |SSL_TICKET_AEAD_METHOD| can fail.
3182enum ssl_test_ticket_aead_failure_mode {
3183 ssl_test_ticket_aead_ok = 0,
3184 ssl_test_ticket_aead_seal_fail,
3185 ssl_test_ticket_aead_open_soft_fail,
3186 ssl_test_ticket_aead_open_hard_fail,
3187};
3188
3189struct ssl_test_ticket_aead_state {
3190 unsigned retry_count;
3191 ssl_test_ticket_aead_failure_mode failure_mode;
3192};
3193
3194static int ssl_test_ticket_aead_ex_index_dup(CRYPTO_EX_DATA *to,
3195 const CRYPTO_EX_DATA *from,
3196 void **from_d, int index,
3197 long argl, void *argp) {
3198 abort();
3199}
3200
3201static void ssl_test_ticket_aead_ex_index_free(void *parent, void *ptr,
3202 CRYPTO_EX_DATA *ad, int index,
3203 long argl, void *argp) {
3204 auto state = reinterpret_cast<ssl_test_ticket_aead_state*>(ptr);
3205 if (state == nullptr) {
3206 return;
3207 }
3208
3209 OPENSSL_free(state);
3210}
3211
3212static CRYPTO_once_t g_ssl_test_ticket_aead_ex_index_once = CRYPTO_ONCE_INIT;
3213static int g_ssl_test_ticket_aead_ex_index;
3214
3215static int ssl_test_ticket_aead_get_ex_index() {
3216 CRYPTO_once(&g_ssl_test_ticket_aead_ex_index_once, [] {
3217 g_ssl_test_ticket_aead_ex_index = SSL_get_ex_new_index(
3218 0, nullptr, nullptr, ssl_test_ticket_aead_ex_index_dup,
3219 ssl_test_ticket_aead_ex_index_free);
3220 });
3221 return g_ssl_test_ticket_aead_ex_index;
3222}
3223
3224static size_t ssl_test_ticket_aead_max_overhead(SSL *ssl) {
3225 return 1;
3226}
3227
3228static int ssl_test_ticket_aead_seal(SSL *ssl, uint8_t *out, size_t *out_len,
3229 size_t max_out_len, const uint8_t *in,
3230 size_t in_len) {
3231 auto state = reinterpret_cast<ssl_test_ticket_aead_state *>(
3232 SSL_get_ex_data(ssl, ssl_test_ticket_aead_get_ex_index()));
3233
3234 if (state->failure_mode == ssl_test_ticket_aead_seal_fail ||
3235 max_out_len < in_len + 1) {
3236 return 0;
3237 }
3238
3239 OPENSSL_memmove(out, in, in_len);
3240 out[in_len] = 0xff;
3241 *out_len = in_len + 1;
3242
3243 return 1;
3244}
3245
3246static ssl_ticket_aead_result_t ssl_test_ticket_aead_open(
3247 SSL *ssl, uint8_t *out, size_t *out_len, size_t max_out_len,
3248 const uint8_t *in, size_t in_len) {
3249 auto state = reinterpret_cast<ssl_test_ticket_aead_state *>(
3250 SSL_get_ex_data(ssl, ssl_test_ticket_aead_get_ex_index()));
3251
3252 if (state->retry_count > 0) {
3253 state->retry_count--;
3254 return ssl_ticket_aead_retry;
3255 }
3256
3257 switch (state->failure_mode) {
3258 case ssl_test_ticket_aead_ok:
3259 break;
3260 case ssl_test_ticket_aead_seal_fail:
3261 // If |seal| failed then there shouldn't be any ticket to try and
3262 // decrypt.
3263 abort();
3264 break;
3265 case ssl_test_ticket_aead_open_soft_fail:
3266 return ssl_ticket_aead_ignore_ticket;
3267 case ssl_test_ticket_aead_open_hard_fail:
3268 return ssl_ticket_aead_error;
3269 }
3270
3271 if (in_len == 0 || in[in_len - 1] != 0xff) {
3272 return ssl_ticket_aead_ignore_ticket;
3273 }
3274
3275 if (max_out_len < in_len - 1) {
3276 return ssl_ticket_aead_error;
3277 }
3278
3279 OPENSSL_memmove(out, in, in_len - 1);
3280 *out_len = in_len - 1;
3281 return ssl_ticket_aead_success;
3282}
3283
3284static const SSL_TICKET_AEAD_METHOD kSSLTestTicketMethod = {
3285 ssl_test_ticket_aead_max_overhead,
3286 ssl_test_ticket_aead_seal,
3287 ssl_test_ticket_aead_open,
3288};
3289
3290static void ConnectClientAndServerWithTicketMethod(
3291 bssl::UniquePtr<SSL> *out_client, bssl::UniquePtr<SSL> *out_server,
3292 SSL_CTX *client_ctx, SSL_CTX *server_ctx, unsigned retry_count,
3293 ssl_test_ticket_aead_failure_mode failure_mode, SSL_SESSION *session) {
3294 bssl::UniquePtr<SSL> client(SSL_new(client_ctx)), server(SSL_new(server_ctx));
3295 ASSERT_TRUE(client);
3296 ASSERT_TRUE(server);
3297 SSL_set_connect_state(client.get());
3298 SSL_set_accept_state(server.get());
3299
3300 auto state = reinterpret_cast<ssl_test_ticket_aead_state *>(
3301 OPENSSL_malloc(sizeof(ssl_test_ticket_aead_state)));
3302 ASSERT_TRUE(state);
3303 OPENSSL_memset(state, 0, sizeof(ssl_test_ticket_aead_state));
3304 state->retry_count = retry_count;
3305 state->failure_mode = failure_mode;
3306
3307 ASSERT_TRUE(SSL_set_ex_data(server.get(), ssl_test_ticket_aead_get_ex_index(),
3308 state));
3309
3310 SSL_set_session(client.get(), session);
3311
3312 BIO *bio1, *bio2;
3313 ASSERT_TRUE(BIO_new_bio_pair(&bio1, 0, &bio2, 0));
3314
3315 // SSL_set_bio takes ownership.
3316 SSL_set_bio(client.get(), bio1, bio1);
3317 SSL_set_bio(server.get(), bio2, bio2);
3318
3319 if (CompleteHandshakes(client.get(), server.get())) {
3320 *out_client = std::move(client);
3321 *out_server = std::move(server);
3322 } else {
3323 out_client->reset();
3324 out_server->reset();
3325 }
3326}
3327
3328class TicketAEADMethodTest
3329 : public ::testing::TestWithParam<testing::tuple<
3330 uint16_t, unsigned, ssl_test_ticket_aead_failure_mode>> {};
3331
3332TEST_P(TicketAEADMethodTest, Resume) {
3333 bssl::UniquePtr<X509> cert = GetTestCertificate();
3334 ASSERT_TRUE(cert);
3335 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
3336 ASSERT_TRUE(key);
3337
3338 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(TLS_method()));
3339 ASSERT_TRUE(server_ctx);
3340 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLS_method()));
3341 ASSERT_TRUE(client_ctx);
3342
3343 const uint16_t version = testing::get<0>(GetParam());
3344 const unsigned retry_count = testing::get<1>(GetParam());
3345 const ssl_test_ticket_aead_failure_mode failure_mode =
3346 testing::get<2>(GetParam());
3347
3348 ASSERT_TRUE(SSL_CTX_use_certificate(server_ctx.get(), cert.get()));
3349 ASSERT_TRUE(SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()));
3350 ASSERT_TRUE(SSL_CTX_set_min_proto_version(client_ctx.get(), version));
3351 ASSERT_TRUE(SSL_CTX_set_max_proto_version(client_ctx.get(), version));
3352 ASSERT_TRUE(SSL_CTX_set_min_proto_version(server_ctx.get(), version));
3353 ASSERT_TRUE(SSL_CTX_set_max_proto_version(server_ctx.get(), version));
3354
3355 SSL_CTX_set_session_cache_mode(client_ctx.get(), SSL_SESS_CACHE_BOTH);
3356 SSL_CTX_set_session_cache_mode(server_ctx.get(), SSL_SESS_CACHE_BOTH);
3357 SSL_CTX_set_current_time_cb(client_ctx.get(), FrozenTimeCallback);
3358 SSL_CTX_set_current_time_cb(server_ctx.get(), FrozenTimeCallback);
David Benjamin707af292017-03-10 17:47:18 -05003359 SSL_CTX_sess_set_new_cb(client_ctx.get(), SaveLastSession);
Adam Langley4c341d02017-03-08 19:33:21 -08003360
3361 SSL_CTX_set_ticket_aead_method(server_ctx.get(), &kSSLTestTicketMethod);
3362
3363 bssl::UniquePtr<SSL> client, server;
3364 ConnectClientAndServerWithTicketMethod(&client, &server, client_ctx.get(),
3365 server_ctx.get(), retry_count,
3366 failure_mode, nullptr);
3367 switch (failure_mode) {
3368 case ssl_test_ticket_aead_ok:
3369 case ssl_test_ticket_aead_open_hard_fail:
3370 case ssl_test_ticket_aead_open_soft_fail:
3371 ASSERT_TRUE(client);
3372 break;
3373 case ssl_test_ticket_aead_seal_fail:
3374 EXPECT_FALSE(client);
3375 return;
3376 }
3377 EXPECT_FALSE(SSL_session_reused(client.get()));
3378 EXPECT_FALSE(SSL_session_reused(server.get()));
3379
David Benjamin707af292017-03-10 17:47:18 -05003380 // Run the read loop to account for post-handshake tickets in TLS 1.3.
3381 SSL_read(client.get(), nullptr, 0);
3382
3383 bssl::UniquePtr<SSL_SESSION> session = std::move(g_last_session);
Adam Langley4c341d02017-03-08 19:33:21 -08003384 ConnectClientAndServerWithTicketMethod(&client, &server, client_ctx.get(),
3385 server_ctx.get(), retry_count,
David Benjamin707af292017-03-10 17:47:18 -05003386 failure_mode, session.get());
Adam Langley4c341d02017-03-08 19:33:21 -08003387 switch (failure_mode) {
3388 case ssl_test_ticket_aead_ok:
3389 ASSERT_TRUE(client);
3390 EXPECT_TRUE(SSL_session_reused(client.get()));
3391 EXPECT_TRUE(SSL_session_reused(server.get()));
3392 break;
3393 case ssl_test_ticket_aead_seal_fail:
3394 abort();
3395 break;
3396 case ssl_test_ticket_aead_open_hard_fail:
3397 EXPECT_FALSE(client);
3398 break;
3399 case ssl_test_ticket_aead_open_soft_fail:
3400 ASSERT_TRUE(client);
3401 EXPECT_FALSE(SSL_session_reused(client.get()));
3402 EXPECT_FALSE(SSL_session_reused(server.get()));
3403 }
3404}
3405
3406INSTANTIATE_TEST_CASE_P(
3407 TicketAEADMethodTests, TicketAEADMethodTest,
3408 testing::Combine(
David Benjamin707af292017-03-10 17:47:18 -05003409 testing::Values(TLS1_2_VERSION, TLS1_3_VERSION),
Adam Langley4c341d02017-03-08 19:33:21 -08003410 testing::Values(0, 1, 2),
3411 testing::Values(ssl_test_ticket_aead_ok,
3412 ssl_test_ticket_aead_seal_fail,
3413 ssl_test_ticket_aead_open_soft_fail,
3414 ssl_test_ticket_aead_open_hard_fail)));
3415
David Benjamin3cfeb952017-03-01 16:48:38 -05003416TEST(SSLTest, SSL3Method) {
3417 bssl::UniquePtr<X509> cert = GetTestCertificate();
3418 ASSERT_TRUE(cert);
3419
3420 // For compatibility, SSLv3_method should work up to SSL_CTX_new and SSL_new.
3421 bssl::UniquePtr<SSL_CTX> ssl3_ctx(SSL_CTX_new(SSLv3_method()));
3422 ASSERT_TRUE(ssl3_ctx);
3423 ASSERT_TRUE(SSL_CTX_use_certificate(ssl3_ctx.get(), cert.get()));
3424 bssl::UniquePtr<SSL> ssl(SSL_new(ssl3_ctx.get()));
3425 EXPECT_TRUE(ssl);
3426
3427 // Create a normal TLS context to test against.
3428 bssl::UniquePtr<SSL_CTX> tls_ctx(SSL_CTX_new(TLS_method()));
3429 ASSERT_TRUE(tls_ctx);
3430 ASSERT_TRUE(SSL_CTX_use_certificate(tls_ctx.get(), cert.get()));
3431
3432 // However, handshaking an SSLv3_method server should fail to resolve the
3433 // version range. Explicit calls to SSL_CTX_set_min_proto_version are the only
3434 // way to enable SSL 3.0.
3435 bssl::UniquePtr<SSL> client, server;
3436 EXPECT_FALSE(ConnectClientAndServer(&client, &server, tls_ctx.get(),
3437 ssl3_ctx.get(),
3438 nullptr /* no session */));
3439 uint32_t err = ERR_get_error();
3440 EXPECT_EQ(ERR_LIB_SSL, ERR_GET_LIB(err));
3441 EXPECT_EQ(SSL_R_NO_SUPPORTED_VERSIONS_ENABLED, ERR_GET_REASON(err));
3442
3443 // Likewise for SSLv3_method clients.
3444 EXPECT_FALSE(ConnectClientAndServer(&client, &server, ssl3_ctx.get(),
3445 tls_ctx.get(),
3446 nullptr /* no session */));
3447 err = ERR_get_error();
3448 EXPECT_EQ(ERR_LIB_SSL, ERR_GET_LIB(err));
3449 EXPECT_EQ(SSL_R_NO_SUPPORTED_VERSIONS_ENABLED, ERR_GET_REASON(err));
3450}
3451
David Benjamin96628432017-01-19 19:05:47 -05003452// TODO(davidben): Convert this file to GTest properly.
3453TEST(SSLTest, AllTests) {
David Benjamine11726a2017-04-23 12:14:28 -04003454 if (!TestSSL_SESSIONEncoding(kOpenSSLSession) ||
Adam Langley10f97f32016-07-12 08:09:33 -07003455 !TestSSL_SESSIONEncoding(kCustomSession) ||
3456 !TestSSL_SESSIONEncoding(kBoringSSLSession) ||
3457 !TestBadSSL_SESSIONEncoding(kBadSessionExtraField) ||
3458 !TestBadSSL_SESSIONEncoding(kBadSessionVersion) ||
3459 !TestBadSSL_SESSIONEncoding(kBadSessionTrailingData) ||
David Benjamin10e664b2016-06-20 22:20:47 -04003460 // TODO(svaldez): Update this when TLS 1.3 is enabled by default.
David Benjamin3cfeb952017-03-01 16:48:38 -05003461 !TestDefaultVersion(TLS1_VERSION, TLS1_2_VERSION, &TLS_method) ||
Adam Langley10f97f32016-07-12 08:09:33 -07003462 !TestDefaultVersion(TLS1_VERSION, TLS1_VERSION, &TLSv1_method) ||
3463 !TestDefaultVersion(TLS1_1_VERSION, TLS1_1_VERSION, &TLSv1_1_method) ||
3464 !TestDefaultVersion(TLS1_2_VERSION, TLS1_2_VERSION, &TLSv1_2_method) ||
3465 !TestDefaultVersion(TLS1_1_VERSION, TLS1_2_VERSION, &DTLS_method) ||
3466 !TestDefaultVersion(TLS1_1_VERSION, TLS1_1_VERSION, &DTLSv1_method) ||
3467 !TestDefaultVersion(TLS1_2_VERSION, TLS1_2_VERSION, &DTLSv1_2_method) ||
Steven Valdeza833c352016-11-01 13:39:36 -04003468 // Test the padding extension at TLS 1.2.
3469 !TestPaddingExtension(TLS1_2_VERSION, TLS1_2_VERSION) ||
3470 // Test the padding extension at TLS 1.3 with a TLS 1.2 session, so there
3471 // will be no PSK binder after the padding extension.
3472 !TestPaddingExtension(TLS1_3_VERSION, TLS1_2_VERSION) ||
3473 // Test the padding extension at TLS 1.3 with a TLS 1.3 session, so there
3474 // will be a PSK binder after the padding extension.
3475 !TestPaddingExtension(TLS1_3_VERSION, TLS1_3_DRAFT_VERSION) ||
David Benjamin0fef3052016-11-18 15:11:10 +09003476 !ForEachVersion(TestSequenceNumber) ||
David Benjamin68f37b72016-11-18 15:14:42 +09003477 !ForEachVersion(TestOneSidedShutdown) ||
David Benjamin0fef3052016-11-18 15:11:10 +09003478 !ForEachVersion(TestGetPeerCertificate) ||
3479 !ForEachVersion(TestRetainOnlySHA256OfCerts) ||
David Benjamina20e5352016-08-02 19:09:41 -04003480 !TestClientHello() ||
David Benjamin0fef3052016-11-18 15:11:10 +09003481 !ForEachVersion(TestSessionIDContext) ||
3482 !ForEachVersion(TestSessionTimeout) ||
3483 !ForEachVersion(TestSNICallback) ||
David Benjamin0fef3052016-11-18 15:11:10 +09003484 !ForEachVersion(TestVersion) ||
David Benjaminb79cc842016-12-07 15:57:14 -05003485 !ForEachVersion(TestALPNCipherAvailable) ||
David Benjamin1444c3a2016-12-20 17:23:11 -05003486 !ForEachVersion(TestSSLClearSessionResumption) ||
David Benjamin48063c22017-01-01 23:56:36 -05003487 !ForEachVersion(TestAutoChain) ||
3488 !ForEachVersion(TestSSLWriteRetry)) {
David Benjamin96628432017-01-19 19:05:47 -05003489 ADD_FAILURE() << "Tests failed";
David Benjaminbb0a17c2014-09-20 15:35:39 -04003490 }
David Benjamin2e521212014-07-16 14:37:51 -04003491}