blob: 3d283f1b41dbdec3377509fb4ac984fd59d82e7e [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>
Steven Valdezc8e0f902018-07-14 11:23:01 -040020#include <limits>
David Benjamin1d77e562015-03-22 17:22:08 -040021#include <string>
David Benjamin4f6acaf2015-11-21 03:00:50 -050022#include <utility>
David Benjamin1d77e562015-03-22 17:22:08 -040023#include <vector>
24
David Benjamin96628432017-01-19 19:05:47 -050025#include <gtest/gtest.h>
26
David Benjamin0e7dbd52019-05-15 16:01:18 -040027#include <openssl/aead.h>
David Benjamin751e8892014-10-19 00:59:36 -040028#include <openssl/base64.h>
29#include <openssl/bio.h>
David Benjamin3c51d9b2016-11-01 17:50:42 -040030#include <openssl/cipher.h>
David Benjamin7a1eefd2015-10-17 23:39:22 -040031#include <openssl/crypto.h>
Daniel McArdle00e434d2021-02-18 11:47:18 -050032#include <openssl/curve25519.h>
David Benjaminbb0a17c2014-09-20 15:35:39 -040033#include <openssl/err.h>
David Benjamin3c51d9b2016-11-01 17:50:42 -040034#include <openssl/hmac.h>
David Benjaminde942382016-02-11 12:02:01 -050035#include <openssl/pem.h>
David Benjamin25490f22016-07-14 00:22:54 -040036#include <openssl/sha.h>
David Benjaminbb0a17c2014-09-20 15:35:39 -040037#include <openssl/ssl.h>
David Benjamin3c51d9b2016-11-01 17:50:42 -040038#include <openssl/rand.h>
David Benjaminde942382016-02-11 12:02:01 -050039#include <openssl/x509.h>
David Benjaminbb0a17c2014-09-20 15:35:39 -040040
Steven Valdez87eab492016-06-27 16:34:59 -040041#include "internal.h"
Steven Valdezcb966542016-08-17 16:56:14 -040042#include "../crypto/internal.h"
Sigbjorn Vik2b23d242015-06-29 15:07:26 +020043#include "../crypto/test/test_util.h"
44
David Benjamin721e8b72016-08-03 13:13:17 -040045#if defined(OPENSSL_WINDOWS)
David Benjaminc11ea9422017-08-29 16:33:21 -040046// Windows defines struct timeval in winsock2.h.
David Benjamin721e8b72016-08-03 13:13:17 -040047OPENSSL_MSVC_PRAGMA(warning(push, 3))
48#include <winsock2.h>
49OPENSSL_MSVC_PRAGMA(warning(pop))
50#else
51#include <sys/time.h>
52#endif
53
David Benjamin5b33eff2018-09-22 16:52:48 -070054#if defined(OPENSSL_THREADS)
David Benjamin6c04bd12018-07-19 18:13:09 -040055#include <thread>
56#endif
57
David Benjamin1d77e562015-03-22 17:22:08 -040058
Joshua Liebow-Feeser8c7c6352018-08-26 18:53:36 -070059BSSL_NAMESPACE_BEGIN
Martin Kreichgauer72912d22017-08-04 12:06:43 -070060
61namespace {
62
Martin Kreichgauer1a663262017-08-16 14:54:04 -070063#define TRACED_CALL(code) \
64 do { \
65 SCOPED_TRACE("<- called from here"); \
66 code; \
67 if (::testing::Test::HasFatalFailure()) { \
68 return; \
69 } \
70 } while (false)
71
Martin Kreichgauer72912d22017-08-04 12:06:43 -070072struct VersionParam {
73 uint16_t version;
74 enum { is_tls, is_dtls } ssl_method;
75 const char name[8];
76};
77
78static const size_t kTicketKeyLen = 48;
79
80static const VersionParam kAllVersions[] = {
Martin Kreichgauer72912d22017-08-04 12:06:43 -070081 {TLS1_VERSION, VersionParam::is_tls, "TLS1"},
82 {TLS1_1_VERSION, VersionParam::is_tls, "TLS1_1"},
83 {TLS1_2_VERSION, VersionParam::is_tls, "TLS1_2"},
Martin Kreichgauer72912d22017-08-04 12:06:43 -070084 {TLS1_3_VERSION, VersionParam::is_tls, "TLS1_3"},
Martin Kreichgauer72912d22017-08-04 12:06:43 -070085 {DTLS1_VERSION, VersionParam::is_dtls, "DTLS1"},
86 {DTLS1_2_VERSION, VersionParam::is_dtls, "DTLS1_2"},
87};
88
David Benjamin1d77e562015-03-22 17:22:08 -040089struct ExpectedCipher {
90 unsigned long id;
David Benjaminbb0a17c2014-09-20 15:35:39 -040091 int in_group_flag;
David Benjamin1d77e562015-03-22 17:22:08 -040092};
David Benjaminbb0a17c2014-09-20 15:35:39 -040093
David Benjamin1d77e562015-03-22 17:22:08 -040094struct CipherTest {
95 // The rule string to apply.
David Benjaminbb0a17c2014-09-20 15:35:39 -040096 const char *rule;
David Benjaminfb974e62015-12-16 19:34:22 -050097 // The list of expected ciphers, in order.
98 std::vector<ExpectedCipher> expected;
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -080099 // True if this cipher list should fail in strict mode.
100 bool strict_fail;
David Benjamin1d77e562015-03-22 17:22:08 -0400101};
David Benjaminbb0a17c2014-09-20 15:35:39 -0400102
Alessandro Ghedini5fd18072016-09-28 21:04:25 +0100103struct CurveTest {
104 // The rule string to apply.
105 const char *rule;
106 // The list of expected curves, in order.
107 std::vector<uint16_t> expected;
108};
109
Steven Valdezc8e0f902018-07-14 11:23:01 -0400110template <typename T>
111class UnownedSSLExData {
112 public:
113 UnownedSSLExData() {
114 index_ = SSL_get_ex_new_index(0, nullptr, nullptr, nullptr, nullptr);
115 }
116
117 T *Get(const SSL *ssl) {
118 return index_ < 0 ? nullptr
119 : static_cast<T *>(SSL_get_ex_data(ssl, index_));
120 }
121
122 bool Set(SSL *ssl, T *t) {
123 return index_ >= 0 && SSL_set_ex_data(ssl, index_, t);
124 }
125
126 private:
127 int index_;
128};
129
David Benjaminfb974e62015-12-16 19:34:22 -0500130static const CipherTest kCipherTests[] = {
131 // Selecting individual ciphers should work.
132 {
133 "ECDHE-ECDSA-CHACHA20-POLY1305:"
134 "ECDHE-RSA-CHACHA20-POLY1305:"
135 "ECDHE-ECDSA-AES128-GCM-SHA256:"
136 "ECDHE-RSA-AES128-GCM-SHA256",
137 {
138 {TLS1_CK_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256, 0},
David Benjaminfb974e62015-12-16 19:34:22 -0500139 {TLS1_CK_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256, 0},
David Benjaminfb974e62015-12-16 19:34:22 -0500140 {TLS1_CK_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, 0},
141 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 0},
142 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800143 false,
David Benjaminfb974e62015-12-16 19:34:22 -0500144 },
145 // + reorders selected ciphers to the end, keeping their relative order.
146 {
147 "ECDHE-ECDSA-CHACHA20-POLY1305:"
148 "ECDHE-RSA-CHACHA20-POLY1305:"
149 "ECDHE-ECDSA-AES128-GCM-SHA256:"
150 "ECDHE-RSA-AES128-GCM-SHA256:"
151 "+aRSA",
152 {
153 {TLS1_CK_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256, 0},
David Benjaminfb974e62015-12-16 19:34:22 -0500154 {TLS1_CK_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, 0},
155 {TLS1_CK_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256, 0},
David Benjaminfb974e62015-12-16 19:34:22 -0500156 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 0},
157 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800158 false,
David Benjaminfb974e62015-12-16 19:34:22 -0500159 },
160 // ! banishes ciphers from future selections.
161 {
162 "!aRSA:"
163 "ECDHE-ECDSA-CHACHA20-POLY1305:"
164 "ECDHE-RSA-CHACHA20-POLY1305:"
165 "ECDHE-ECDSA-AES128-GCM-SHA256:"
166 "ECDHE-RSA-AES128-GCM-SHA256",
167 {
168 {TLS1_CK_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256, 0},
David Benjaminfb974e62015-12-16 19:34:22 -0500169 {TLS1_CK_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, 0},
170 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800171 false,
David Benjaminfb974e62015-12-16 19:34:22 -0500172 },
173 // Multiple masks can be ANDed in a single rule.
174 {
175 "kRSA+AESGCM+AES128",
176 {
177 {TLS1_CK_RSA_WITH_AES_128_GCM_SHA256, 0},
178 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800179 false,
David Benjaminfb974e62015-12-16 19:34:22 -0500180 },
181 // - removes selected ciphers, but preserves their order for future
Matthew Braithwaitecedc6f12017-03-15 19:20:23 -0700182 // selections. Select AES_128_GCM, but order the key exchanges RSA,
David Benjaminfb974e62015-12-16 19:34:22 -0500183 // ECDHE_RSA.
184 {
Matthew Braithwaitecedc6f12017-03-15 19:20:23 -0700185 "ALL:-kECDHE:"
Matthew Braithwaitecedc6f12017-03-15 19:20:23 -0700186 "-kRSA:-ALL:"
David Benjaminfb974e62015-12-16 19:34:22 -0500187 "AESGCM+AES128+aRSA",
188 {
189 {TLS1_CK_RSA_WITH_AES_128_GCM_SHA256, 0},
David Benjaminfb974e62015-12-16 19:34:22 -0500190 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 0},
191 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800192 false,
David Benjaminfb974e62015-12-16 19:34:22 -0500193 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800194 // Unknown selectors are no-ops, except in strict mode.
David Benjaminfb974e62015-12-16 19:34:22 -0500195 {
196 "ECDHE-ECDSA-CHACHA20-POLY1305:"
197 "ECDHE-RSA-CHACHA20-POLY1305:"
198 "ECDHE-ECDSA-AES128-GCM-SHA256:"
199 "ECDHE-RSA-AES128-GCM-SHA256:"
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800200 "BOGUS1",
David Benjaminfb974e62015-12-16 19:34:22 -0500201 {
202 {TLS1_CK_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256, 0},
David Benjaminfb974e62015-12-16 19:34:22 -0500203 {TLS1_CK_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256, 0},
David Benjaminfb974e62015-12-16 19:34:22 -0500204 {TLS1_CK_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, 0},
205 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 0},
206 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800207 true,
208 },
209 // Unknown selectors are no-ops, except in strict mode.
210 {
211 "ECDHE-ECDSA-CHACHA20-POLY1305:"
212 "ECDHE-RSA-CHACHA20-POLY1305:"
213 "ECDHE-ECDSA-AES128-GCM-SHA256:"
214 "ECDHE-RSA-AES128-GCM-SHA256:"
215 "-BOGUS2:+BOGUS3:!BOGUS4",
216 {
217 {TLS1_CK_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256, 0},
218 {TLS1_CK_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256, 0},
219 {TLS1_CK_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, 0},
220 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 0},
221 },
222 true,
David Benjaminfb974e62015-12-16 19:34:22 -0500223 },
224 // Square brackets specify equi-preference groups.
225 {
226 "[ECDHE-ECDSA-CHACHA20-POLY1305|ECDHE-ECDSA-AES128-GCM-SHA256]:"
227 "[ECDHE-RSA-CHACHA20-POLY1305]:"
228 "ECDHE-RSA-AES128-GCM-SHA256",
229 {
230 {TLS1_CK_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256, 1},
David Benjaminfb974e62015-12-16 19:34:22 -0500231 {TLS1_CK_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, 0},
Adam Langley2e839242017-01-19 15:12:44 -0800232 {TLS1_CK_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256, 0},
David Benjaminfb974e62015-12-16 19:34:22 -0500233 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 0},
234 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800235 false,
David Benjaminfb974e62015-12-16 19:34:22 -0500236 },
David Benjamin6fff3862017-06-21 21:07:04 -0400237 // Standard names may be used instead of OpenSSL names.
238 {
239 "[TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256|"
David Benjaminbf5f1922017-07-01 11:13:53 -0400240 "TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256]:"
David Benjamin6fff3862017-06-21 21:07:04 -0400241 "[TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256]:"
242 "TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256",
243 {
244 {TLS1_CK_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256, 1},
245 {TLS1_CK_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, 0},
246 {TLS1_CK_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256, 0},
247 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 0},
248 },
249 false,
250 },
David Benjaminfb974e62015-12-16 19:34:22 -0500251 // @STRENGTH performs a stable strength-sort of the selected ciphers and
252 // only the selected ciphers.
253 {
254 // To simplify things, banish all but {ECDHE_RSA,RSA} x
Matthew Braithwaite8aaa9e12016-09-07 15:09:58 -0700255 // {CHACHA20,AES_256_CBC,AES_128_CBC} x SHA1.
David Benjamin6e678ee2018-04-16 19:54:42 -0400256 "!AESGCM:!3DES:"
David Benjaminfb974e62015-12-16 19:34:22 -0500257 // Order some ciphers backwards by strength.
Matthew Braithwaite8aaa9e12016-09-07 15:09:58 -0700258 "ALL:-CHACHA20:-AES256:-AES128:-ALL:"
David Benjaminfb974e62015-12-16 19:34:22 -0500259 // Select ECDHE ones and sort them by strength. Ties should resolve
260 // based on the order above.
261 "kECDHE:@STRENGTH:-ALL:"
262 // Now bring back everything uses RSA. ECDHE_RSA should be first, sorted
263 // by strength. Then RSA, backwards by strength.
264 "aRSA",
265 {
266 {TLS1_CK_ECDHE_RSA_WITH_AES_256_CBC_SHA, 0},
267 {TLS1_CK_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256, 0},
David Benjaminfb974e62015-12-16 19:34:22 -0500268 {TLS1_CK_ECDHE_RSA_WITH_AES_128_CBC_SHA, 0},
David Benjaminfb974e62015-12-16 19:34:22 -0500269 {TLS1_CK_RSA_WITH_AES_128_SHA, 0},
270 {TLS1_CK_RSA_WITH_AES_256_SHA, 0},
271 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800272 false,
David Benjaminfb974e62015-12-16 19:34:22 -0500273 },
David Benjaminbf5f1922017-07-01 11:13:53 -0400274 // Additional masks after @STRENGTH get silently discarded.
275 //
276 // TODO(davidben): Make this an error. If not silently discarded, they get
277 // interpreted as + opcodes which are very different.
278 {
279 "ECDHE-RSA-AES128-GCM-SHA256:"
280 "ECDHE-RSA-AES256-GCM-SHA384:"
281 "@STRENGTH+AES256",
282 {
283 {TLS1_CK_ECDHE_RSA_WITH_AES_256_GCM_SHA384, 0},
284 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 0},
285 },
286 false,
287 },
288 {
289 "ECDHE-RSA-AES128-GCM-SHA256:"
290 "ECDHE-RSA-AES256-GCM-SHA384:"
291 "@STRENGTH+AES256:"
292 "ECDHE-RSA-CHACHA20-POLY1305",
293 {
294 {TLS1_CK_ECDHE_RSA_WITH_AES_256_GCM_SHA384, 0},
295 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 0},
296 {TLS1_CK_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256, 0},
297 },
298 false,
299 },
David Benjaminfb974e62015-12-16 19:34:22 -0500300 // Exact ciphers may not be used in multi-part rules; they are treated
301 // as unknown aliases.
302 {
303 "ECDHE-ECDSA-AES128-GCM-SHA256:"
304 "ECDHE-RSA-AES128-GCM-SHA256:"
305 "!ECDHE-RSA-AES128-GCM-SHA256+RSA:"
306 "!ECDSA+ECDHE-ECDSA-AES128-GCM-SHA256",
307 {
308 {TLS1_CK_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, 0},
309 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 0},
310 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800311 true,
David Benjaminfb974e62015-12-16 19:34:22 -0500312 },
313 // SSLv3 matches everything that existed before TLS 1.2.
314 {
David Benjamin6e678ee2018-04-16 19:54:42 -0400315 "AES128-SHA:ECDHE-RSA-AES128-GCM-SHA256:!SSLv3",
David Benjaminfb974e62015-12-16 19:34:22 -0500316 {
David Benjamin6e678ee2018-04-16 19:54:42 -0400317 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 0},
David Benjaminfb974e62015-12-16 19:34:22 -0500318 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800319 false,
David Benjaminfb974e62015-12-16 19:34:22 -0500320 },
321 // TLSv1.2 matches everything added in TLS 1.2.
322 {
David Benjamin6e678ee2018-04-16 19:54:42 -0400323 "AES128-SHA:ECDHE-RSA-AES128-GCM-SHA256:!TLSv1.2",
David Benjaminfb974e62015-12-16 19:34:22 -0500324 {
325 {TLS1_CK_RSA_WITH_AES_128_SHA, 0},
326 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800327 false,
David Benjaminfb974e62015-12-16 19:34:22 -0500328 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800329 // The two directives have no intersection. But each component is valid, so
330 // even in strict mode it is accepted.
David Benjaminfb974e62015-12-16 19:34:22 -0500331 {
David Benjamin6e678ee2018-04-16 19:54:42 -0400332 "AES128-SHA:ECDHE-RSA-AES128-GCM-SHA256:!TLSv1.2+SSLv3",
David Benjaminfb974e62015-12-16 19:34:22 -0500333 {
334 {TLS1_CK_RSA_WITH_AES_128_SHA, 0},
David Benjamin6e678ee2018-04-16 19:54:42 -0400335 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 0},
David Benjaminfb974e62015-12-16 19:34:22 -0500336 },
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -0800337 false,
David Benjaminfb974e62015-12-16 19:34:22 -0500338 },
Adam Langley22df6912017-07-25 12:27:37 -0700339 // Spaces, semi-colons and commas are separators.
340 {
David Benjamin6e678ee2018-04-16 19:54:42 -0400341 "AES128-SHA: ECDHE-RSA-AES128-GCM-SHA256 AES256-SHA ,ECDHE-ECDSA-AES128-GCM-SHA256 ; AES128-GCM-SHA256",
Adam Langley22df6912017-07-25 12:27:37 -0700342 {
343 {TLS1_CK_RSA_WITH_AES_128_SHA, 0},
David Benjamin6e678ee2018-04-16 19:54:42 -0400344 {TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 0},
Adam Langley22df6912017-07-25 12:27:37 -0700345 {TLS1_CK_RSA_WITH_AES_256_SHA, 0},
David Benjamin6e678ee2018-04-16 19:54:42 -0400346 {TLS1_CK_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, 0},
Adam Langley22df6912017-07-25 12:27:37 -0700347 {TLS1_CK_RSA_WITH_AES_128_GCM_SHA256, 0},
348 },
349 // …but not in strict mode.
350 true,
351 },
David Benjaminbb0a17c2014-09-20 15:35:39 -0400352};
353
354static const char *kBadRules[] = {
David Benjamin1d77e562015-03-22 17:22:08 -0400355 // Invalid brackets.
David Benjaminbb0a17c2014-09-20 15:35:39 -0400356 "[ECDHE-RSA-CHACHA20-POLY1305|ECDHE-RSA-AES128-GCM-SHA256",
357 "RSA]",
358 "[[RSA]]",
David Benjamin1d77e562015-03-22 17:22:08 -0400359 // Operators inside brackets.
David Benjaminbb0a17c2014-09-20 15:35:39 -0400360 "[+RSA]",
David Benjamin1d77e562015-03-22 17:22:08 -0400361 // Unknown directive.
David Benjaminbb0a17c2014-09-20 15:35:39 -0400362 "@BOGUS",
David Benjamin1d77e562015-03-22 17:22:08 -0400363 // Empty cipher lists error at SSL_CTX_set_cipher_list.
David Benjaminbb0a17c2014-09-20 15:35:39 -0400364 "",
365 "BOGUS",
David Benjamin32fbdf22015-04-07 01:14:06 -0400366 // COMPLEMENTOFDEFAULT is empty.
367 "COMPLEMENTOFDEFAULT",
David Benjamin1d77e562015-03-22 17:22:08 -0400368 // Invalid command.
David Benjaminbb0a17c2014-09-20 15:35:39 -0400369 "?BAR",
David Benjamin1d77e562015-03-22 17:22:08 -0400370 // Special operators are not allowed if groups are used.
David Benjamin37d92462014-09-20 17:54:24 -0400371 "[ECDHE-RSA-CHACHA20-POLY1305|ECDHE-RSA-AES128-GCM-SHA256]:+FOO",
372 "[ECDHE-RSA-CHACHA20-POLY1305|ECDHE-RSA-AES128-GCM-SHA256]:!FOO",
373 "[ECDHE-RSA-CHACHA20-POLY1305|ECDHE-RSA-AES128-GCM-SHA256]:-FOO",
374 "[ECDHE-RSA-CHACHA20-POLY1305|ECDHE-RSA-AES128-GCM-SHA256]:@STRENGTH",
Adam Langleyf99f2442016-10-02 09:53:38 -0700375 // Opcode supplied, but missing selector.
376 "+",
Adam Langley22df6912017-07-25 12:27:37 -0700377 // Spaces are forbidden in equal-preference groups.
378 "[AES128-SHA | AES128-SHA256]",
David Benjaminbb0a17c2014-09-20 15:35:39 -0400379};
380
Matt Braithwaiteaf096752015-09-02 19:48:16 -0700381static const char *kMustNotIncludeNull[] = {
382 "ALL",
383 "DEFAULT",
David Benjamind6e9eec2015-11-18 09:48:55 -0500384 "HIGH",
Matt Braithwaiteaf096752015-09-02 19:48:16 -0700385 "FIPS",
386 "SHA",
387 "SHA1",
388 "RSA",
389 "SSLv3",
390 "TLSv1",
391 "TLSv1.2",
Matt Braithwaiteaf096752015-09-02 19:48:16 -0700392};
393
Alessandro Ghedini5fd18072016-09-28 21:04:25 +0100394static const CurveTest kCurveTests[] = {
395 {
396 "P-256",
397 { SSL_CURVE_SECP256R1 },
398 },
399 {
Adam Langley7b935932018-11-12 13:53:42 -0800400 "P-256:CECPQ2",
401 { SSL_CURVE_SECP256R1, SSL_CURVE_CECPQ2 },
402 },
403
404 {
Alessandro Ghedini5fd18072016-09-28 21:04:25 +0100405 "P-256:P-384:P-521:X25519",
406 {
407 SSL_CURVE_SECP256R1,
408 SSL_CURVE_SECP384R1,
409 SSL_CURVE_SECP521R1,
410 SSL_CURVE_X25519,
411 },
412 },
David Benjamin6dda1662017-11-02 20:44:26 -0400413 {
414 "prime256v1:secp384r1:secp521r1:x25519",
415 {
416 SSL_CURVE_SECP256R1,
417 SSL_CURVE_SECP384R1,
418 SSL_CURVE_SECP521R1,
419 SSL_CURVE_X25519,
420 },
421 },
Alessandro Ghedini5fd18072016-09-28 21:04:25 +0100422};
423
424static const char *kBadCurvesLists[] = {
425 "",
426 ":",
427 "::",
428 "P-256::X25519",
429 "RSA:P-256",
430 "P-256:RSA",
431 "X25519:P-256:",
432 ":X25519:P-256",
433};
434
David Benjamin70dbf042017-08-08 18:51:37 -0400435static std::string CipherListToString(SSL_CTX *ctx) {
David Benjamin1d77e562015-03-22 17:22:08 -0400436 bool in_group = false;
David Benjamine11726a2017-04-23 12:14:28 -0400437 std::string ret;
David Benjamin70dbf042017-08-08 18:51:37 -0400438 const STACK_OF(SSL_CIPHER) *ciphers = SSL_CTX_get_ciphers(ctx);
439 for (size_t i = 0; i < sk_SSL_CIPHER_num(ciphers); i++) {
440 const SSL_CIPHER *cipher = sk_SSL_CIPHER_value(ciphers, i);
441 if (!in_group && SSL_CTX_cipher_in_group(ctx, i)) {
David Benjamine11726a2017-04-23 12:14:28 -0400442 ret += "\t[\n";
David Benjamin1d77e562015-03-22 17:22:08 -0400443 in_group = true;
David Benjaminbb0a17c2014-09-20 15:35:39 -0400444 }
David Benjamine11726a2017-04-23 12:14:28 -0400445 ret += "\t";
David Benjaminbb0a17c2014-09-20 15:35:39 -0400446 if (in_group) {
David Benjamine11726a2017-04-23 12:14:28 -0400447 ret += " ";
David Benjaminbb0a17c2014-09-20 15:35:39 -0400448 }
David Benjamine11726a2017-04-23 12:14:28 -0400449 ret += SSL_CIPHER_get_name(cipher);
450 ret += "\n";
David Benjamin70dbf042017-08-08 18:51:37 -0400451 if (in_group && !SSL_CTX_cipher_in_group(ctx, i)) {
David Benjamine11726a2017-04-23 12:14:28 -0400452 ret += "\t]\n";
David Benjamin1d77e562015-03-22 17:22:08 -0400453 in_group = false;
David Benjaminbb0a17c2014-09-20 15:35:39 -0400454 }
455 }
David Benjamine11726a2017-04-23 12:14:28 -0400456 return ret;
David Benjaminbb0a17c2014-09-20 15:35:39 -0400457}
458
David Benjamin70dbf042017-08-08 18:51:37 -0400459static bool CipherListsEqual(SSL_CTX *ctx,
David Benjamine11726a2017-04-23 12:14:28 -0400460 const std::vector<ExpectedCipher> &expected) {
David Benjamin70dbf042017-08-08 18:51:37 -0400461 const STACK_OF(SSL_CIPHER) *ciphers = SSL_CTX_get_ciphers(ctx);
462 if (sk_SSL_CIPHER_num(ciphers) != expected.size()) {
David Benjamin1d77e562015-03-22 17:22:08 -0400463 return false;
David Benjamin65226252015-02-05 16:49:47 -0500464 }
465
David Benjamine11726a2017-04-23 12:14:28 -0400466 for (size_t i = 0; i < expected.size(); i++) {
David Benjamin70dbf042017-08-08 18:51:37 -0400467 const SSL_CIPHER *cipher = sk_SSL_CIPHER_value(ciphers, i);
David Benjamine11726a2017-04-23 12:14:28 -0400468 if (expected[i].id != SSL_CIPHER_get_id(cipher) ||
David Benjamin70dbf042017-08-08 18:51:37 -0400469 expected[i].in_group_flag != !!SSL_CTX_cipher_in_group(ctx, i)) {
David Benjamin1d77e562015-03-22 17:22:08 -0400470 return false;
David Benjaminbb0a17c2014-09-20 15:35:39 -0400471 }
472 }
473
David Benjamin1d77e562015-03-22 17:22:08 -0400474 return true;
David Benjaminbb0a17c2014-09-20 15:35:39 -0400475}
476
Daniel McArdleff746c12019-09-16 12:35:05 -0400477TEST(GrowableArrayTest, Resize) {
478 GrowableArray<size_t> array;
479 ASSERT_TRUE(array.empty());
480 EXPECT_EQ(array.size(), 0u);
481
482 ASSERT_TRUE(array.Push(42));
483 ASSERT_TRUE(!array.empty());
484 EXPECT_EQ(array.size(), 1u);
485
486 // Force a resize operation to occur
487 for (size_t i = 0; i < 16; i++) {
488 ASSERT_TRUE(array.Push(i + 1));
489 }
490
491 EXPECT_EQ(array.size(), 17u);
492
493 // Verify that expected values are still contained in array
494 for (size_t i = 0; i < array.size(); i++) {
495 EXPECT_EQ(array[i], i == 0 ? 42 : i);
496 }
497}
498
499TEST(GrowableArrayTest, MoveConstructor) {
500 GrowableArray<size_t> array;
501 for (size_t i = 0; i < 100; i++) {
502 ASSERT_TRUE(array.Push(i));
503 }
504
505 GrowableArray<size_t> array_moved(std::move(array));
506 for (size_t i = 0; i < 100; i++) {
507 EXPECT_EQ(array_moved[i], i);
508 }
509}
510
511TEST(GrowableArrayTest, GrowableArrayContainingGrowableArrays) {
512 // Representative example of a struct that contains a GrowableArray.
513 struct TagAndArray {
514 size_t tag;
515 GrowableArray<size_t> array;
516 };
517
518 GrowableArray<TagAndArray> array;
519 for (size_t i = 0; i < 100; i++) {
520 TagAndArray elem;
521 elem.tag = i;
522 for (size_t j = 0; j < i; j++) {
523 ASSERT_TRUE(elem.array.Push(j));
524 }
525 ASSERT_TRUE(array.Push(std::move(elem)));
526 }
527 EXPECT_EQ(array.size(), static_cast<size_t>(100));
528
529 GrowableArray<TagAndArray> array_moved(std::move(array));
530 EXPECT_EQ(array_moved.size(), static_cast<size_t>(100));
531 size_t count = 0;
532 for (const TagAndArray &elem : array_moved) {
533 // Test the square bracket operator returns the same value as iteration.
534 EXPECT_EQ(&elem, &array_moved[count]);
535
536 EXPECT_EQ(elem.tag, count);
537 EXPECT_EQ(elem.array.size(), count);
538 for (size_t j = 0; j < count; j++) {
539 EXPECT_EQ(elem.array[j], j);
540 }
541 count++;
542 }
543}
544
David Benjamine11726a2017-04-23 12:14:28 -0400545TEST(SSLTest, CipherRules) {
546 for (const CipherTest &t : kCipherTests) {
547 SCOPED_TRACE(t.rule);
548 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
549 ASSERT_TRUE(ctx);
Matt Braithwaiteaf096752015-09-02 19:48:16 -0700550
David Benjamine11726a2017-04-23 12:14:28 -0400551 // Test lax mode.
552 ASSERT_TRUE(SSL_CTX_set_cipher_list(ctx.get(), t.rule));
David Benjamin70dbf042017-08-08 18:51:37 -0400553 EXPECT_TRUE(CipherListsEqual(ctx.get(), t.expected))
David Benjamine11726a2017-04-23 12:14:28 -0400554 << "Cipher rule evaluated to:\n"
David Benjamin70dbf042017-08-08 18:51:37 -0400555 << CipherListToString(ctx.get());
David Benjamine11726a2017-04-23 12:14:28 -0400556
557 // Test strict mode.
558 if (t.strict_fail) {
559 EXPECT_FALSE(SSL_CTX_set_strict_cipher_list(ctx.get(), t.rule));
560 } else {
561 ASSERT_TRUE(SSL_CTX_set_strict_cipher_list(ctx.get(), t.rule));
David Benjamin70dbf042017-08-08 18:51:37 -0400562 EXPECT_TRUE(CipherListsEqual(ctx.get(), t.expected))
David Benjamine11726a2017-04-23 12:14:28 -0400563 << "Cipher rule evaluated to:\n"
David Benjamin70dbf042017-08-08 18:51:37 -0400564 << CipherListToString(ctx.get());
David Benjaminbb0a17c2014-09-20 15:35:39 -0400565 }
566 }
567
David Benjaminfb974e62015-12-16 19:34:22 -0500568 for (const char *rule : kBadRules) {
David Benjamine11726a2017-04-23 12:14:28 -0400569 SCOPED_TRACE(rule);
570 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
571 ASSERT_TRUE(ctx);
572
573 EXPECT_FALSE(SSL_CTX_set_cipher_list(ctx.get(), rule));
David Benjaminbb0a17c2014-09-20 15:35:39 -0400574 ERR_clear_error();
David Benjaminbb0a17c2014-09-20 15:35:39 -0400575 }
576
David Benjaminfb974e62015-12-16 19:34:22 -0500577 for (const char *rule : kMustNotIncludeNull) {
David Benjamine11726a2017-04-23 12:14:28 -0400578 SCOPED_TRACE(rule);
579 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
580 ASSERT_TRUE(ctx);
581
582 ASSERT_TRUE(SSL_CTX_set_strict_cipher_list(ctx.get(), rule));
David Benjamin70dbf042017-08-08 18:51:37 -0400583 for (const SSL_CIPHER *cipher : SSL_CTX_get_ciphers(ctx.get())) {
David Benjamine3bb51c2017-08-22 23:16:02 -0700584 EXPECT_NE(NID_undef, SSL_CIPHER_get_cipher_nid(cipher));
Matt Braithwaiteaf096752015-09-02 19:48:16 -0700585 }
586 }
David Benjaminbb0a17c2014-09-20 15:35:39 -0400587}
David Benjamin2e521212014-07-16 14:37:51 -0400588
David Benjamine11726a2017-04-23 12:14:28 -0400589TEST(SSLTest, CurveRules) {
590 for (const CurveTest &t : kCurveTests) {
591 SCOPED_TRACE(t.rule);
592 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
593 ASSERT_TRUE(ctx);
Alessandro Ghedini5fd18072016-09-28 21:04:25 +0100594
David Benjamine11726a2017-04-23 12:14:28 -0400595 ASSERT_TRUE(SSL_CTX_set1_curves_list(ctx.get(), t.rule));
David Benjamin0ce090a2018-07-02 20:24:40 -0400596 ASSERT_EQ(t.expected.size(), ctx->supported_group_list.size());
David Benjamine11726a2017-04-23 12:14:28 -0400597 for (size_t i = 0; i < t.expected.size(); i++) {
598 EXPECT_EQ(t.expected[i], ctx->supported_group_list[i]);
Alessandro Ghedini5fd18072016-09-28 21:04:25 +0100599 }
600 }
601
602 for (const char *rule : kBadCurvesLists) {
David Benjamine11726a2017-04-23 12:14:28 -0400603 SCOPED_TRACE(rule);
604 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
605 ASSERT_TRUE(ctx);
606
607 EXPECT_FALSE(SSL_CTX_set1_curves_list(ctx.get(), rule));
Alessandro Ghedini5fd18072016-09-28 21:04:25 +0100608 ERR_clear_error();
609 }
Alessandro Ghedini5fd18072016-09-28 21:04:25 +0100610}
611
Adam Langley364f7a62016-12-12 10:51:00 -0800612// kOpenSSLSession is a serialized SSL_SESSION.
Adam Langley10f97f32016-07-12 08:09:33 -0700613static const char kOpenSSLSession[] =
Adam Langley364f7a62016-12-12 10:51:00 -0800614 "MIIFqgIBAQICAwMEAsAvBCAG5Q1ndq4Yfmbeo1zwLkNRKmCXGdNgWvGT3cskV0yQ"
Adam Langley10f97f32016-07-12 08:09:33 -0700615 "kAQwJlrlzkAWBOWiLj/jJ76D7l+UXoizP2KI2C7I2FccqMmIfFmmkUy32nIJ0mZH"
616 "IWoJoQYCBFRDO46iBAICASyjggR6MIIEdjCCA16gAwIBAgIIK9dUvsPWSlUwDQYJ"
617 "KoZIhvcNAQEFBQAwSTELMAkGA1UEBhMCVVMxEzARBgNVBAoTCkdvb2dsZSBJbmMx"
618 "JTAjBgNVBAMTHEdvb2dsZSBJbnRlcm5ldCBBdXRob3JpdHkgRzIwHhcNMTQxMDA4"
619 "MTIwNzU3WhcNMTUwMTA2MDAwMDAwWjBoMQswCQYDVQQGEwJVUzETMBEGA1UECAwK"
620 "Q2FsaWZvcm5pYTEWMBQGA1UEBwwNTW91bnRhaW4gVmlldzETMBEGA1UECgwKR29v"
621 "Z2xlIEluYzEXMBUGA1UEAwwOd3d3Lmdvb2dsZS5jb20wggEiMA0GCSqGSIb3DQEB"
622 "AQUAA4IBDwAwggEKAoIBAQCcKeLrplAC+Lofy8t/wDwtB6eu72CVp0cJ4V3lknN6"
623 "huH9ct6FFk70oRIh/VBNBBz900jYy+7111Jm1b8iqOTQ9aT5C7SEhNcQFJvqzH3e"
624 "MPkb6ZSWGm1yGF7MCQTGQXF20Sk/O16FSjAynU/b3oJmOctcycWYkY0ytS/k3LBu"
625 "Id45PJaoMqjB0WypqvNeJHC3q5JjCB4RP7Nfx5jjHSrCMhw8lUMW4EaDxjaR9KDh"
626 "PLgjsk+LDIySRSRDaCQGhEOWLJZVLzLo4N6/UlctCHEllpBUSvEOyFga52qroGjg"
627 "rf3WOQ925MFwzd6AK+Ich0gDRg8sQfdLH5OuP1cfLfU1AgMBAAGjggFBMIIBPTAd"
628 "BgNVHSUEFjAUBggrBgEFBQcDAQYIKwYBBQUHAwIwGQYDVR0RBBIwEIIOd3d3Lmdv"
629 "b2dsZS5jb20waAYIKwYBBQUHAQEEXDBaMCsGCCsGAQUFBzAChh9odHRwOi8vcGtp"
630 "Lmdvb2dsZS5jb20vR0lBRzIuY3J0MCsGCCsGAQUFBzABhh9odHRwOi8vY2xpZW50"
631 "czEuZ29vZ2xlLmNvbS9vY3NwMB0GA1UdDgQWBBQ7a+CcxsZByOpc+xpYFcIbnUMZ"
632 "hTAMBgNVHRMBAf8EAjAAMB8GA1UdIwQYMBaAFErdBhYbvPZotXb1gba7Yhq6WoEv"
633 "MBcGA1UdIAQQMA4wDAYKKwYBBAHWeQIFATAwBgNVHR8EKTAnMCWgI6Ahhh9odHRw"
634 "Oi8vcGtpLmdvb2dsZS5jb20vR0lBRzIuY3JsMA0GCSqGSIb3DQEBBQUAA4IBAQCa"
635 "OXCBdoqUy5bxyq+Wrh1zsyyCFim1PH5VU2+yvDSWrgDY8ibRGJmfff3r4Lud5kal"
636 "dKs9k8YlKD3ITG7P0YT/Rk8hLgfEuLcq5cc0xqmE42xJ+Eo2uzq9rYorc5emMCxf"
637 "5L0TJOXZqHQpOEcuptZQ4OjdYMfSxk5UzueUhA3ogZKRcRkdB3WeWRp+nYRhx4St"
638 "o2rt2A0MKmY9165GHUqMK9YaaXHDXqBu7Sefr1uSoAP9gyIJKeihMivsGqJ1TD6Z"
639 "cc6LMe+dN2P8cZEQHtD1y296ul4Mivqk3jatUVL8/hCwgch9A8O4PGZq9WqBfEWm"
640 "IyHh1dPtbg1lOXdYCWtjpAIEAKUDAgEUqQUCAwGJwKqBpwSBpBwUQvoeOk0Kg36S"
641 "YTcLEkXqKwOBfF9vE4KX0NxeLwjcDTpsuh3qXEaZ992r1N38VDcyS6P7I6HBYN9B"
642 "sNHM362zZnY27GpTw+Kwd751CLoXFPoaMOe57dbBpXoro6Pd3BTbf/Tzr88K06yE"
643 "OTDKPNj3+inbMaVigtK4PLyPq+Topyzvx9USFgRvyuoxn0Hgb+R0A3j6SLRuyOdA"
Adam Langley364f7a62016-12-12 10:51:00 -0800644 "i4gv7Y5oliyntgMBAQA=";
Adam Langley10f97f32016-07-12 08:09:33 -0700645
646// kCustomSession is a custom serialized SSL_SESSION generated by
647// filling in missing fields from |kOpenSSLSession|. This includes
648// providing |peer_sha256|, so |peer| is not serialized.
649static const char kCustomSession[] =
David Benjamina8614602017-09-06 15:40:19 -0400650 "MIIBZAIBAQICAwMEAsAvBCAG5Q1ndq4Yfmbeo1zwLkNRKmCXGdNgWvGT3cskV0yQ"
Adam Langley10f97f32016-07-12 08:09:33 -0700651 "kAQwJlrlzkAWBOWiLj/jJ76D7l+UXoizP2KI2C7I2FccqMmIfFmmkUy32nIJ0mZH"
David Benjamina8614602017-09-06 15:40:19 -0400652 "IWoJoQYCBFRDO46iBAICASykAwQBAqUDAgEUqAcEBXdvcmxkqQUCAwGJwKqBpwSB"
653 "pBwUQvoeOk0Kg36SYTcLEkXqKwOBfF9vE4KX0NxeLwjcDTpsuh3qXEaZ992r1N38"
654 "VDcyS6P7I6HBYN9BsNHM362zZnY27GpTw+Kwd751CLoXFPoaMOe57dbBpXoro6Pd"
655 "3BTbf/Tzr88K06yEOTDKPNj3+inbMaVigtK4PLyPq+Topyzvx9USFgRvyuoxn0Hg"
656 "b+R0A3j6SLRuyOdAi4gv7Y5oliynrSIEIAYGBgYGBgYGBgYGBgYGBgYGBgYGBgYG"
657 "BgYGBgYGBgYGrgMEAQevAwQBBLADBAEF";
Adam Langley10f97f32016-07-12 08:09:33 -0700658
659// kBoringSSLSession is a serialized SSL_SESSION generated from bssl client.
660static const char kBoringSSLSession[] =
661 "MIIRwQIBAQICAwMEAsAvBCDdoGxGK26mR+8lM0uq6+k9xYuxPnwAjpcF9n0Yli9R"
662 "kQQwbyshfWhdi5XQ1++7n2L1qqrcVlmHBPpr6yknT/u4pUrpQB5FZ7vqvNn8MdHf"
663 "9rWgoQYCBFXgs7uiBAICHCCjggR6MIIEdjCCA16gAwIBAgIIf+yfD7Y6UicwDQYJ"
664 "KoZIhvcNAQELBQAwSTELMAkGA1UEBhMCVVMxEzARBgNVBAoTCkdvb2dsZSBJbmMx"
665 "JTAjBgNVBAMTHEdvb2dsZSBJbnRlcm5ldCBBdXRob3JpdHkgRzIwHhcNMTUwODEy"
666 "MTQ1MzE1WhcNMTUxMTEwMDAwMDAwWjBoMQswCQYDVQQGEwJVUzETMBEGA1UECAwK"
667 "Q2FsaWZvcm5pYTEWMBQGA1UEBwwNTW91bnRhaW4gVmlldzETMBEGA1UECgwKR29v"
668 "Z2xlIEluYzEXMBUGA1UEAwwOd3d3Lmdvb2dsZS5jb20wggEiMA0GCSqGSIb3DQEB"
669 "AQUAA4IBDwAwggEKAoIBAQC0MeG5YGQ0t+IeJeoneP/PrhEaieibeKYkbKVLNZpo"
670 "PLuBinvhkXZo3DC133NpCBpy6ZktBwamqyixAyuk/NU6OjgXqwwxfQ7di1AInLIU"
671 "792c7hFyNXSUCG7At8Ifi3YwBX9Ba6u/1d6rWTGZJrdCq3QU11RkKYyTq2KT5mce"
672 "Tv9iGKqSkSTlp8puy/9SZ/3DbU3U+BuqCFqeSlz7zjwFmk35acdCilpJlVDDN5C/"
673 "RCh8/UKc8PaL+cxlt531qoTENvYrflBno14YEZlCBZsPiFeUSILpKEj3Ccwhy0eL"
674 "EucWQ72YZU8mUzXBoXGn0zA0crFl5ci/2sTBBGZsylNBAgMBAAGjggFBMIIBPTAd"
675 "BgNVHSUEFjAUBggrBgEFBQcDAQYIKwYBBQUHAwIwGQYDVR0RBBIwEIIOd3d3Lmdv"
676 "b2dsZS5jb20waAYIKwYBBQUHAQEEXDBaMCsGCCsGAQUFBzAChh9odHRwOi8vcGtp"
677 "Lmdvb2dsZS5jb20vR0lBRzIuY3J0MCsGCCsGAQUFBzABhh9odHRwOi8vY2xpZW50"
678 "czEuZ29vZ2xlLmNvbS9vY3NwMB0GA1UdDgQWBBS/bzHxcE73Q4j3slC4BLbMtLjG"
679 "GjAMBgNVHRMBAf8EAjAAMB8GA1UdIwQYMBaAFErdBhYbvPZotXb1gba7Yhq6WoEv"
680 "MBcGA1UdIAQQMA4wDAYKKwYBBAHWeQIFATAwBgNVHR8EKTAnMCWgI6Ahhh9odHRw"
681 "Oi8vcGtpLmdvb2dsZS5jb20vR0lBRzIuY3JsMA0GCSqGSIb3DQEBCwUAA4IBAQAb"
682 "qdWPZEHk0X7iKPCTHL6S3w6q1eR67goxZGFSM1lk1hjwyu7XcLJuvALVV9uY3ovE"
683 "kQZSHwT+pyOPWQhsSjO+1GyjvCvK/CAwiUmBX+bQRGaqHsRcio7xSbdVcajQ3bXd"
684 "X+s0WdbOpn6MStKAiBVloPlSxEI8pxY6x/BBCnTIk/+DMB17uZlOjG3vbAnkDkP+"
685 "n0OTucD9sHV7EVj9XUxi51nOfNBCN/s7lpUjDS/NJ4k3iwOtbCPswiot8vLO779a"
686 "f07vR03r349Iz/KTzk95rlFtX0IU+KYNxFNsanIXZ+C9FYGRXkwhHcvFb4qMUB1y"
687 "TTlM80jBMOwyjZXmjRAhpAIEAKUDAgEUqQUCAwGJwKqBpwSBpOgebbmn9NRUtMWH"
688 "+eJpqA5JLMFSMCChOsvKey3toBaCNGU7HfAEiiXNuuAdCBoK262BjQc2YYfqFzqH"
689 "zuppopXCvhohx7j/tnCNZIMgLYt/O9SXK2RYI5z8FhCCHvB4CbD5G0LGl5EFP27s"
690 "Jb6S3aTTYPkQe8yZSlxevg6NDwmTogLO9F7UUkaYmVcMQhzssEE2ZRYNwSOU6KjE"
691 "0Yj+8fAiBtbQriIEIN2L8ZlpaVrdN5KFNdvcmOxJu81P8q53X55xQyGTnGWwsgMC"
692 "ARezggvvMIIEdjCCA16gAwIBAgIIf+yfD7Y6UicwDQYJKoZIhvcNAQELBQAwSTEL"
693 "MAkGA1UEBhMCVVMxEzARBgNVBAoTCkdvb2dsZSBJbmMxJTAjBgNVBAMTHEdvb2ds"
694 "ZSBJbnRlcm5ldCBBdXRob3JpdHkgRzIwHhcNMTUwODEyMTQ1MzE1WhcNMTUxMTEw"
695 "MDAwMDAwWjBoMQswCQYDVQQGEwJVUzETMBEGA1UECAwKQ2FsaWZvcm5pYTEWMBQG"
696 "A1UEBwwNTW91bnRhaW4gVmlldzETMBEGA1UECgwKR29vZ2xlIEluYzEXMBUGA1UE"
697 "AwwOd3d3Lmdvb2dsZS5jb20wggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIB"
698 "AQC0MeG5YGQ0t+IeJeoneP/PrhEaieibeKYkbKVLNZpoPLuBinvhkXZo3DC133Np"
699 "CBpy6ZktBwamqyixAyuk/NU6OjgXqwwxfQ7di1AInLIU792c7hFyNXSUCG7At8If"
700 "i3YwBX9Ba6u/1d6rWTGZJrdCq3QU11RkKYyTq2KT5mceTv9iGKqSkSTlp8puy/9S"
701 "Z/3DbU3U+BuqCFqeSlz7zjwFmk35acdCilpJlVDDN5C/RCh8/UKc8PaL+cxlt531"
702 "qoTENvYrflBno14YEZlCBZsPiFeUSILpKEj3Ccwhy0eLEucWQ72YZU8mUzXBoXGn"
703 "0zA0crFl5ci/2sTBBGZsylNBAgMBAAGjggFBMIIBPTAdBgNVHSUEFjAUBggrBgEF"
704 "BQcDAQYIKwYBBQUHAwIwGQYDVR0RBBIwEIIOd3d3Lmdvb2dsZS5jb20waAYIKwYB"
705 "BQUHAQEEXDBaMCsGCCsGAQUFBzAChh9odHRwOi8vcGtpLmdvb2dsZS5jb20vR0lB"
706 "RzIuY3J0MCsGCCsGAQUFBzABhh9odHRwOi8vY2xpZW50czEuZ29vZ2xlLmNvbS9v"
707 "Y3NwMB0GA1UdDgQWBBS/bzHxcE73Q4j3slC4BLbMtLjGGjAMBgNVHRMBAf8EAjAA"
708 "MB8GA1UdIwQYMBaAFErdBhYbvPZotXb1gba7Yhq6WoEvMBcGA1UdIAQQMA4wDAYK"
709 "KwYBBAHWeQIFATAwBgNVHR8EKTAnMCWgI6Ahhh9odHRwOi8vcGtpLmdvb2dsZS5j"
710 "b20vR0lBRzIuY3JsMA0GCSqGSIb3DQEBCwUAA4IBAQAbqdWPZEHk0X7iKPCTHL6S"
711 "3w6q1eR67goxZGFSM1lk1hjwyu7XcLJuvALVV9uY3ovEkQZSHwT+pyOPWQhsSjO+"
712 "1GyjvCvK/CAwiUmBX+bQRGaqHsRcio7xSbdVcajQ3bXdX+s0WdbOpn6MStKAiBVl"
713 "oPlSxEI8pxY6x/BBCnTIk/+DMB17uZlOjG3vbAnkDkP+n0OTucD9sHV7EVj9XUxi"
714 "51nOfNBCN/s7lpUjDS/NJ4k3iwOtbCPswiot8vLO779af07vR03r349Iz/KTzk95"
715 "rlFtX0IU+KYNxFNsanIXZ+C9FYGRXkwhHcvFb4qMUB1yTTlM80jBMOwyjZXmjRAh"
716 "MIID8DCCAtigAwIBAgIDAjqDMA0GCSqGSIb3DQEBCwUAMEIxCzAJBgNVBAYTAlVT"
717 "MRYwFAYDVQQKEw1HZW9UcnVzdCBJbmMuMRswGQYDVQQDExJHZW9UcnVzdCBHbG9i"
718 "YWwgQ0EwHhcNMTMwNDA1MTUxNTU2WhcNMTYxMjMxMjM1OTU5WjBJMQswCQYDVQQG"
719 "EwJVUzETMBEGA1UEChMKR29vZ2xlIEluYzElMCMGA1UEAxMcR29vZ2xlIEludGVy"
720 "bmV0IEF1dGhvcml0eSBHMjCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEB"
721 "AJwqBHdc2FCROgajguDYUEi8iT/xGXAaiEZ+4I/F8YnOIe5a/mENtzJEiaB0C1NP"
722 "VaTOgmKV7utZX8bhBYASxF6UP7xbSDj0U/ck5vuR6RXEz/RTDfRK/J9U3n2+oGtv"
723 "h8DQUB8oMANA2ghzUWx//zo8pzcGjr1LEQTrfSTe5vn8MXH7lNVg8y5Kr0LSy+rE"
724 "ahqyzFPdFUuLH8gZYR/Nnag+YyuENWllhMgZxUYi+FOVvuOAShDGKuy6lyARxzmZ"
725 "EASg8GF6lSWMTlJ14rbtCMoU/M4iarNOz0YDl5cDfsCx3nuvRTPPuj5xt970JSXC"
726 "DTWJnZ37DhF5iR43xa+OcmkCAwEAAaOB5zCB5DAfBgNVHSMEGDAWgBTAephojYn7"
727 "qwVkDBF9qn1luMrMTjAdBgNVHQ4EFgQUSt0GFhu89mi1dvWBtrtiGrpagS8wDgYD"
728 "VR0PAQH/BAQDAgEGMC4GCCsGAQUFBwEBBCIwIDAeBggrBgEFBQcwAYYSaHR0cDov"
729 "L2cuc3ltY2QuY29tMBIGA1UdEwEB/wQIMAYBAf8CAQAwNQYDVR0fBC4wLDAqoCig"
730 "JoYkaHR0cDovL2cuc3ltY2IuY29tL2NybHMvZ3RnbG9iYWwuY3JsMBcGA1UdIAQQ"
731 "MA4wDAYKKwYBBAHWeQIFATANBgkqhkiG9w0BAQsFAAOCAQEAqvqpIM1qZ4PtXtR+"
732 "3h3Ef+AlBgDFJPupyC1tft6dgmUsgWM0Zj7pUsIItMsv91+ZOmqcUHqFBYx90SpI"
733 "hNMJbHzCzTWf84LuUt5oX+QAihcglvcpjZpNy6jehsgNb1aHA30DP9z6eX0hGfnI"
734 "Oi9RdozHQZJxjyXON/hKTAAj78Q1EK7gI4BzfE00LshukNYQHpmEcxpw8u1VDu4X"
735 "Bupn7jLrLN1nBz/2i8Jw3lsA5rsb0zYaImxssDVCbJAJPZPpZAkiDoUGn8JzIdPm"
736 "X4DkjYUiOnMDsWCOrmji9D6X52ASCWg23jrW4kOVWzeBkoEfu43XrVJkFleW2V40"
737 "fsg12DCCA30wggLmoAMCAQICAxK75jANBgkqhkiG9w0BAQUFADBOMQswCQYDVQQG"
738 "EwJVUzEQMA4GA1UEChMHRXF1aWZheDEtMCsGA1UECxMkRXF1aWZheCBTZWN1cmUg"
739 "Q2VydGlmaWNhdGUgQXV0aG9yaXR5MB4XDTAyMDUyMTA0MDAwMFoXDTE4MDgyMTA0"
740 "MDAwMFowQjELMAkGA1UEBhMCVVMxFjAUBgNVBAoTDUdlb1RydXN0IEluYy4xGzAZ"
741 "BgNVBAMTEkdlb1RydXN0IEdsb2JhbCBDQTCCASIwDQYJKoZIhvcNAQEBBQADggEP"
742 "ADCCAQoCggEBANrMGGMw/fQXIxpWflvfPGw45HG3eJHUvKHYTPioQ7YD6U0hBwiI"
743 "2lgvZjkpvQV4i5046AW3an5xpObEYKaw74DkiSgPniXW7YPzraaRx5jJQhg1FJ2t"
744 "mEaSLk/K8YdDwRaVVy1Q74ktgHpXrfLuX2vSAI25FPgUFTXZwEaje3LIkb/JVSvN"
745 "0Jc+nCZkzN/Ogxlxyk7m1NV7qRnNVd7I7NJeOFPlXE+MLf5QIzb8ZubLjqQ5GQC3"
746 "lQI5kQsO/jgu0R0FmvZNPm8PBx2vLB6PYDni+jZTEznUXiYr2z2oFL0y6xgDKFIE"
747 "ceWrMz3hOLsHNoRinHnqFjD0X8Ar6HFr5PkCAwEAAaOB8DCB7TAfBgNVHSMEGDAW"
748 "gBRI5mj5K9KylddH2CMgEE8zmJCf1DAdBgNVHQ4EFgQUwHqYaI2J+6sFZAwRfap9"
749 "ZbjKzE4wDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMCAQYwOgYDVR0fBDMw"
750 "MTAvoC2gK4YpaHR0cDovL2NybC5nZW90cnVzdC5jb20vY3Jscy9zZWN1cmVjYS5j"
751 "cmwwTgYDVR0gBEcwRTBDBgRVHSAAMDswOQYIKwYBBQUHAgEWLWh0dHBzOi8vd3d3"
752 "Lmdlb3RydXN0LmNvbS9yZXNvdXJjZXMvcmVwb3NpdG9yeTANBgkqhkiG9w0BAQUF"
753 "AAOBgQB24RJuTksWEoYwBrKBCM/wCMfHcX5m7sLt1Dsf//DwyE7WQziwuTB9GNBV"
754 "g6JqyzYRnOhIZqNtf7gT1Ef+i1pcc/yu2RsyGTirlzQUqpbS66McFAhJtrvlke+D"
755 "NusdVm/K2rxzY5Dkf3s+Iss9B+1fOHSc4wNQTqGvmO5h8oQ/Eg==";
756
757// kBadSessionExtraField is a custom serialized SSL_SESSION generated by replacing
Steven Valdez51607f12020-08-05 10:46:05 -0400758// the final (optional) element of |kCustomSession| with tag number 99.
Adam Langley10f97f32016-07-12 08:09:33 -0700759static const char kBadSessionExtraField[] =
760 "MIIBdgIBAQICAwMEAsAvBCAG5Q1ndq4Yfmbeo1zwLkNRKmCXGdNgWvGT3cskV0yQ"
761 "kAQwJlrlzkAWBOWiLj/jJ76D7l+UXoizP2KI2C7I2FccqMmIfFmmkUy32nIJ0mZH"
762 "IWoJoQYCBFRDO46iBAICASykAwQBAqUDAgEUphAEDnd3dy5nb29nbGUuY29tqAcE"
763 "BXdvcmxkqQUCAwGJwKqBpwSBpBwUQvoeOk0Kg36SYTcLEkXqKwOBfF9vE4KX0Nxe"
764 "LwjcDTpsuh3qXEaZ992r1N38VDcyS6P7I6HBYN9BsNHM362zZnY27GpTw+Kwd751"
765 "CLoXFPoaMOe57dbBpXoro6Pd3BTbf/Tzr88K06yEOTDKPNj3+inbMaVigtK4PLyP"
766 "q+Topyzvx9USFgRvyuoxn0Hgb+R0A3j6SLRuyOdAi4gv7Y5oliynrSIEIAYGBgYG"
Steven Valdez51607f12020-08-05 10:46:05 -0400767 "BgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGrgMEAQevAwQBBOMDBAEF";
Adam Langley10f97f32016-07-12 08:09:33 -0700768
769// kBadSessionVersion is a custom serialized SSL_SESSION generated by replacing
770// the version of |kCustomSession| with 2.
771static const char kBadSessionVersion[] =
772 "MIIBdgIBAgICAwMEAsAvBCAG5Q1ndq4Yfmbeo1zwLkNRKmCXGdNgWvGT3cskV0yQ"
773 "kAQwJlrlzkAWBOWiLj/jJ76D7l+UXoizP2KI2C7I2FccqMmIfFmmkUy32nIJ0mZH"
774 "IWoJoQYCBFRDO46iBAICASykAwQBAqUDAgEUphAEDnd3dy5nb29nbGUuY29tqAcE"
775 "BXdvcmxkqQUCAwGJwKqBpwSBpBwUQvoeOk0Kg36SYTcLEkXqKwOBfF9vE4KX0Nxe"
776 "LwjcDTpsuh3qXEaZ992r1N38VDcyS6P7I6HBYN9BsNHM362zZnY27GpTw+Kwd751"
777 "CLoXFPoaMOe57dbBpXoro6Pd3BTbf/Tzr88K06yEOTDKPNj3+inbMaVigtK4PLyP"
778 "q+Topyzvx9USFgRvyuoxn0Hgb+R0A3j6SLRuyOdAi4gv7Y5oliynrSIEIAYGBgYG"
779 "BgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGrgMEAQevAwQBBLADBAEF";
780
781// kBadSessionTrailingData is a custom serialized SSL_SESSION with trailing data
782// appended.
783static const char kBadSessionTrailingData[] =
784 "MIIBdgIBAQICAwMEAsAvBCAG5Q1ndq4Yfmbeo1zwLkNRKmCXGdNgWvGT3cskV0yQ"
785 "kAQwJlrlzkAWBOWiLj/jJ76D7l+UXoizP2KI2C7I2FccqMmIfFmmkUy32nIJ0mZH"
786 "IWoJoQYCBFRDO46iBAICASykAwQBAqUDAgEUphAEDnd3dy5nb29nbGUuY29tqAcE"
787 "BXdvcmxkqQUCAwGJwKqBpwSBpBwUQvoeOk0Kg36SYTcLEkXqKwOBfF9vE4KX0Nxe"
788 "LwjcDTpsuh3qXEaZ992r1N38VDcyS6P7I6HBYN9BsNHM362zZnY27GpTw+Kwd751"
789 "CLoXFPoaMOe57dbBpXoro6Pd3BTbf/Tzr88K06yEOTDKPNj3+inbMaVigtK4PLyP"
790 "q+Topyzvx9USFgRvyuoxn0Hgb+R0A3j6SLRuyOdAi4gv7Y5oliynrSIEIAYGBgYG"
791 "BgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGBgYGrgMEAQevAwQBBLADBAEFAAAA";
792
David Benjamin1d77e562015-03-22 17:22:08 -0400793static bool DecodeBase64(std::vector<uint8_t> *out, const char *in) {
David Benjamin751e8892014-10-19 00:59:36 -0400794 size_t len;
David Benjamin751e8892014-10-19 00:59:36 -0400795 if (!EVP_DecodedLength(&len, strlen(in))) {
796 fprintf(stderr, "EVP_DecodedLength failed\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400797 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400798 }
799
David Benjamin1d77e562015-03-22 17:22:08 -0400800 out->resize(len);
David Benjaminef14b2d2015-11-11 14:01:27 -0800801 if (!EVP_DecodeBase64(out->data(), &len, len, (const uint8_t *)in,
David Benjamin751e8892014-10-19 00:59:36 -0400802 strlen(in))) {
803 fprintf(stderr, "EVP_DecodeBase64 failed\n");
David Benjamin1d77e562015-03-22 17:22:08 -0400804 return false;
David Benjamin751e8892014-10-19 00:59:36 -0400805 }
David Benjamin1d77e562015-03-22 17:22:08 -0400806 out->resize(len);
807 return true;
David Benjamin751e8892014-10-19 00:59:36 -0400808}
809
David Benjamina486c6c2019-03-28 18:32:38 -0500810TEST(SSLTest, SessionEncoding) {
811 for (const char *input_b64 : {
812 kOpenSSLSession,
813 kCustomSession,
814 kBoringSSLSession,
815 }) {
816 SCOPED_TRACE(std::string(input_b64));
817 // Decode the input.
818 std::vector<uint8_t> input;
819 ASSERT_TRUE(DecodeBase64(&input, input_b64));
David Benjamin751e8892014-10-19 00:59:36 -0400820
David Benjamina486c6c2019-03-28 18:32:38 -0500821 // Verify the SSL_SESSION decodes.
822 bssl::UniquePtr<SSL_CTX> ssl_ctx(SSL_CTX_new(TLS_method()));
823 ASSERT_TRUE(ssl_ctx);
824 bssl::UniquePtr<SSL_SESSION> session(
825 SSL_SESSION_from_bytes(input.data(), input.size(), ssl_ctx.get()));
826 ASSERT_TRUE(session) << "SSL_SESSION_from_bytes failed";
827
828 // Verify the SSL_SESSION encoding round-trips.
829 size_t encoded_len;
830 bssl::UniquePtr<uint8_t> encoded;
831 uint8_t *encoded_raw;
832 ASSERT_TRUE(SSL_SESSION_to_bytes(session.get(), &encoded_raw, &encoded_len))
833 << "SSL_SESSION_to_bytes failed";
834 encoded.reset(encoded_raw);
835 EXPECT_EQ(Bytes(encoded.get(), encoded_len), Bytes(input))
836 << "SSL_SESSION_to_bytes did not round-trip";
837
838 // Verify the SSL_SESSION also decodes with the legacy API.
839 const uint8_t *cptr = input.data();
840 session.reset(d2i_SSL_SESSION(NULL, &cptr, input.size()));
841 ASSERT_TRUE(session) << "d2i_SSL_SESSION failed";
842 EXPECT_EQ(cptr, input.data() + input.size());
843
844 // Verify the SSL_SESSION encoding round-trips via the legacy API.
845 int len = i2d_SSL_SESSION(session.get(), NULL);
846 ASSERT_GT(len, 0) << "i2d_SSL_SESSION failed";
847 ASSERT_EQ(static_cast<size_t>(len), input.size())
848 << "i2d_SSL_SESSION(NULL) returned invalid length";
849
850 encoded.reset((uint8_t *)OPENSSL_malloc(input.size()));
851 ASSERT_TRUE(encoded);
852
853 uint8_t *ptr = encoded.get();
854 len = i2d_SSL_SESSION(session.get(), &ptr);
855 ASSERT_GT(len, 0) << "i2d_SSL_SESSION failed";
856 ASSERT_EQ(static_cast<size_t>(len), input.size())
857 << "i2d_SSL_SESSION(NULL) returned invalid length";
858 ASSERT_EQ(ptr, encoded.get() + input.size())
859 << "i2d_SSL_SESSION did not advance ptr correctly";
860 EXPECT_EQ(Bytes(encoded.get(), encoded_len), Bytes(input))
861 << "SSL_SESSION_to_bytes did not round-trip";
David Benjamin751e8892014-10-19 00:59:36 -0400862 }
863
David Benjamina486c6c2019-03-28 18:32:38 -0500864 for (const char *input_b64 : {
865 kBadSessionExtraField,
866 kBadSessionVersion,
867 kBadSessionTrailingData,
868 }) {
869 SCOPED_TRACE(std::string(input_b64));
870 std::vector<uint8_t> input;
871 ASSERT_TRUE(DecodeBase64(&input, input_b64));
David Benjamin751e8892014-10-19 00:59:36 -0400872
David Benjamina486c6c2019-03-28 18:32:38 -0500873 // Verify that the SSL_SESSION fails to decode.
874 bssl::UniquePtr<SSL_CTX> ssl_ctx(SSL_CTX_new(TLS_method()));
875 ASSERT_TRUE(ssl_ctx);
876 bssl::UniquePtr<SSL_SESSION> session(
877 SSL_SESSION_from_bytes(input.data(), input.size(), ssl_ctx.get()));
878 EXPECT_FALSE(session) << "SSL_SESSION_from_bytes unexpectedly succeeded";
879 ERR_clear_error();
David Benjamin3cac4502014-10-21 01:46:30 -0400880 }
David Benjaminf297e022015-05-28 19:55:29 -0400881}
882
David Benjamin321fcdc2017-04-24 11:42:42 -0400883static void ExpectDefaultVersion(uint16_t min_version, uint16_t max_version,
884 const SSL_METHOD *(*method)(void)) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -0700885 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(method()));
David Benjamin321fcdc2017-04-24 11:42:42 -0400886 ASSERT_TRUE(ctx);
Nitish Sakhawalkara4af5f82019-03-25 17:26:59 -0700887 EXPECT_EQ(min_version, SSL_CTX_get_min_proto_version(ctx.get()));
888 EXPECT_EQ(max_version, SSL_CTX_get_max_proto_version(ctx.get()));
David Benjamin321fcdc2017-04-24 11:42:42 -0400889}
890
891TEST(SSLTest, DefaultVersion) {
Matthew Braithwaite58d56f42019-11-04 13:20:01 -0800892 ExpectDefaultVersion(TLS1_VERSION, TLS1_3_VERSION, &TLS_method);
David Benjamin321fcdc2017-04-24 11:42:42 -0400893 ExpectDefaultVersion(TLS1_VERSION, TLS1_VERSION, &TLSv1_method);
894 ExpectDefaultVersion(TLS1_1_VERSION, TLS1_1_VERSION, &TLSv1_1_method);
895 ExpectDefaultVersion(TLS1_2_VERSION, TLS1_2_VERSION, &TLSv1_2_method);
Nitish Sakhawalkara4af5f82019-03-25 17:26:59 -0700896 ExpectDefaultVersion(DTLS1_VERSION, DTLS1_2_VERSION, &DTLS_method);
897 ExpectDefaultVersion(DTLS1_VERSION, DTLS1_VERSION, &DTLSv1_method);
898 ExpectDefaultVersion(DTLS1_2_VERSION, DTLS1_2_VERSION, &DTLSv1_2_method);
David Benjamin82c9e902014-12-12 15:55:27 -0500899}
900
David Benjamin348f0d82017-08-10 16:06:27 -0400901TEST(SSLTest, CipherProperties) {
David Benjamin6fff3862017-06-21 21:07:04 -0400902 static const struct {
903 int id;
904 const char *standard_name;
David Benjamin348f0d82017-08-10 16:06:27 -0400905 int cipher_nid;
906 int digest_nid;
907 int kx_nid;
908 int auth_nid;
David Benjaminb1b76ae2017-09-21 17:03:34 -0400909 int prf_nid;
David Benjamin6fff3862017-06-21 21:07:04 -0400910 } kTests[] = {
David Benjamin348f0d82017-08-10 16:06:27 -0400911 {
912 SSL3_CK_RSA_DES_192_CBC3_SHA,
913 "TLS_RSA_WITH_3DES_EDE_CBC_SHA",
914 NID_des_ede3_cbc,
915 NID_sha1,
916 NID_kx_rsa,
917 NID_auth_rsa,
David Benjaminb1b76ae2017-09-21 17:03:34 -0400918 NID_md5_sha1,
David Benjamin348f0d82017-08-10 16:06:27 -0400919 },
920 {
921 TLS1_CK_RSA_WITH_AES_128_SHA,
922 "TLS_RSA_WITH_AES_128_CBC_SHA",
923 NID_aes_128_cbc,
924 NID_sha1,
925 NID_kx_rsa,
926 NID_auth_rsa,
David Benjaminb1b76ae2017-09-21 17:03:34 -0400927 NID_md5_sha1,
David Benjamin348f0d82017-08-10 16:06:27 -0400928 },
929 {
930 TLS1_CK_PSK_WITH_AES_256_CBC_SHA,
931 "TLS_PSK_WITH_AES_256_CBC_SHA",
932 NID_aes_256_cbc,
933 NID_sha1,
934 NID_kx_psk,
935 NID_auth_psk,
David Benjaminb1b76ae2017-09-21 17:03:34 -0400936 NID_md5_sha1,
David Benjamin348f0d82017-08-10 16:06:27 -0400937 },
938 {
David Benjamin6e678ee2018-04-16 19:54:42 -0400939 TLS1_CK_ECDHE_RSA_WITH_AES_128_CBC_SHA,
940 "TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA",
David Benjamin348f0d82017-08-10 16:06:27 -0400941 NID_aes_128_cbc,
David Benjamin6e678ee2018-04-16 19:54:42 -0400942 NID_sha1,
David Benjamin348f0d82017-08-10 16:06:27 -0400943 NID_kx_ecdhe,
944 NID_auth_rsa,
David Benjamin6e678ee2018-04-16 19:54:42 -0400945 NID_md5_sha1,
David Benjamin348f0d82017-08-10 16:06:27 -0400946 },
947 {
David Benjamin6e678ee2018-04-16 19:54:42 -0400948 TLS1_CK_ECDHE_RSA_WITH_AES_256_CBC_SHA,
949 "TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA",
David Benjamin348f0d82017-08-10 16:06:27 -0400950 NID_aes_256_cbc,
David Benjamin6e678ee2018-04-16 19:54:42 -0400951 NID_sha1,
David Benjamin348f0d82017-08-10 16:06:27 -0400952 NID_kx_ecdhe,
953 NID_auth_rsa,
David Benjamin6e678ee2018-04-16 19:54:42 -0400954 NID_md5_sha1,
David Benjamin348f0d82017-08-10 16:06:27 -0400955 },
956 {
957 TLS1_CK_ECDHE_RSA_WITH_AES_128_GCM_SHA256,
958 "TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256",
959 NID_aes_128_gcm,
960 NID_undef,
961 NID_kx_ecdhe,
962 NID_auth_rsa,
David Benjaminb1b76ae2017-09-21 17:03:34 -0400963 NID_sha256,
David Benjamin348f0d82017-08-10 16:06:27 -0400964 },
965 {
966 TLS1_CK_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256,
967 "TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256",
968 NID_aes_128_gcm,
969 NID_undef,
970 NID_kx_ecdhe,
971 NID_auth_ecdsa,
David Benjaminb1b76ae2017-09-21 17:03:34 -0400972 NID_sha256,
David Benjamin348f0d82017-08-10 16:06:27 -0400973 },
974 {
975 TLS1_CK_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384,
976 "TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384",
977 NID_aes_256_gcm,
978 NID_undef,
979 NID_kx_ecdhe,
980 NID_auth_ecdsa,
David Benjaminb1b76ae2017-09-21 17:03:34 -0400981 NID_sha384,
David Benjamin348f0d82017-08-10 16:06:27 -0400982 },
983 {
984 TLS1_CK_ECDHE_PSK_WITH_AES_128_CBC_SHA,
985 "TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA",
986 NID_aes_128_cbc,
987 NID_sha1,
988 NID_kx_ecdhe,
989 NID_auth_psk,
David Benjaminb1b76ae2017-09-21 17:03:34 -0400990 NID_md5_sha1,
David Benjamin348f0d82017-08-10 16:06:27 -0400991 },
992 {
993 TLS1_CK_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256,
994 "TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256",
995 NID_chacha20_poly1305,
996 NID_undef,
997 NID_kx_ecdhe,
998 NID_auth_rsa,
David Benjaminb1b76ae2017-09-21 17:03:34 -0400999 NID_sha256,
David Benjamin348f0d82017-08-10 16:06:27 -04001000 },
1001 {
1002 TLS1_CK_AES_256_GCM_SHA384,
1003 "TLS_AES_256_GCM_SHA384",
1004 NID_aes_256_gcm,
1005 NID_undef,
1006 NID_kx_any,
1007 NID_auth_any,
David Benjaminb1b76ae2017-09-21 17:03:34 -04001008 NID_sha384,
David Benjamin348f0d82017-08-10 16:06:27 -04001009 },
1010 {
1011 TLS1_CK_AES_128_GCM_SHA256,
1012 "TLS_AES_128_GCM_SHA256",
1013 NID_aes_128_gcm,
1014 NID_undef,
1015 NID_kx_any,
1016 NID_auth_any,
David Benjaminb1b76ae2017-09-21 17:03:34 -04001017 NID_sha256,
David Benjamin348f0d82017-08-10 16:06:27 -04001018 },
1019 {
1020 TLS1_CK_CHACHA20_POLY1305_SHA256,
1021 "TLS_CHACHA20_POLY1305_SHA256",
1022 NID_chacha20_poly1305,
1023 NID_undef,
1024 NID_kx_any,
1025 NID_auth_any,
David Benjaminb1b76ae2017-09-21 17:03:34 -04001026 NID_sha256,
David Benjamin348f0d82017-08-10 16:06:27 -04001027 },
David Benjamin6fff3862017-06-21 21:07:04 -04001028 };
David Benjamin65226252015-02-05 16:49:47 -05001029
David Benjamin6fff3862017-06-21 21:07:04 -04001030 for (const auto &t : kTests) {
1031 SCOPED_TRACE(t.standard_name);
David Benjamine11726a2017-04-23 12:14:28 -04001032
1033 const SSL_CIPHER *cipher = SSL_get_cipher_by_value(t.id & 0xffff);
1034 ASSERT_TRUE(cipher);
David Benjamin6fff3862017-06-21 21:07:04 -04001035 EXPECT_STREQ(t.standard_name, SSL_CIPHER_standard_name(cipher));
1036
David Benjamine11726a2017-04-23 12:14:28 -04001037 bssl::UniquePtr<char> rfc_name(SSL_CIPHER_get_rfc_name(cipher));
1038 ASSERT_TRUE(rfc_name);
David Benjamin6fff3862017-06-21 21:07:04 -04001039 EXPECT_STREQ(t.standard_name, rfc_name.get());
David Benjamin348f0d82017-08-10 16:06:27 -04001040
1041 EXPECT_EQ(t.cipher_nid, SSL_CIPHER_get_cipher_nid(cipher));
1042 EXPECT_EQ(t.digest_nid, SSL_CIPHER_get_digest_nid(cipher));
1043 EXPECT_EQ(t.kx_nid, SSL_CIPHER_get_kx_nid(cipher));
1044 EXPECT_EQ(t.auth_nid, SSL_CIPHER_get_auth_nid(cipher));
David Benjaminb1b76ae2017-09-21 17:03:34 -04001045 EXPECT_EQ(t.prf_nid, SSL_CIPHER_get_prf_nid(cipher));
David Benjamin65226252015-02-05 16:49:47 -05001046 }
David Benjamin65226252015-02-05 16:49:47 -05001047}
1048
Steven Valdeza833c352016-11-01 13:39:36 -04001049// CreateSessionWithTicket returns a sample |SSL_SESSION| with the specified
1050// version and ticket length or nullptr on failure.
1051static bssl::UniquePtr<SSL_SESSION> CreateSessionWithTicket(uint16_t version,
1052 size_t ticket_len) {
David Benjamin422fe082015-07-21 22:03:43 -04001053 std::vector<uint8_t> der;
1054 if (!DecodeBase64(&der, kOpenSSLSession)) {
1055 return nullptr;
1056 }
Adam Langley46db7af2017-02-01 15:49:37 -08001057
1058 bssl::UniquePtr<SSL_CTX> ssl_ctx(SSL_CTX_new(TLS_method()));
1059 if (!ssl_ctx) {
1060 return nullptr;
1061 }
David Benjaminaaef8332018-06-29 16:45:49 -04001062 // Use a garbage ticket.
1063 std::vector<uint8_t> ticket(ticket_len, 'a');
Steven Valdeza833c352016-11-01 13:39:36 -04001064 bssl::UniquePtr<SSL_SESSION> session(
Adam Langley46db7af2017-02-01 15:49:37 -08001065 SSL_SESSION_from_bytes(der.data(), der.size(), ssl_ctx.get()));
David Benjaminaaef8332018-06-29 16:45:49 -04001066 if (!session ||
1067 !SSL_SESSION_set_protocol_version(session.get(), version) ||
1068 !SSL_SESSION_set_ticket(session.get(), ticket.data(), ticket.size())) {
David Benjamin422fe082015-07-21 22:03:43 -04001069 return nullptr;
1070 }
David Benjamin1269ddd2015-10-18 15:18:55 -04001071 // Fix up the timeout.
David Benjamin9b63f292016-11-15 00:44:05 -05001072#if defined(BORINGSSL_UNSAFE_DETERMINISTIC_MODE)
David Benjaminaaef8332018-06-29 16:45:49 -04001073 SSL_SESSION_set_time(session.get(), 1234);
David Benjamin9b63f292016-11-15 00:44:05 -05001074#else
David Benjaminaaef8332018-06-29 16:45:49 -04001075 SSL_SESSION_set_time(session.get(), time(nullptr));
David Benjamin9b63f292016-11-15 00:44:05 -05001076#endif
David Benjamin422fe082015-07-21 22:03:43 -04001077 return session;
1078}
1079
David Benjaminafc64de2016-07-19 17:12:41 +02001080static bool GetClientHello(SSL *ssl, std::vector<uint8_t> *out) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001081 bssl::UniquePtr<BIO> bio(BIO_new(BIO_s_mem()));
David Benjaminafc64de2016-07-19 17:12:41 +02001082 if (!bio) {
1083 return false;
1084 }
1085 // Do not configure a reading BIO, but record what's written to a memory BIO.
David Benjamin96a16cd2016-08-11 12:14:47 -04001086 BIO_up_ref(bio.get());
1087 SSL_set_bio(ssl, nullptr /* rbio */, bio.get());
David Benjaminafc64de2016-07-19 17:12:41 +02001088 int ret = SSL_connect(ssl);
1089 if (ret > 0) {
1090 // SSL_connect should fail without a BIO to write to.
1091 return false;
1092 }
1093 ERR_clear_error();
1094
1095 const uint8_t *client_hello;
1096 size_t client_hello_len;
1097 if (!BIO_mem_contents(bio.get(), &client_hello, &client_hello_len)) {
1098 return false;
1099 }
1100 *out = std::vector<uint8_t>(client_hello, client_hello + client_hello_len);
1101 return true;
1102}
1103
Steven Valdeza833c352016-11-01 13:39:36 -04001104// GetClientHelloLen creates a client SSL connection with the specified version
1105// and ticket length. It returns the length of the ClientHello, not including
1106// the record header, on success and zero on error.
1107static size_t GetClientHelloLen(uint16_t max_version, uint16_t session_version,
1108 size_t ticket_len) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001109 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
Steven Valdeza833c352016-11-01 13:39:36 -04001110 bssl::UniquePtr<SSL_SESSION> session =
1111 CreateSessionWithTicket(session_version, ticket_len);
David Benjamin422fe082015-07-21 22:03:43 -04001112 if (!ctx || !session) {
1113 return 0;
1114 }
Steven Valdeza833c352016-11-01 13:39:36 -04001115
1116 // Set a one-element cipher list so the baseline ClientHello is unpadded.
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001117 bssl::UniquePtr<SSL> ssl(SSL_new(ctx.get()));
Steven Valdez2c62fe92016-10-14 12:08:12 -04001118 if (!ssl || !SSL_set_session(ssl.get(), session.get()) ||
Matthew Braithwaitea57dcfb2017-02-17 22:08:23 -08001119 !SSL_set_strict_cipher_list(ssl.get(), "ECDHE-RSA-AES128-GCM-SHA256") ||
Steven Valdeza833c352016-11-01 13:39:36 -04001120 !SSL_set_max_proto_version(ssl.get(), max_version)) {
David Benjamin422fe082015-07-21 22:03:43 -04001121 return 0;
1122 }
Steven Valdeza833c352016-11-01 13:39:36 -04001123
David Benjaminafc64de2016-07-19 17:12:41 +02001124 std::vector<uint8_t> client_hello;
1125 if (!GetClientHello(ssl.get(), &client_hello) ||
1126 client_hello.size() <= SSL3_RT_HEADER_LENGTH) {
David Benjamin422fe082015-07-21 22:03:43 -04001127 return 0;
1128 }
Steven Valdeza833c352016-11-01 13:39:36 -04001129
David Benjaminafc64de2016-07-19 17:12:41 +02001130 return client_hello.size() - SSL3_RT_HEADER_LENGTH;
David Benjamin422fe082015-07-21 22:03:43 -04001131}
1132
David Benjamina486c6c2019-03-28 18:32:38 -05001133TEST(SSLTest, Padding) {
1134 struct PaddingVersions {
1135 uint16_t max_version, session_version;
1136 };
1137 static const PaddingVersions kPaddingVersions[] = {
1138 // Test the padding extension at TLS 1.2.
1139 {TLS1_2_VERSION, TLS1_2_VERSION},
1140 // Test the padding extension at TLS 1.3 with a TLS 1.2 session, so there
1141 // will be no PSK binder after the padding extension.
1142 {TLS1_3_VERSION, TLS1_2_VERSION},
1143 // Test the padding extension at TLS 1.3 with a TLS 1.3 session, so there
1144 // will be a PSK binder after the padding extension.
1145 {TLS1_3_VERSION, TLS1_3_VERSION},
David Benjamin422fe082015-07-21 22:03:43 -04001146
David Benjamina486c6c2019-03-28 18:32:38 -05001147 };
David Benjamin422fe082015-07-21 22:03:43 -04001148
David Benjamina486c6c2019-03-28 18:32:38 -05001149 struct PaddingTest {
1150 size_t input_len, padded_len;
1151 };
1152 static const PaddingTest kPaddingTests[] = {
1153 // ClientHellos of length below 0x100 do not require padding.
1154 {0xfe, 0xfe},
1155 {0xff, 0xff},
1156 // ClientHellos of length 0x100 through 0x1fb are padded up to 0x200.
1157 {0x100, 0x200},
1158 {0x123, 0x200},
1159 {0x1fb, 0x200},
1160 // ClientHellos of length 0x1fc through 0x1ff get padded beyond 0x200. The
1161 // padding extension takes a minimum of four bytes plus one required
1162 // content
1163 // byte. (To work around yet more server bugs, we avoid empty final
1164 // extensions.)
1165 {0x1fc, 0x201},
1166 {0x1fd, 0x202},
1167 {0x1fe, 0x203},
1168 {0x1ff, 0x204},
1169 // Finally, larger ClientHellos need no padding.
1170 {0x200, 0x200},
1171 {0x201, 0x201},
1172 };
David Benjamin422fe082015-07-21 22:03:43 -04001173
David Benjamina486c6c2019-03-28 18:32:38 -05001174 for (const PaddingVersions &versions : kPaddingVersions) {
1175 SCOPED_TRACE(versions.max_version);
1176 SCOPED_TRACE(versions.session_version);
David Benjamin422fe082015-07-21 22:03:43 -04001177
David Benjamina486c6c2019-03-28 18:32:38 -05001178 // Sample a baseline length.
1179 size_t base_len =
1180 GetClientHelloLen(versions.max_version, versions.session_version, 1);
1181 ASSERT_NE(base_len, 0u) << "Baseline length could not be sampled";
1182
1183 for (const PaddingTest &test : kPaddingTests) {
1184 SCOPED_TRACE(test.input_len);
1185 ASSERT_LE(base_len, test.input_len) << "Baseline ClientHello too long";
1186
1187 size_t padded_len =
1188 GetClientHelloLen(versions.max_version, versions.session_version,
1189 1 + test.input_len - base_len);
1190 EXPECT_EQ(padded_len, test.padded_len)
1191 << "ClientHello was not padded to expected length";
David Benjamin422fe082015-07-21 22:03:43 -04001192 }
1193 }
David Benjamin422fe082015-07-21 22:03:43 -04001194}
1195
David Benjamin2f3958a2021-04-16 11:55:23 -04001196static bssl::UniquePtr<X509> CertFromPEM(const char *pem) {
1197 bssl::UniquePtr<BIO> bio(BIO_new_mem_buf(pem, strlen(pem)));
1198 if (!bio) {
1199 return nullptr;
1200 }
1201 return bssl::UniquePtr<X509>(
1202 PEM_read_bio_X509(bio.get(), nullptr, nullptr, nullptr));
1203}
1204
1205static bssl::UniquePtr<EVP_PKEY> KeyFromPEM(const char *pem) {
1206 bssl::UniquePtr<BIO> bio(BIO_new_mem_buf(pem, strlen(pem)));
1207 if (!bio) {
1208 return nullptr;
1209 }
1210 return bssl::UniquePtr<EVP_PKEY>(
1211 PEM_read_bio_PrivateKey(bio.get(), nullptr, nullptr, nullptr));
1212}
1213
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001214static bssl::UniquePtr<X509> GetTestCertificate() {
David Benjaminde942382016-02-11 12:02:01 -05001215 static const char kCertPEM[] =
1216 "-----BEGIN CERTIFICATE-----\n"
1217 "MIICWDCCAcGgAwIBAgIJAPuwTC6rEJsMMA0GCSqGSIb3DQEBBQUAMEUxCzAJBgNV\n"
1218 "BAYTAkFVMRMwEQYDVQQIDApTb21lLVN0YXRlMSEwHwYDVQQKDBhJbnRlcm5ldCBX\n"
1219 "aWRnaXRzIFB0eSBMdGQwHhcNMTQwNDIzMjA1MDQwWhcNMTcwNDIyMjA1MDQwWjBF\n"
1220 "MQswCQYDVQQGEwJBVTETMBEGA1UECAwKU29tZS1TdGF0ZTEhMB8GA1UECgwYSW50\n"
1221 "ZXJuZXQgV2lkZ2l0cyBQdHkgTHRkMIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKB\n"
1222 "gQDYK8imMuRi/03z0K1Zi0WnvfFHvwlYeyK9Na6XJYaUoIDAtB92kWdGMdAQhLci\n"
1223 "HnAjkXLI6W15OoV3gA/ElRZ1xUpxTMhjP6PyY5wqT5r6y8FxbiiFKKAnHmUcrgfV\n"
1224 "W28tQ+0rkLGMryRtrukXOgXBv7gcrmU7G1jC2a7WqmeI8QIDAQABo1AwTjAdBgNV\n"
1225 "HQ4EFgQUi3XVrMsIvg4fZbf6Vr5sp3Xaha8wHwYDVR0jBBgwFoAUi3XVrMsIvg4f\n"
1226 "Zbf6Vr5sp3Xaha8wDAYDVR0TBAUwAwEB/zANBgkqhkiG9w0BAQUFAAOBgQA76Hht\n"
1227 "ldY9avcTGSwbwoiuIqv0jTL1fHFnzy3RHMLDh+Lpvolc5DSrSJHCP5WuK0eeJXhr\n"
1228 "T5oQpHL9z/cCDLAKCKRa4uV0fhEdOWBqyR9p8y5jJtye72t6CuFUV5iqcpF4BH4f\n"
1229 "j2VNHwsSrJwkD4QUGlUtH7vwnQmyCFxZMmWAJg==\n"
1230 "-----END CERTIFICATE-----\n";
David Benjamin2f3958a2021-04-16 11:55:23 -04001231 return CertFromPEM(kCertPEM);
David Benjaminde942382016-02-11 12:02:01 -05001232}
1233
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001234static bssl::UniquePtr<EVP_PKEY> GetTestKey() {
David Benjaminde942382016-02-11 12:02:01 -05001235 static const char kKeyPEM[] =
1236 "-----BEGIN RSA PRIVATE KEY-----\n"
1237 "MIICXgIBAAKBgQDYK8imMuRi/03z0K1Zi0WnvfFHvwlYeyK9Na6XJYaUoIDAtB92\n"
1238 "kWdGMdAQhLciHnAjkXLI6W15OoV3gA/ElRZ1xUpxTMhjP6PyY5wqT5r6y8FxbiiF\n"
1239 "KKAnHmUcrgfVW28tQ+0rkLGMryRtrukXOgXBv7gcrmU7G1jC2a7WqmeI8QIDAQAB\n"
1240 "AoGBAIBy09Fd4DOq/Ijp8HeKuCMKTHqTW1xGHshLQ6jwVV2vWZIn9aIgmDsvkjCe\n"
1241 "i6ssZvnbjVcwzSoByhjN8ZCf/i15HECWDFFh6gt0P5z0MnChwzZmvatV/FXCT0j+\n"
1242 "WmGNB/gkehKjGXLLcjTb6dRYVJSCZhVuOLLcbWIV10gggJQBAkEA8S8sGe4ezyyZ\n"
1243 "m4e9r95g6s43kPqtj5rewTsUxt+2n4eVodD+ZUlCULWVNAFLkYRTBCASlSrm9Xhj\n"
1244 "QpmWAHJUkQJBAOVzQdFUaewLtdOJoPCtpYoY1zd22eae8TQEmpGOR11L6kbxLQsk\n"
1245 "aMly/DOnOaa82tqAGTdqDEZgSNmCeKKknmECQAvpnY8GUOVAubGR6c+W90iBuQLj\n"
1246 "LtFp/9ihd2w/PoDwrHZaoUYVcT4VSfJQog/k7kjE4MYXYWL8eEKg3WTWQNECQQDk\n"
1247 "104Wi91Umd1PzF0ijd2jXOERJU1wEKe6XLkYYNHWQAe5l4J4MWj9OdxFXAxIuuR/\n"
1248 "tfDwbqkta4xcux67//khAkEAvvRXLHTaa6VFzTaiiO8SaFsHV3lQyXOtMrBpB5jd\n"
1249 "moZWgjHvB2W9Ckn7sDqsPB+U2tyX0joDdQEyuiMECDY8oQ==\n"
1250 "-----END RSA PRIVATE KEY-----\n";
David Benjamin2f3958a2021-04-16 11:55:23 -04001251 return KeyFromPEM(kKeyPEM);
David Benjaminde942382016-02-11 12:02:01 -05001252}
1253
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001254static bssl::UniquePtr<X509> GetECDSATestCertificate() {
David Benjamin0fc37ef2016-08-17 15:29:46 -04001255 static const char kCertPEM[] =
1256 "-----BEGIN CERTIFICATE-----\n"
1257 "MIIBzzCCAXagAwIBAgIJANlMBNpJfb/rMAkGByqGSM49BAEwRTELMAkGA1UEBhMC\n"
1258 "QVUxEzARBgNVBAgMClNvbWUtU3RhdGUxITAfBgNVBAoMGEludGVybmV0IFdpZGdp\n"
1259 "dHMgUHR5IEx0ZDAeFw0xNDA0MjMyMzIxNTdaFw0xNDA1MjMyMzIxNTdaMEUxCzAJ\n"
1260 "BgNVBAYTAkFVMRMwEQYDVQQIDApTb21lLVN0YXRlMSEwHwYDVQQKDBhJbnRlcm5l\n"
1261 "dCBXaWRnaXRzIFB0eSBMdGQwWTATBgcqhkjOPQIBBggqhkjOPQMBBwNCAATmK2ni\n"
1262 "v2Wfl74vHg2UikzVl2u3qR4NRvvdqakendy6WgHn1peoChj5w8SjHlbifINI2xYa\n"
1263 "HPUdfvGULUvPciLBo1AwTjAdBgNVHQ4EFgQUq4TSrKuV8IJOFngHVVdf5CaNgtEw\n"
1264 "HwYDVR0jBBgwFoAUq4TSrKuV8IJOFngHVVdf5CaNgtEwDAYDVR0TBAUwAwEB/zAJ\n"
1265 "BgcqhkjOPQQBA0gAMEUCIQDyoDVeUTo2w4J5m+4nUIWOcAZ0lVfSKXQA9L4Vh13E\n"
1266 "BwIgfB55FGohg/B6dGh5XxSZmmi08cueFV7mHzJSYV51yRQ=\n"
1267 "-----END CERTIFICATE-----\n";
David Benjamin2f3958a2021-04-16 11:55:23 -04001268 return CertFromPEM(kCertPEM);
David Benjamin0fc37ef2016-08-17 15:29:46 -04001269}
1270
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001271static bssl::UniquePtr<EVP_PKEY> GetECDSATestKey() {
David Benjamin0fc37ef2016-08-17 15:29:46 -04001272 static const char kKeyPEM[] =
1273 "-----BEGIN PRIVATE KEY-----\n"
1274 "MIGHAgEAMBMGByqGSM49AgEGCCqGSM49AwEHBG0wawIBAQQgBw8IcnrUoEqc3VnJ\n"
1275 "TYlodwi1b8ldMHcO6NHJzgqLtGqhRANCAATmK2niv2Wfl74vHg2UikzVl2u3qR4N\n"
1276 "Rvvdqakendy6WgHn1peoChj5w8SjHlbifINI2xYaHPUdfvGULUvPciLB\n"
1277 "-----END PRIVATE KEY-----\n";
David Benjamin2f3958a2021-04-16 11:55:23 -04001278 return KeyFromPEM(kKeyPEM);
David Benjamin0fc37ef2016-08-17 15:29:46 -04001279}
1280
Adam Langleyd04ca952017-02-28 11:26:51 -08001281static bssl::UniquePtr<CRYPTO_BUFFER> BufferFromPEM(const char *pem) {
1282 bssl::UniquePtr<BIO> bio(BIO_new_mem_buf(pem, strlen(pem)));
1283 char *name, *header;
1284 uint8_t *data;
1285 long data_len;
1286 if (!PEM_read_bio(bio.get(), &name, &header, &data,
1287 &data_len)) {
1288 return nullptr;
1289 }
1290 OPENSSL_free(name);
1291 OPENSSL_free(header);
1292
1293 auto ret = bssl::UniquePtr<CRYPTO_BUFFER>(
1294 CRYPTO_BUFFER_new(data, data_len, nullptr));
1295 OPENSSL_free(data);
1296 return ret;
1297}
1298
1299static bssl::UniquePtr<CRYPTO_BUFFER> GetChainTestCertificateBuffer() {
David Benjamin1444c3a2016-12-20 17:23:11 -05001300 static const char kCertPEM[] =
1301 "-----BEGIN CERTIFICATE-----\n"
1302 "MIIC0jCCAbqgAwIBAgICEAAwDQYJKoZIhvcNAQELBQAwDzENMAsGA1UEAwwEQiBD\n"
1303 "QTAeFw0xNjAyMjgyMDI3MDNaFw0yNjAyMjUyMDI3MDNaMBgxFjAUBgNVBAMMDUNs\n"
1304 "aWVudCBDZXJ0IEEwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDRvaz8\n"
1305 "CC/cshpCafJo4jLkHEoBqDLhdgFelJoAiQUyIqyWl2O7YHPnpJH+TgR7oelzNzt/\n"
1306 "kLRcH89M/TszB6zqyLTC4aqmvzKL0peD/jL2LWBucR0WXIvjA3zoRuF/x86+rYH3\n"
1307 "tHb+xs2PSs8EGL/Ev+ss+qTzTGEn26fuGNHkNw6tOwPpc+o8+wUtzf/kAthamo+c\n"
1308 "IDs2rQ+lP7+aLZTLeU/q4gcLutlzcK5imex5xy2jPkweq48kijK0kIzl1cPlA5d1\n"
1309 "z7C8jU50Pj9X9sQDJTN32j7UYRisJeeYQF8GaaN8SbrDI6zHgKzrRLyxDt/KQa9V\n"
1310 "iLeXANgZi+Xx9KgfAgMBAAGjLzAtMAwGA1UdEwEB/wQCMAAwHQYDVR0lBBYwFAYI\n"
1311 "KwYBBQUHAwEGCCsGAQUFBwMCMA0GCSqGSIb3DQEBCwUAA4IBAQBFEVbmYl+2RtNw\n"
1312 "rDftRDF1v2QUbcN2ouSnQDHxeDQdSgasLzT3ui8iYu0Rw2WWcZ0DV5e0ztGPhWq7\n"
1313 "AO0B120aFRMOY+4+bzu9Q2FFkQqc7/fKTvTDzIJI5wrMnFvUfzzvxh3OHWMYSs/w\n"
1314 "giq33hTKeHEq6Jyk3btCny0Ycecyc3yGXH10sizUfiHlhviCkDuESk8mFDwDDzqW\n"
1315 "ZF0IipzFbEDHoIxLlm3GQxpiLoEV4k8KYJp3R5KBLFyxM6UGPz8h72mIPCJp2RuK\n"
1316 "MYgF91UDvVzvnYm6TfseM2+ewKirC00GOrZ7rEcFvtxnKSqYf4ckqfNdSU1Y+RRC\n"
1317 "1ngWZ7Ih\n"
1318 "-----END CERTIFICATE-----\n";
Adam Langleyd04ca952017-02-28 11:26:51 -08001319 return BufferFromPEM(kCertPEM);
David Benjamin1444c3a2016-12-20 17:23:11 -05001320}
1321
Adam Langleyd04ca952017-02-28 11:26:51 -08001322static bssl::UniquePtr<X509> X509FromBuffer(
1323 bssl::UniquePtr<CRYPTO_BUFFER> buffer) {
1324 if (!buffer) {
1325 return nullptr;
1326 }
1327 const uint8_t *derp = CRYPTO_BUFFER_data(buffer.get());
1328 return bssl::UniquePtr<X509>(
1329 d2i_X509(NULL, &derp, CRYPTO_BUFFER_len(buffer.get())));
1330}
1331
1332static bssl::UniquePtr<X509> GetChainTestCertificate() {
1333 return X509FromBuffer(GetChainTestCertificateBuffer());
1334}
1335
1336static bssl::UniquePtr<CRYPTO_BUFFER> GetChainTestIntermediateBuffer() {
David Benjamin1444c3a2016-12-20 17:23:11 -05001337 static const char kCertPEM[] =
1338 "-----BEGIN CERTIFICATE-----\n"
1339 "MIICwjCCAaqgAwIBAgICEAEwDQYJKoZIhvcNAQELBQAwFDESMBAGA1UEAwwJQyBS\n"
1340 "b290IENBMB4XDTE2MDIyODIwMjcwM1oXDTI2MDIyNTIwMjcwM1owDzENMAsGA1UE\n"
1341 "AwwEQiBDQTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBALsSCYmDip2D\n"
1342 "GkjFxw7ykz26JSjELkl6ArlYjFJ3aT/SCh8qbS4gln7RH8CPBd78oFdfhIKQrwtZ\n"
1343 "3/q21ykD9BAS3qHe2YdcJfm8/kWAy5DvXk6NXU4qX334KofBAEpgdA/igEFq1P1l\n"
1344 "HAuIfZCpMRfT+i5WohVsGi8f/NgpRvVaMONLNfgw57mz1lbtFeBEISmX0kbsuJxF\n"
1345 "Qj/Bwhi5/0HAEXG8e7zN4cEx0yPRvmOATRdVb/8dW2pwOHRJq9R5M0NUkIsTSnL7\n"
1346 "6N/z8hRAHMsV3IudC5Yd7GXW1AGu9a+iKU+Q4xcZCoj0DC99tL4VKujrV1kAeqsM\n"
1347 "cz5/dKzi6+cCAwEAAaMjMCEwDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMC\n"
1348 "AQYwDQYJKoZIhvcNAQELBQADggEBAIIeZiEeNhWWQ8Y4D+AGDwqUUeG8NjCbKrXQ\n"
1349 "BlHg5wZ8xftFaiP1Dp/UAezmx2LNazdmuwrYB8lm3FVTyaPDTKEGIPS4wJKHgqH1\n"
1350 "QPDhqNm85ey7TEtI9oYjsNim/Rb+iGkIAMXaxt58SzxbjvP0kMr1JfJIZbic9vye\n"
1351 "NwIspMFIpP3FB8ywyu0T0hWtCQgL4J47nigCHpOu58deP88fS/Nyz/fyGVWOZ76b\n"
1352 "WhWwgM3P3X95fQ3d7oFPR/bVh0YV+Cf861INwplokXgXQ3/TCQ+HNXeAMWn3JLWv\n"
1353 "XFwk8owk9dq/kQGdndGgy3KTEW4ctPX5GNhf3LJ9Q7dLji4ReQ4=\n"
1354 "-----END CERTIFICATE-----\n";
Adam Langleyd04ca952017-02-28 11:26:51 -08001355 return BufferFromPEM(kCertPEM);
1356}
1357
1358static bssl::UniquePtr<X509> GetChainTestIntermediate() {
1359 return X509FromBuffer(GetChainTestIntermediateBuffer());
David Benjamin1444c3a2016-12-20 17:23:11 -05001360}
1361
1362static bssl::UniquePtr<EVP_PKEY> GetChainTestKey() {
1363 static const char kKeyPEM[] =
1364 "-----BEGIN PRIVATE KEY-----\n"
1365 "MIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQDRvaz8CC/cshpC\n"
1366 "afJo4jLkHEoBqDLhdgFelJoAiQUyIqyWl2O7YHPnpJH+TgR7oelzNzt/kLRcH89M\n"
1367 "/TszB6zqyLTC4aqmvzKL0peD/jL2LWBucR0WXIvjA3zoRuF/x86+rYH3tHb+xs2P\n"
1368 "Ss8EGL/Ev+ss+qTzTGEn26fuGNHkNw6tOwPpc+o8+wUtzf/kAthamo+cIDs2rQ+l\n"
1369 "P7+aLZTLeU/q4gcLutlzcK5imex5xy2jPkweq48kijK0kIzl1cPlA5d1z7C8jU50\n"
1370 "Pj9X9sQDJTN32j7UYRisJeeYQF8GaaN8SbrDI6zHgKzrRLyxDt/KQa9ViLeXANgZ\n"
1371 "i+Xx9KgfAgMBAAECggEBAK0VjSJzkyPaamcyTVSWjo7GdaBGcK60lk657RjR+lK0\n"
1372 "YJ7pkej4oM2hdsVZFsP8Cs4E33nXLa/0pDsRov/qrp0WQm2skwqGMC1I/bZ0WRPk\n"
1373 "wHaDrBBfESWnJDX/AGpVtlyOjPmgmK6J2usMPihQUDkKdAYrVWJePrMIxt1q6BMe\n"
1374 "iczs3qriMmtY3bUc4UyUwJ5fhDLjshHvfuIpYQyI6EXZM6dZksn9LylXJnigY6QJ\n"
1375 "HxOYO0BDwOsZ8yQ8J8afLk88i0GizEkgE1z3REtQUwgWfxr1WV/ud+T6/ZhSAgH9\n"
1376 "042mQvSFZnIUSEsmCvjhWuAunfxHKCTcAoYISWfzWpkCgYEA7gpf3HHU5Tn+CgUn\n"
1377 "1X5uGpG3DmcMgfeGgs2r2f/IIg/5Ac1dfYILiybL1tN9zbyLCJfcbFpWBc9hJL6f\n"
1378 "CPc5hUiwWFJqBJewxQkC1Ae/HakHbip+IZ+Jr0842O4BAArvixk4Lb7/N2Ct9sTE\n"
1379 "NJO6RtK9lbEZ5uK61DglHy8CS2UCgYEA4ZC1o36kPAMQBggajgnucb2yuUEelk0f\n"
1380 "AEr+GI32MGE+93xMr7rAhBoqLg4AITyIfEnOSQ5HwagnIHonBbv1LV/Gf9ursx8Z\n"
1381 "YOGbvT8zzzC+SU1bkDzdjAYnFQVGIjMtKOBJ3K07++ypwX1fr4QsQ8uKL8WSOWwt\n"
1382 "Z3Bym6XiZzMCgYADnhy+2OwHX85AkLt+PyGlPbmuelpyTzS4IDAQbBa6jcuW/2wA\n"
1383 "UE2km75VUXmD+u2R/9zVuLm99NzhFhSMqlUxdV1YukfqMfP5yp1EY6m/5aW7QuIP\n"
1384 "2MDa7TVL9rIFMiVZ09RKvbBbQxjhuzPQKL6X/PPspnhiTefQ+dl2k9xREQKBgHDS\n"
1385 "fMfGNEeAEKezrfSVqxphE9/tXms3L+ZpnCaT+yu/uEr5dTIAawKoQ6i9f/sf1/Sy\n"
1386 "xedsqR+IB+oKrzIDDWMgoJybN4pkZ8E5lzhVQIjFjKgFdWLzzqyW9z1gYfABQPlN\n"
1387 "FiS20WX0vgP1vcKAjdNrHzc9zyHBpgQzDmAj3NZZAoGBAI8vKCKdH7w3aL5CNkZQ\n"
1388 "2buIeWNA2HZazVwAGG5F2TU/LmXfRKnG6dX5bkU+AkBZh56jNZy//hfFSewJB4Kk\n"
1389 "buB7ERSdaNbO21zXt9FEA3+z0RfMd/Zv2vlIWOSB5nzl/7UKti3sribK6s9ZVLfi\n"
1390 "SxpiPQ8d/hmSGwn4ksrWUsJD\n"
1391 "-----END PRIVATE KEY-----\n";
David Benjamin2f3958a2021-04-16 11:55:23 -04001392 return KeyFromPEM(kKeyPEM);
David Benjamin1444c3a2016-12-20 17:23:11 -05001393}
1394
David Benjaminc79ae7a2017-08-29 16:09:44 -04001395// Test that |SSL_get_client_CA_list| echoes back the configured parameter even
1396// before configuring as a server.
1397TEST(SSLTest, ClientCAList) {
1398 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
1399 ASSERT_TRUE(ctx);
1400 bssl::UniquePtr<SSL> ssl(SSL_new(ctx.get()));
1401 ASSERT_TRUE(ssl);
1402
1403 bssl::UniquePtr<X509_NAME> name(X509_NAME_new());
1404 ASSERT_TRUE(name);
1405
1406 bssl::UniquePtr<X509_NAME> name_dup(X509_NAME_dup(name.get()));
1407 ASSERT_TRUE(name_dup);
1408
1409 bssl::UniquePtr<STACK_OF(X509_NAME)> stack(sk_X509_NAME_new_null());
1410 ASSERT_TRUE(stack);
David Benjamin2908dd12018-06-29 17:46:42 -04001411 ASSERT_TRUE(PushToStack(stack.get(), std::move(name_dup)));
David Benjaminc79ae7a2017-08-29 16:09:44 -04001412
1413 // |SSL_set_client_CA_list| takes ownership.
1414 SSL_set_client_CA_list(ssl.get(), stack.release());
1415
1416 STACK_OF(X509_NAME) *result = SSL_get_client_CA_list(ssl.get());
1417 ASSERT_TRUE(result);
1418 ASSERT_EQ(1u, sk_X509_NAME_num(result));
1419 EXPECT_EQ(0, X509_NAME_cmp(sk_X509_NAME_value(result, 0), name.get()));
1420}
1421
1422TEST(SSLTest, AddClientCA) {
1423 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
1424 ASSERT_TRUE(ctx);
1425 bssl::UniquePtr<SSL> ssl(SSL_new(ctx.get()));
1426 ASSERT_TRUE(ssl);
1427
1428 bssl::UniquePtr<X509> cert1 = GetTestCertificate();
1429 bssl::UniquePtr<X509> cert2 = GetChainTestCertificate();
1430 ASSERT_TRUE(cert1 && cert2);
1431 X509_NAME *name1 = X509_get_subject_name(cert1.get());
1432 X509_NAME *name2 = X509_get_subject_name(cert2.get());
1433
1434 EXPECT_EQ(0u, sk_X509_NAME_num(SSL_get_client_CA_list(ssl.get())));
1435
1436 ASSERT_TRUE(SSL_add_client_CA(ssl.get(), cert1.get()));
1437 ASSERT_TRUE(SSL_add_client_CA(ssl.get(), cert2.get()));
1438
1439 STACK_OF(X509_NAME) *list = SSL_get_client_CA_list(ssl.get());
1440 ASSERT_EQ(2u, sk_X509_NAME_num(list));
1441 EXPECT_EQ(0, X509_NAME_cmp(sk_X509_NAME_value(list, 0), name1));
1442 EXPECT_EQ(0, X509_NAME_cmp(sk_X509_NAME_value(list, 1), name2));
1443
1444 ASSERT_TRUE(SSL_add_client_CA(ssl.get(), cert1.get()));
1445
1446 list = SSL_get_client_CA_list(ssl.get());
1447 ASSERT_EQ(3u, sk_X509_NAME_num(list));
1448 EXPECT_EQ(0, X509_NAME_cmp(sk_X509_NAME_value(list, 0), name1));
1449 EXPECT_EQ(0, X509_NAME_cmp(sk_X509_NAME_value(list, 1), name2));
1450 EXPECT_EQ(0, X509_NAME_cmp(sk_X509_NAME_value(list, 2), name1));
1451}
1452
Daniel McArdle00e434d2021-02-18 11:47:18 -05001453// kECHConfig contains a serialized ECHConfig value.
1454static const uint8_t kECHConfig[] = {
1455 // version
Steven Valdez94a63a52021-04-29 10:52:42 -04001456 0xfe, 0x0a,
Daniel McArdle00e434d2021-02-18 11:47:18 -05001457 // length
Steven Valdez94a63a52021-04-29 10:52:42 -04001458 0x00, 0x43,
1459 // contents.config_id
1460 0x42,
1461 // contents.kem_id
1462 0x00, 0x20,
Daniel McArdle00e434d2021-02-18 11:47:18 -05001463 // contents.public_key
1464 0x00, 0x20, 0xa6, 0x9a, 0x41, 0x48, 0x5d, 0x32, 0x96, 0xa4, 0xe0, 0xc3,
1465 0x6a, 0xee, 0xf6, 0x63, 0x0f, 0x59, 0x32, 0x6f, 0xdc, 0xff, 0x81, 0x29,
1466 0x59, 0xa5, 0x85, 0xd3, 0x9b, 0x3b, 0xde, 0x98, 0x55, 0x5c,
Daniel McArdle00e434d2021-02-18 11:47:18 -05001467 // contents.cipher_suites
1468 0x00, 0x08, 0x00, 0x01, 0x00, 0x01, 0x00, 0x01, 0x00, 0x03,
1469 // contents.maximum_name_length
1470 0x00, 0x10,
Steven Valdez94a63a52021-04-29 10:52:42 -04001471 // contents.public_name
1472 0x00, 0x0e, 0x70, 0x75, 0x62, 0x6c, 0x69, 0x63, 0x2e, 0x65, 0x78, 0x61,
1473 0x6d, 0x70, 0x6c, 0x65,
Daniel McArdle00e434d2021-02-18 11:47:18 -05001474 // contents.extensions
1475 0x00, 0x00};
1476
1477// kECHConfigPublicKey is the public key encoded in |kECHConfig|.
1478static const uint8_t kECHConfigPublicKey[X25519_PUBLIC_VALUE_LEN] = {
1479 0xa6, 0x9a, 0x41, 0x48, 0x5d, 0x32, 0x96, 0xa4, 0xe0, 0xc3, 0x6a,
1480 0xee, 0xf6, 0x63, 0x0f, 0x59, 0x32, 0x6f, 0xdc, 0xff, 0x81, 0x29,
1481 0x59, 0xa5, 0x85, 0xd3, 0x9b, 0x3b, 0xde, 0x98, 0x55, 0x5c};
1482
1483// kECHConfigPrivateKey is the X25519 private key corresponding to
1484// |kECHConfigPublicKey|.
1485static const uint8_t kECHConfigPrivateKey[X25519_PRIVATE_KEY_LEN] = {
1486 0xbc, 0xb5, 0x51, 0x29, 0x31, 0x10, 0x30, 0xc9, 0xed, 0x26, 0xde,
1487 0xd4, 0xb3, 0xdf, 0x3a, 0xce, 0x06, 0x8a, 0xee, 0x17, 0xab, 0xce,
1488 0xd7, 0xdb, 0xf3, 0x11, 0xe5, 0xa8, 0xf3, 0xb1, 0x8e, 0x24};
1489
1490// MakeECHConfig serializes an ECHConfig and writes it to |*out| with the
1491// specified parameters. |cipher_suites| is a list of code points which should
1492// contain pairs of KDF and AEAD IDs.
Steven Valdez94a63a52021-04-29 10:52:42 -04001493bool MakeECHConfig(std::vector<uint8_t> *out, uint8_t config_id,
1494 uint16_t kem_id, Span<const uint8_t> public_key,
Daniel McArdle00e434d2021-02-18 11:47:18 -05001495 Span<const uint16_t> cipher_suites,
1496 Span<const uint8_t> extensions) {
1497 bssl::ScopedCBB cbb;
1498 CBB contents, child;
1499 static const char kPublicName[] = "example.com";
1500 if (!CBB_init(cbb.get(), 64) ||
1501 !CBB_add_u16(cbb.get(), TLSEXT_TYPE_encrypted_client_hello) ||
1502 !CBB_add_u16_length_prefixed(cbb.get(), &contents) ||
Steven Valdez94a63a52021-04-29 10:52:42 -04001503 !CBB_add_u8(&contents, config_id) ||
1504 !CBB_add_u16(&contents, kem_id) ||
Daniel McArdle00e434d2021-02-18 11:47:18 -05001505 !CBB_add_u16_length_prefixed(&contents, &child) ||
1506 !CBB_add_bytes(&child, public_key.data(), public_key.size()) ||
Daniel McArdle00e434d2021-02-18 11:47:18 -05001507 !CBB_add_u16_length_prefixed(&contents, &child)) {
1508 return false;
1509 }
1510 for (uint16_t cipher_suite : cipher_suites) {
1511 if (!CBB_add_u16(&child, cipher_suite)) {
1512 return false;
1513 }
1514 }
1515 if (!CBB_add_u16(&contents, strlen(kPublicName)) || // maximum_name_length
1516 !CBB_add_u16_length_prefixed(&contents, &child) ||
Steven Valdez94a63a52021-04-29 10:52:42 -04001517 !CBB_add_bytes(&child, reinterpret_cast<const uint8_t *>(kPublicName),
1518 strlen(kPublicName)) ||
1519 !CBB_add_u16_length_prefixed(&contents, &child) ||
Daniel McArdle00e434d2021-02-18 11:47:18 -05001520 !CBB_add_bytes(&child, extensions.data(), extensions.size()) ||
1521 !CBB_flush(cbb.get())) {
1522 return false;
1523 }
1524
1525 out->assign(CBB_data(cbb.get()), CBB_data(cbb.get()) + CBB_len(cbb.get()));
1526 return true;
1527}
1528
1529TEST(SSLTest, ECHServerConfigList) {
1530 // kWrongPrivateKey is an unrelated, but valid X25519 private key.
1531 const uint8_t kWrongPrivateKey[X25519_PRIVATE_KEY_LEN] = {
1532 0xbb, 0xfe, 0x08, 0xf7, 0x31, 0xde, 0x9c, 0x8a, 0xf2, 0x06, 0x4a,
1533 0x18, 0xd7, 0x8b, 0x79, 0x31, 0xe2, 0x53, 0xdd, 0x63, 0x8f, 0x58,
1534 0x42, 0xda, 0x21, 0x0e, 0x61, 0x97, 0x29, 0xcc, 0x17, 0x71};
1535
1536 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
1537 ASSERT_TRUE(ctx);
1538
1539 bssl::UniquePtr<SSL_ECH_SERVER_CONFIG_LIST> config_list(
1540 SSL_ECH_SERVER_CONFIG_LIST_new());
1541 ASSERT_TRUE(config_list);
1542
1543 // Adding an ECHConfig with the wrong private key is an error.
1544 ASSERT_FALSE(SSL_ECH_SERVER_CONFIG_LIST_add(
1545 config_list.get(), /*is_retry_config=*/1, kECHConfig, sizeof(kECHConfig),
1546 kWrongPrivateKey, sizeof(kWrongPrivateKey)));
1547 uint32_t err = ERR_get_error();
1548 EXPECT_EQ(ERR_LIB_SSL, ERR_GET_LIB(err));
1549 EXPECT_EQ(SSL_R_ECH_SERVER_CONFIG_AND_PRIVATE_KEY_MISMATCH,
1550 ERR_GET_REASON(err));
1551 ERR_clear_error();
1552
1553 // Adding an ECHConfig with the matching private key succeeds.
1554 ASSERT_TRUE(SSL_ECH_SERVER_CONFIG_LIST_add(
1555 config_list.get(), /*is_retry_config=*/1, kECHConfig, sizeof(kECHConfig),
1556 kECHConfigPrivateKey, sizeof(kECHConfigPrivateKey)));
1557
1558 ASSERT_TRUE(
1559 SSL_CTX_set1_ech_server_config_list(ctx.get(), config_list.get()));
1560
1561 // Build a new config list and replace the old one on |ctx|.
1562 bssl::UniquePtr<SSL_ECH_SERVER_CONFIG_LIST> next_config_list(
1563 SSL_ECH_SERVER_CONFIG_LIST_new());
1564 ASSERT_TRUE(SSL_ECH_SERVER_CONFIG_LIST_add(
1565 next_config_list.get(), /*is_retry_config=*/1, kECHConfig,
1566 sizeof(kECHConfig), kECHConfigPrivateKey, sizeof(kECHConfigPrivateKey)));
1567 ASSERT_TRUE(
1568 SSL_CTX_set1_ech_server_config_list(ctx.get(), next_config_list.get()));
1569}
1570
1571TEST(SSLTest, ECHServerConfigListTruncatedPublicKey) {
1572 std::vector<uint8_t> ech_config;
1573 ASSERT_TRUE(MakeECHConfig(
Steven Valdez94a63a52021-04-29 10:52:42 -04001574 &ech_config, 0x42, EVP_HPKE_DHKEM_X25519_HKDF_SHA256,
Daniel McArdle00e434d2021-02-18 11:47:18 -05001575 MakeConstSpan(kECHConfigPublicKey, sizeof(kECHConfigPublicKey) - 1),
1576 std::vector<uint16_t>{EVP_HPKE_HKDF_SHA256, EVP_HPKE_AEAD_AES_128_GCM},
1577 /*extensions=*/{}));
1578
1579 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
1580 ASSERT_TRUE(ctx);
1581
1582 bssl::UniquePtr<SSL_ECH_SERVER_CONFIG_LIST> config_list(
1583 SSL_ECH_SERVER_CONFIG_LIST_new());
1584 ASSERT_TRUE(config_list);
1585 ASSERT_FALSE(SSL_ECH_SERVER_CONFIG_LIST_add(
1586 config_list.get(), /*is_retry_config=*/1, ech_config.data(),
1587 ech_config.size(), kECHConfigPrivateKey, sizeof(kECHConfigPrivateKey)));
1588
1589 uint32_t err = ERR_peek_error();
1590 EXPECT_EQ(ERR_LIB_SSL, ERR_GET_LIB(err));
1591 EXPECT_EQ(SSL_R_UNSUPPORTED_ECH_SERVER_CONFIG, ERR_GET_REASON(err));
1592 ERR_clear_error();
1593}
1594
1595// Test that |SSL_CTX_set1_ech_server_config_list| fails when the config list
1596// has no retry configs.
1597TEST(SSLTest, ECHServerConfigsWithoutRetryConfigs) {
1598 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
1599 ASSERT_TRUE(ctx);
1600
1601 bssl::UniquePtr<SSL_ECH_SERVER_CONFIG_LIST> config_list(
1602 SSL_ECH_SERVER_CONFIG_LIST_new());
1603 ASSERT_TRUE(config_list);
1604
1605 // Adding an ECHConfig with the matching private key succeeds.
1606 ASSERT_TRUE(SSL_ECH_SERVER_CONFIG_LIST_add(
1607 config_list.get(), /*is_retry_config=*/0, kECHConfig, sizeof(kECHConfig),
1608 kECHConfigPrivateKey, sizeof(kECHConfigPrivateKey)));
1609
1610 ASSERT_FALSE(
1611 SSL_CTX_set1_ech_server_config_list(ctx.get(), config_list.get()));
1612 uint32_t err = ERR_peek_error();
1613 EXPECT_EQ(ERR_LIB_SSL, ERR_GET_LIB(err));
1614 EXPECT_EQ(SSL_R_ECH_SERVER_WOULD_HAVE_NO_RETRY_CONFIGS, ERR_GET_REASON(err));
1615 ERR_clear_error();
1616
1617 // Add the same ECHConfig to the list, but this time mark it as a retry
1618 // config.
1619 ASSERT_TRUE(SSL_ECH_SERVER_CONFIG_LIST_add(
1620 config_list.get(), /*is_retry_config=*/1, kECHConfig, sizeof(kECHConfig),
1621 kECHConfigPrivateKey, sizeof(kECHConfigPrivateKey)));
1622 ASSERT_TRUE(
1623 SSL_CTX_set1_ech_server_config_list(ctx.get(), config_list.get()));
1624}
1625
1626// Test that the server APIs reject ECHConfigs with unsupported features.
1627TEST(SSLTest, UnsupportedECHConfig) {
1628 bssl::UniquePtr<SSL_ECH_SERVER_CONFIG_LIST> config_list(
1629 SSL_ECH_SERVER_CONFIG_LIST_new());
1630 ASSERT_TRUE(config_list);
1631
1632 // Unsupported versions are rejected.
1633 static const uint8_t kUnsupportedVersion[] = {0xff, 0xff, 0x00, 0x00};
1634 EXPECT_FALSE(SSL_ECH_SERVER_CONFIG_LIST_add(
1635 config_list.get(), /*is_retry_config=*/1, kUnsupportedVersion,
1636 sizeof(kUnsupportedVersion), kECHConfigPrivateKey,
1637 sizeof(kECHConfigPrivateKey)));
1638
1639 // Unsupported cipher suites are rejected. (We only support HKDF-SHA256.)
1640 std::vector<uint8_t> ech_config;
1641 ASSERT_TRUE(MakeECHConfig(
Steven Valdez94a63a52021-04-29 10:52:42 -04001642 &ech_config, 0x42, EVP_HPKE_DHKEM_X25519_HKDF_SHA256, kECHConfigPublicKey,
David Benjamin9f700972021-05-03 15:31:56 -04001643 std::vector<uint16_t>{0x002 /* HKDF-SHA384 */, EVP_HPKE_AEAD_AES_128_GCM},
Daniel McArdle00e434d2021-02-18 11:47:18 -05001644 /*extensions=*/{}));
1645 EXPECT_FALSE(SSL_ECH_SERVER_CONFIG_LIST_add(
1646 config_list.get(), /*is_retry_config=*/1, ech_config.data(),
1647 ech_config.size(), kECHConfigPrivateKey, sizeof(kECHConfigPrivateKey)));
1648
1649 // Unsupported KEMs are rejected.
1650 static const uint8_t kP256PublicKey[] = {
1651 0x04, 0xe6, 0x2b, 0x69, 0xe2, 0xbf, 0x65, 0x9f, 0x97, 0xbe, 0x2f,
1652 0x1e, 0x0d, 0x94, 0x8a, 0x4c, 0xd5, 0x97, 0x6b, 0xb7, 0xa9, 0x1e,
1653 0x0d, 0x46, 0xfb, 0xdd, 0xa9, 0xa9, 0x1e, 0x9d, 0xdc, 0xba, 0x5a,
1654 0x01, 0xe7, 0xd6, 0x97, 0xa8, 0x0a, 0x18, 0xf9, 0xc3, 0xc4, 0xa3,
1655 0x1e, 0x56, 0xe2, 0x7c, 0x83, 0x48, 0xdb, 0x16, 0x1a, 0x1c, 0xf5,
1656 0x1d, 0x7e, 0xf1, 0x94, 0x2d, 0x4b, 0xcf, 0x72, 0x22, 0xc1};
1657 static const uint8_t kP256PrivateKey[] = {
1658 0x07, 0x0f, 0x08, 0x72, 0x7a, 0xd4, 0xa0, 0x4a, 0x9c, 0xdd, 0x59,
1659 0xc9, 0x4d, 0x89, 0x68, 0x77, 0x08, 0xb5, 0x6f, 0xc9, 0x5d, 0x30,
1660 0x77, 0x0e, 0xe8, 0xd1, 0xc9, 0xce, 0x0a, 0x8b, 0xb4, 0x6a};
1661 ASSERT_TRUE(MakeECHConfig(
Steven Valdez94a63a52021-04-29 10:52:42 -04001662 &ech_config, 0x42, 0x0010 /* DHKEM(P-256, HKDF-SHA256) */, kP256PublicKey,
Daniel McArdle00e434d2021-02-18 11:47:18 -05001663 std::vector<uint16_t>{EVP_HPKE_HKDF_SHA256, EVP_HPKE_AEAD_AES_128_GCM},
1664 /*extensions=*/{}));
1665 EXPECT_FALSE(SSL_ECH_SERVER_CONFIG_LIST_add(
1666 config_list.get(), /*is_retry_config=*/1, ech_config.data(),
1667 ech_config.size(), kP256PrivateKey, sizeof(kP256PrivateKey)));
1668
1669 // Unsupported extensions are rejected.
1670 static const uint8_t kExtensions[] = {0x00, 0x01, 0x00, 0x00};
1671 ASSERT_TRUE(MakeECHConfig(
Steven Valdez94a63a52021-04-29 10:52:42 -04001672 &ech_config, 0x42, EVP_HPKE_DHKEM_X25519_HKDF_SHA256, kECHConfigPublicKey,
Daniel McArdle00e434d2021-02-18 11:47:18 -05001673 std::vector<uint16_t>{EVP_HPKE_HKDF_SHA256, EVP_HPKE_AEAD_AES_128_GCM},
1674 kExtensions));
1675 EXPECT_FALSE(SSL_ECH_SERVER_CONFIG_LIST_add(
1676 config_list.get(), /*is_retry_config=*/1, ech_config.data(),
1677 ech_config.size(), kECHConfigPrivateKey, sizeof(kECHConfigPrivateKey)));
1678}
1679
David Benjaminc79ae7a2017-08-29 16:09:44 -04001680static void AppendSession(SSL_SESSION *session, void *arg) {
1681 std::vector<SSL_SESSION*> *out =
1682 reinterpret_cast<std::vector<SSL_SESSION*>*>(arg);
1683 out->push_back(session);
1684}
1685
1686// CacheEquals returns true if |ctx|'s session cache consists of |expected|, in
1687// order.
1688static bool CacheEquals(SSL_CTX *ctx,
1689 const std::vector<SSL_SESSION*> &expected) {
1690 // Check the linked list.
1691 SSL_SESSION *ptr = ctx->session_cache_head;
1692 for (SSL_SESSION *session : expected) {
1693 if (ptr != session) {
1694 return false;
1695 }
1696 // TODO(davidben): This is an absurd way to denote the end of the list.
1697 if (ptr->next ==
1698 reinterpret_cast<SSL_SESSION *>(&ctx->session_cache_tail)) {
1699 ptr = nullptr;
1700 } else {
1701 ptr = ptr->next;
1702 }
1703 }
1704 if (ptr != nullptr) {
1705 return false;
1706 }
1707
1708 // Check the hash table.
1709 std::vector<SSL_SESSION*> actual, expected_copy;
David Benjamin9eaa3bd2017-09-27 17:03:54 -04001710 lh_SSL_SESSION_doall_arg(ctx->sessions, AppendSession, &actual);
David Benjaminc79ae7a2017-08-29 16:09:44 -04001711 expected_copy = expected;
1712
1713 std::sort(actual.begin(), actual.end());
1714 std::sort(expected_copy.begin(), expected_copy.end());
1715
1716 return actual == expected_copy;
1717}
1718
1719static bssl::UniquePtr<SSL_SESSION> CreateTestSession(uint32_t number) {
1720 bssl::UniquePtr<SSL_CTX> ssl_ctx(SSL_CTX_new(TLS_method()));
1721 if (!ssl_ctx) {
1722 return nullptr;
1723 }
1724 bssl::UniquePtr<SSL_SESSION> ret(SSL_SESSION_new(ssl_ctx.get()));
1725 if (!ret) {
1726 return nullptr;
1727 }
1728
David Benjaminaaef8332018-06-29 16:45:49 -04001729 uint8_t id[SSL3_SSL_SESSION_ID_LENGTH] = {0};
1730 OPENSSL_memcpy(id, &number, sizeof(number));
1731 if (!SSL_SESSION_set1_id(ret.get(), id, sizeof(id))) {
1732 return nullptr;
1733 }
David Benjaminc79ae7a2017-08-29 16:09:44 -04001734 return ret;
1735}
1736
1737// Test that the internal session cache behaves as expected.
1738TEST(SSLTest, InternalSessionCache) {
1739 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
1740 ASSERT_TRUE(ctx);
1741
1742 // Prepare 10 test sessions.
1743 std::vector<bssl::UniquePtr<SSL_SESSION>> sessions;
1744 for (int i = 0; i < 10; i++) {
1745 bssl::UniquePtr<SSL_SESSION> session = CreateTestSession(i);
1746 ASSERT_TRUE(session);
1747 sessions.push_back(std::move(session));
1748 }
1749
1750 SSL_CTX_sess_set_cache_size(ctx.get(), 5);
1751
1752 // Insert all the test sessions.
1753 for (const auto &session : sessions) {
1754 ASSERT_TRUE(SSL_CTX_add_session(ctx.get(), session.get()));
1755 }
1756
1757 // Only the last five should be in the list.
1758 ASSERT_TRUE(CacheEquals(
1759 ctx.get(), {sessions[9].get(), sessions[8].get(), sessions[7].get(),
1760 sessions[6].get(), sessions[5].get()}));
1761
1762 // Inserting an element already in the cache should fail and leave the cache
1763 // unchanged.
1764 ASSERT_FALSE(SSL_CTX_add_session(ctx.get(), sessions[7].get()));
1765 ASSERT_TRUE(CacheEquals(
1766 ctx.get(), {sessions[9].get(), sessions[8].get(), sessions[7].get(),
1767 sessions[6].get(), sessions[5].get()}));
1768
1769 // Although collisions should be impossible (256-bit session IDs), the cache
1770 // must handle them gracefully.
1771 bssl::UniquePtr<SSL_SESSION> collision(CreateTestSession(7));
1772 ASSERT_TRUE(collision);
1773 ASSERT_TRUE(SSL_CTX_add_session(ctx.get(), collision.get()));
1774 ASSERT_TRUE(CacheEquals(
1775 ctx.get(), {collision.get(), sessions[9].get(), sessions[8].get(),
1776 sessions[6].get(), sessions[5].get()}));
1777
1778 // Removing sessions behaves correctly.
1779 ASSERT_TRUE(SSL_CTX_remove_session(ctx.get(), sessions[6].get()));
1780 ASSERT_TRUE(CacheEquals(ctx.get(), {collision.get(), sessions[9].get(),
1781 sessions[8].get(), sessions[5].get()}));
1782
1783 // Removing sessions requires an exact match.
1784 ASSERT_FALSE(SSL_CTX_remove_session(ctx.get(), sessions[0].get()));
1785 ASSERT_FALSE(SSL_CTX_remove_session(ctx.get(), sessions[7].get()));
1786
1787 // The cache remains unchanged.
1788 ASSERT_TRUE(CacheEquals(ctx.get(), {collision.get(), sessions[9].get(),
1789 sessions[8].get(), sessions[5].get()}));
1790}
1791
1792static uint16_t EpochFromSequence(uint64_t seq) {
1793 return static_cast<uint16_t>(seq >> 48);
1794}
1795
David Benjamin71dfad42017-07-16 17:27:39 -04001796static const uint8_t kTestName[] = {
1797 0x30, 0x45, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13,
1798 0x02, 0x41, 0x55, 0x31, 0x13, 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x08,
1799 0x0c, 0x0a, 0x53, 0x6f, 0x6d, 0x65, 0x2d, 0x53, 0x74, 0x61, 0x74, 0x65,
1800 0x31, 0x21, 0x30, 0x1f, 0x06, 0x03, 0x55, 0x04, 0x0a, 0x0c, 0x18, 0x49,
1801 0x6e, 0x74, 0x65, 0x72, 0x6e, 0x65, 0x74, 0x20, 0x57, 0x69, 0x64, 0x67,
1802 0x69, 0x74, 0x73, 0x20, 0x50, 0x74, 0x79, 0x20, 0x4c, 0x74, 0x64,
1803};
1804
David Benjaminb79cc842016-12-07 15:57:14 -05001805static bool CompleteHandshakes(SSL *client, SSL *server) {
1806 // Drive both their handshakes to completion.
1807 for (;;) {
1808 int client_ret = SSL_do_handshake(client);
1809 int client_err = SSL_get_error(client, client_ret);
1810 if (client_err != SSL_ERROR_NONE &&
1811 client_err != SSL_ERROR_WANT_READ &&
Adam Langley4c341d02017-03-08 19:33:21 -08001812 client_err != SSL_ERROR_WANT_WRITE &&
1813 client_err != SSL_ERROR_PENDING_TICKET) {
Matthew Braithwaite4f3e8212020-01-08 16:56:48 -08001814 fprintf(stderr, "Client error: %s\n", SSL_error_description(client_err));
David Benjaminb79cc842016-12-07 15:57:14 -05001815 return false;
1816 }
1817
1818 int server_ret = SSL_do_handshake(server);
1819 int server_err = SSL_get_error(server, server_ret);
1820 if (server_err != SSL_ERROR_NONE &&
1821 server_err != SSL_ERROR_WANT_READ &&
Adam Langley4c341d02017-03-08 19:33:21 -08001822 server_err != SSL_ERROR_WANT_WRITE &&
1823 server_err != SSL_ERROR_PENDING_TICKET) {
Matthew Braithwaite4f3e8212020-01-08 16:56:48 -08001824 fprintf(stderr, "Server error: %s\n", SSL_error_description(server_err));
David Benjaminb79cc842016-12-07 15:57:14 -05001825 return false;
1826 }
1827
1828 if (client_ret == 1 && server_ret == 1) {
1829 break;
1830 }
1831 }
1832
1833 return true;
1834}
1835
Steven Valdez777a2392019-02-21 11:30:47 -05001836static bool FlushNewSessionTickets(SSL *client, SSL *server) {
1837 // NewSessionTickets are deferred on the server to |SSL_write|, and clients do
1838 // not pick them up until |SSL_read|.
1839 for (;;) {
1840 int server_ret = SSL_write(server, nullptr, 0);
1841 int server_err = SSL_get_error(server, server_ret);
1842 // The server may either succeed (|server_ret| is zero) or block on write
1843 // (|server_ret| is -1 and |server_err| is |SSL_ERROR_WANT_WRITE|).
1844 if (server_ret > 0 ||
1845 (server_ret < 0 && server_err != SSL_ERROR_WANT_WRITE)) {
1846 fprintf(stderr, "Unexpected server result: %d %d\n", server_ret,
1847 server_err);
1848 return false;
1849 }
1850
1851 int client_ret = SSL_read(client, nullptr, 0);
1852 int client_err = SSL_get_error(client, client_ret);
1853 // The client must always block on read.
1854 if (client_ret != -1 || client_err != SSL_ERROR_WANT_READ) {
1855 fprintf(stderr, "Unexpected client result: %d %d\n", client_ret,
1856 client_err);
1857 return false;
1858 }
1859
1860 // The server flushed everything it had to write.
1861 if (server_ret == 0) {
1862 return true;
1863 }
1864 }
1865}
1866
David Benjamina8614602017-09-06 15:40:19 -04001867struct ClientConfig {
1868 SSL_SESSION *session = nullptr;
1869 std::string servername;
Matthew Braithwaite4f3e8212020-01-08 16:56:48 -08001870 bool early_data = false;
David Benjamina8614602017-09-06 15:40:19 -04001871};
1872
David Benjaminb79cc842016-12-07 15:57:14 -05001873static bool ConnectClientAndServer(bssl::UniquePtr<SSL> *out_client,
1874 bssl::UniquePtr<SSL> *out_server,
David Benjamina20e5352016-08-02 19:09:41 -04001875 SSL_CTX *client_ctx, SSL_CTX *server_ctx,
Adam Langleyddb57cf2018-01-26 09:17:53 -08001876 const ClientConfig &config = ClientConfig(),
Matthew Braithwaiteb7bc80a2018-04-13 15:51:30 -07001877 bool do_handshake = true,
1878 bool shed_handshake_config = true) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07001879 bssl::UniquePtr<SSL> client(SSL_new(client_ctx)), server(SSL_new(server_ctx));
David Benjaminde942382016-02-11 12:02:01 -05001880 if (!client || !server) {
1881 return false;
1882 }
Matthew Braithwaite4f3e8212020-01-08 16:56:48 -08001883 if (config.early_data) {
1884 SSL_set_early_data_enabled(client.get(), 1);
1885 }
David Benjaminde942382016-02-11 12:02:01 -05001886 SSL_set_connect_state(client.get());
1887 SSL_set_accept_state(server.get());
1888
David Benjamina8614602017-09-06 15:40:19 -04001889 if (config.session) {
1890 SSL_set_session(client.get(), config.session);
1891 }
1892 if (!config.servername.empty() &&
1893 !SSL_set_tlsext_host_name(client.get(), config.servername.c_str())) {
1894 return false;
1895 }
David Benjamina20e5352016-08-02 19:09:41 -04001896
David Benjaminde942382016-02-11 12:02:01 -05001897 BIO *bio1, *bio2;
1898 if (!BIO_new_bio_pair(&bio1, 0, &bio2, 0)) {
1899 return false;
1900 }
1901 // SSL_set_bio takes ownership.
1902 SSL_set_bio(client.get(), bio1, bio1);
1903 SSL_set_bio(server.get(), bio2, bio2);
1904
Matthew Braithwaiteb7bc80a2018-04-13 15:51:30 -07001905 SSL_set_shed_handshake_config(client.get(), shed_handshake_config);
1906 SSL_set_shed_handshake_config(server.get(), shed_handshake_config);
1907
Adam Langleyddb57cf2018-01-26 09:17:53 -08001908 if (do_handshake && !CompleteHandshakes(client.get(), server.get())) {
David Benjaminb79cc842016-12-07 15:57:14 -05001909 return false;
David Benjaminde942382016-02-11 12:02:01 -05001910 }
1911
David Benjamin686bb192016-05-10 15:15:41 -04001912 *out_client = std::move(client);
1913 *out_server = std::move(server);
1914 return true;
1915}
1916
David Benjaminc11ea9422017-08-29 16:33:21 -04001917// SSLVersionTest executes its test cases under all available protocol versions.
1918// Test cases call |Connect| to create a connection using context objects with
1919// the protocol version fixed to the current version under test.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07001920class SSLVersionTest : public ::testing::TestWithParam<VersionParam> {
1921 protected:
1922 SSLVersionTest() : cert_(GetTestCertificate()), key_(GetTestKey()) {}
1923
1924 void SetUp() { ResetContexts(); }
1925
1926 bssl::UniquePtr<SSL_CTX> CreateContext() const {
1927 const SSL_METHOD *method = is_dtls() ? DTLS_method() : TLS_method();
1928 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(method));
1929 if (!ctx || !SSL_CTX_set_min_proto_version(ctx.get(), version()) ||
1930 !SSL_CTX_set_max_proto_version(ctx.get(), version())) {
1931 return nullptr;
1932 }
1933 return ctx;
David Benjamin0fef3052016-11-18 15:11:10 +09001934 }
David Benjamin686bb192016-05-10 15:15:41 -04001935
Martin Kreichgauer1a663262017-08-16 14:54:04 -07001936 void ResetContexts() {
1937 ASSERT_TRUE(cert_);
1938 ASSERT_TRUE(key_);
1939 client_ctx_ = CreateContext();
1940 ASSERT_TRUE(client_ctx_);
1941 server_ctx_ = CreateContext();
1942 ASSERT_TRUE(server_ctx_);
1943 // Set up a server cert. Client certs can be set up explicitly.
1944 ASSERT_TRUE(UseCertAndKey(server_ctx_.get()));
David Benjamin0fef3052016-11-18 15:11:10 +09001945 }
David Benjamin686bb192016-05-10 15:15:41 -04001946
Martin Kreichgauer1a663262017-08-16 14:54:04 -07001947 bool UseCertAndKey(SSL_CTX *ctx) const {
1948 return SSL_CTX_use_certificate(ctx, cert_.get()) &&
1949 SSL_CTX_use_PrivateKey(ctx, key_.get());
David Benjamin0fef3052016-11-18 15:11:10 +09001950 }
David Benjamin686bb192016-05-10 15:15:41 -04001951
David Benjamina8614602017-09-06 15:40:19 -04001952 bool Connect(const ClientConfig &config = ClientConfig()) {
Martin Kreichgauer1a663262017-08-16 14:54:04 -07001953 return ConnectClientAndServer(&client_, &server_, client_ctx_.get(),
Matthew Braithwaiteb7bc80a2018-04-13 15:51:30 -07001954 server_ctx_.get(), config, true,
1955 shed_handshake_config_);
Martin Kreichgauer1a663262017-08-16 14:54:04 -07001956 }
1957
1958 uint16_t version() const { return GetParam().version; }
1959
1960 bool is_dtls() const {
1961 return GetParam().ssl_method == VersionParam::is_dtls;
1962 }
1963
Matthew Braithwaiteb7bc80a2018-04-13 15:51:30 -07001964 bool shed_handshake_config_ = true;
Martin Kreichgauer1a663262017-08-16 14:54:04 -07001965 bssl::UniquePtr<SSL> client_, server_;
1966 bssl::UniquePtr<SSL_CTX> server_ctx_, client_ctx_;
1967 bssl::UniquePtr<X509> cert_;
1968 bssl::UniquePtr<EVP_PKEY> key_;
1969};
1970
David Benjaminbe7006a2019-04-09 18:05:02 -05001971INSTANTIATE_TEST_SUITE_P(WithVersion, SSLVersionTest,
1972 testing::ValuesIn(kAllVersions),
1973 [](const testing::TestParamInfo<VersionParam> &i) {
1974 return i.param.name;
1975 });
Martin Kreichgauer1a663262017-08-16 14:54:04 -07001976
1977TEST_P(SSLVersionTest, SequenceNumber) {
1978 ASSERT_TRUE(Connect());
1979
David Benjamin0fef3052016-11-18 15:11:10 +09001980 // Drain any post-handshake messages to ensure there are no unread records
1981 // on either end.
Steven Valdez777a2392019-02-21 11:30:47 -05001982 ASSERT_TRUE(FlushNewSessionTickets(client_.get(), server_.get()));
David Benjaminde942382016-02-11 12:02:01 -05001983
Martin Kreichgauer1a663262017-08-16 14:54:04 -07001984 uint64_t client_read_seq = SSL_get_read_sequence(client_.get());
1985 uint64_t client_write_seq = SSL_get_write_sequence(client_.get());
1986 uint64_t server_read_seq = SSL_get_read_sequence(server_.get());
1987 uint64_t server_write_seq = SSL_get_write_sequence(server_.get());
Steven Valdez2c62fe92016-10-14 12:08:12 -04001988
Martin Kreichgauer1a663262017-08-16 14:54:04 -07001989 if (is_dtls()) {
David Benjamin0fef3052016-11-18 15:11:10 +09001990 // Both client and server must be at epoch 1.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07001991 EXPECT_EQ(EpochFromSequence(client_read_seq), 1);
1992 EXPECT_EQ(EpochFromSequence(client_write_seq), 1);
1993 EXPECT_EQ(EpochFromSequence(server_read_seq), 1);
1994 EXPECT_EQ(EpochFromSequence(server_write_seq), 1);
David Benjamin0fef3052016-11-18 15:11:10 +09001995
1996 // The next record to be written should exceed the largest received.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07001997 EXPECT_GT(client_write_seq, server_read_seq);
1998 EXPECT_GT(server_write_seq, client_read_seq);
David Benjamin0fef3052016-11-18 15:11:10 +09001999 } else {
2000 // The next record to be written should equal the next to be received.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002001 EXPECT_EQ(client_write_seq, server_read_seq);
2002 EXPECT_EQ(server_write_seq, client_read_seq);
David Benjamin0fef3052016-11-18 15:11:10 +09002003 }
2004
2005 // Send a record from client to server.
Steven Valdez777a2392019-02-21 11:30:47 -05002006 uint8_t byte = 0;
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002007 EXPECT_EQ(SSL_write(client_.get(), &byte, 1), 1);
2008 EXPECT_EQ(SSL_read(server_.get(), &byte, 1), 1);
David Benjamin0fef3052016-11-18 15:11:10 +09002009
2010 // The client write and server read sequence numbers should have
2011 // incremented.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002012 EXPECT_EQ(client_write_seq + 1, SSL_get_write_sequence(client_.get()));
2013 EXPECT_EQ(server_read_seq + 1, SSL_get_read_sequence(server_.get()));
David Benjaminde942382016-02-11 12:02:01 -05002014}
2015
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002016TEST_P(SSLVersionTest, OneSidedShutdown) {
David Benjamin68f37b72016-11-18 15:14:42 +09002017 // SSL_shutdown is a no-op in DTLS.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002018 if (is_dtls()) {
2019 return;
David Benjamin686bb192016-05-10 15:15:41 -04002020 }
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002021 ASSERT_TRUE(Connect());
David Benjamin686bb192016-05-10 15:15:41 -04002022
2023 // Shut down half the connection. SSL_shutdown will return 0 to signal only
2024 // one side has shut down.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002025 ASSERT_EQ(SSL_shutdown(client_.get()), 0);
David Benjamin686bb192016-05-10 15:15:41 -04002026
2027 // Reading from the server should consume the EOF.
2028 uint8_t byte;
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002029 ASSERT_EQ(SSL_read(server_.get(), &byte, 1), 0);
2030 ASSERT_EQ(SSL_get_error(server_.get(), 0), SSL_ERROR_ZERO_RETURN);
David Benjamin686bb192016-05-10 15:15:41 -04002031
2032 // However, the server may continue to write data and then shut down the
2033 // connection.
2034 byte = 42;
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002035 ASSERT_EQ(SSL_write(server_.get(), &byte, 1), 1);
2036 ASSERT_EQ(SSL_read(client_.get(), &byte, 1), 1);
2037 ASSERT_EQ(byte, 42);
David Benjamin686bb192016-05-10 15:15:41 -04002038
2039 // The server may then shutdown the connection.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002040 EXPECT_EQ(SSL_shutdown(server_.get()), 1);
2041 EXPECT_EQ(SSL_shutdown(client_.get()), 1);
David Benjamin686bb192016-05-10 15:15:41 -04002042}
David Benjamin68f37b72016-11-18 15:14:42 +09002043
David Benjaminf0d8e222017-02-04 10:58:26 -05002044TEST(SSLTest, SessionDuplication) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002045 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLS_method()));
2046 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(TLS_method()));
David Benjaminf0d8e222017-02-04 10:58:26 -05002047 ASSERT_TRUE(client_ctx);
2048 ASSERT_TRUE(server_ctx);
Steven Valdez87eab492016-06-27 16:34:59 -04002049
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002050 bssl::UniquePtr<X509> cert = GetTestCertificate();
2051 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
David Benjaminf0d8e222017-02-04 10:58:26 -05002052 ASSERT_TRUE(cert);
2053 ASSERT_TRUE(key);
2054 ASSERT_TRUE(SSL_CTX_use_certificate(server_ctx.get(), cert.get()));
2055 ASSERT_TRUE(SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()));
Steven Valdez87eab492016-06-27 16:34:59 -04002056
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002057 bssl::UniquePtr<SSL> client, server;
David Benjaminf0d8e222017-02-04 10:58:26 -05002058 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx.get(),
David Benjamina8614602017-09-06 15:40:19 -04002059 server_ctx.get()));
Steven Valdez87eab492016-06-27 16:34:59 -04002060
2061 SSL_SESSION *session0 = SSL_get_session(client.get());
David Benjamin31b0c9b2017-07-20 14:49:15 -04002062 bssl::UniquePtr<SSL_SESSION> session1 =
2063 bssl::SSL_SESSION_dup(session0, SSL_SESSION_DUP_ALL);
David Benjaminf0d8e222017-02-04 10:58:26 -05002064 ASSERT_TRUE(session1);
David Benjamin4501bd52016-08-01 13:39:41 -04002065
David Benjamina3a71e92018-06-29 13:24:45 -04002066 session1->not_resumable = false;
Steven Valdez84b5c002016-08-25 16:30:58 -04002067
Steven Valdez87eab492016-06-27 16:34:59 -04002068 uint8_t *s0_bytes, *s1_bytes;
2069 size_t s0_len, s1_len;
2070
David Benjaminf0d8e222017-02-04 10:58:26 -05002071 ASSERT_TRUE(SSL_SESSION_to_bytes(session0, &s0_bytes, &s0_len));
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002072 bssl::UniquePtr<uint8_t> free_s0(s0_bytes);
Steven Valdez87eab492016-06-27 16:34:59 -04002073
David Benjaminf0d8e222017-02-04 10:58:26 -05002074 ASSERT_TRUE(SSL_SESSION_to_bytes(session1.get(), &s1_bytes, &s1_len));
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002075 bssl::UniquePtr<uint8_t> free_s1(s1_bytes);
Steven Valdez87eab492016-06-27 16:34:59 -04002076
David Benjamin7d7554b2017-02-04 11:48:59 -05002077 EXPECT_EQ(Bytes(s0_bytes, s0_len), Bytes(s1_bytes, s1_len));
Steven Valdez87eab492016-06-27 16:34:59 -04002078}
David Benjamin686bb192016-05-10 15:15:41 -04002079
David Benjaminf0d8e222017-02-04 10:58:26 -05002080static void ExpectFDs(const SSL *ssl, int rfd, int wfd) {
David Benjaminca743582017-06-15 17:51:35 -04002081 EXPECT_EQ(rfd, SSL_get_fd(ssl));
David Benjaminf0d8e222017-02-04 10:58:26 -05002082 EXPECT_EQ(rfd, SSL_get_rfd(ssl));
2083 EXPECT_EQ(wfd, SSL_get_wfd(ssl));
David Benjamin5c0fb882016-06-14 14:03:51 -04002084
2085 // The wrapper BIOs are always equal when fds are equal, even if set
2086 // individually.
David Benjaminf0d8e222017-02-04 10:58:26 -05002087 if (rfd == wfd) {
2088 EXPECT_EQ(SSL_get_rbio(ssl), SSL_get_wbio(ssl));
David Benjamin5c0fb882016-06-14 14:03:51 -04002089 }
David Benjamin5c0fb882016-06-14 14:03:51 -04002090}
2091
David Benjaminf0d8e222017-02-04 10:58:26 -05002092TEST(SSLTest, SetFD) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002093 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
David Benjaminf0d8e222017-02-04 10:58:26 -05002094 ASSERT_TRUE(ctx);
David Benjamin5c0fb882016-06-14 14:03:51 -04002095
2096 // Test setting different read and write FDs.
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002097 bssl::UniquePtr<SSL> ssl(SSL_new(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05002098 ASSERT_TRUE(ssl);
2099 EXPECT_TRUE(SSL_set_rfd(ssl.get(), 1));
2100 EXPECT_TRUE(SSL_set_wfd(ssl.get(), 2));
2101 ExpectFDs(ssl.get(), 1, 2);
David Benjamin5c0fb882016-06-14 14:03:51 -04002102
2103 // Test setting the same FD.
2104 ssl.reset(SSL_new(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05002105 ASSERT_TRUE(ssl);
2106 EXPECT_TRUE(SSL_set_fd(ssl.get(), 1));
2107 ExpectFDs(ssl.get(), 1, 1);
David Benjamin5c0fb882016-06-14 14:03:51 -04002108
2109 // Test setting the same FD one side at a time.
2110 ssl.reset(SSL_new(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05002111 ASSERT_TRUE(ssl);
2112 EXPECT_TRUE(SSL_set_rfd(ssl.get(), 1));
2113 EXPECT_TRUE(SSL_set_wfd(ssl.get(), 1));
2114 ExpectFDs(ssl.get(), 1, 1);
David Benjamin5c0fb882016-06-14 14:03:51 -04002115
2116 // Test setting the same FD in the other order.
2117 ssl.reset(SSL_new(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05002118 ASSERT_TRUE(ssl);
2119 EXPECT_TRUE(SSL_set_wfd(ssl.get(), 1));
2120 EXPECT_TRUE(SSL_set_rfd(ssl.get(), 1));
2121 ExpectFDs(ssl.get(), 1, 1);
David Benjamin5c0fb882016-06-14 14:03:51 -04002122
David Benjamin5c0fb882016-06-14 14:03:51 -04002123 // Test changing the read FD partway through.
2124 ssl.reset(SSL_new(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05002125 ASSERT_TRUE(ssl);
2126 EXPECT_TRUE(SSL_set_fd(ssl.get(), 1));
2127 EXPECT_TRUE(SSL_set_rfd(ssl.get(), 2));
2128 ExpectFDs(ssl.get(), 2, 1);
David Benjamin5c0fb882016-06-14 14:03:51 -04002129
2130 // Test changing the write FD partway through.
2131 ssl.reset(SSL_new(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05002132 ASSERT_TRUE(ssl);
2133 EXPECT_TRUE(SSL_set_fd(ssl.get(), 1));
2134 EXPECT_TRUE(SSL_set_wfd(ssl.get(), 2));
2135 ExpectFDs(ssl.get(), 1, 2);
David Benjamin5c0fb882016-06-14 14:03:51 -04002136
2137 // Test a no-op change to the read FD partway through.
2138 ssl.reset(SSL_new(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05002139 ASSERT_TRUE(ssl);
2140 EXPECT_TRUE(SSL_set_fd(ssl.get(), 1));
2141 EXPECT_TRUE(SSL_set_rfd(ssl.get(), 1));
2142 ExpectFDs(ssl.get(), 1, 1);
David Benjamin5c0fb882016-06-14 14:03:51 -04002143
2144 // Test a no-op change to the write FD partway through.
2145 ssl.reset(SSL_new(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05002146 ASSERT_TRUE(ssl);
2147 EXPECT_TRUE(SSL_set_fd(ssl.get(), 1));
2148 EXPECT_TRUE(SSL_set_wfd(ssl.get(), 1));
2149 ExpectFDs(ssl.get(), 1, 1);
David Benjamin5c0fb882016-06-14 14:03:51 -04002150
2151 // ASan builds will implicitly test that the internal |BIO| reference-counting
2152 // is correct.
David Benjamin5c0fb882016-06-14 14:03:51 -04002153}
2154
David Benjaminf0d8e222017-02-04 10:58:26 -05002155TEST(SSLTest, SetBIO) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002156 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
David Benjaminf0d8e222017-02-04 10:58:26 -05002157 ASSERT_TRUE(ctx);
David Benjamin4501bd52016-08-01 13:39:41 -04002158
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002159 bssl::UniquePtr<SSL> ssl(SSL_new(ctx.get()));
2160 bssl::UniquePtr<BIO> bio1(BIO_new(BIO_s_mem())), bio2(BIO_new(BIO_s_mem())),
David Benjamin4501bd52016-08-01 13:39:41 -04002161 bio3(BIO_new(BIO_s_mem()));
David Benjaminf0d8e222017-02-04 10:58:26 -05002162 ASSERT_TRUE(ssl);
2163 ASSERT_TRUE(bio1);
2164 ASSERT_TRUE(bio2);
2165 ASSERT_TRUE(bio3);
David Benjamin4501bd52016-08-01 13:39:41 -04002166
2167 // SSL_set_bio takes one reference when the parameters are the same.
2168 BIO_up_ref(bio1.get());
2169 SSL_set_bio(ssl.get(), bio1.get(), bio1.get());
2170
2171 // Repeating the call does nothing.
2172 SSL_set_bio(ssl.get(), bio1.get(), bio1.get());
2173
2174 // It takes one reference each when the parameters are different.
2175 BIO_up_ref(bio2.get());
2176 BIO_up_ref(bio3.get());
2177 SSL_set_bio(ssl.get(), bio2.get(), bio3.get());
2178
2179 // Repeating the call does nothing.
2180 SSL_set_bio(ssl.get(), bio2.get(), bio3.get());
2181
2182 // It takes one reference when changing only wbio.
2183 BIO_up_ref(bio1.get());
2184 SSL_set_bio(ssl.get(), bio2.get(), bio1.get());
2185
2186 // It takes one reference when changing only rbio and the two are different.
2187 BIO_up_ref(bio3.get());
2188 SSL_set_bio(ssl.get(), bio3.get(), bio1.get());
2189
2190 // If setting wbio to rbio, it takes no additional references.
2191 SSL_set_bio(ssl.get(), bio3.get(), bio3.get());
2192
2193 // From there, wbio may be switched to something else.
2194 BIO_up_ref(bio1.get());
2195 SSL_set_bio(ssl.get(), bio3.get(), bio1.get());
2196
2197 // If setting rbio to wbio, it takes no additional references.
2198 SSL_set_bio(ssl.get(), bio1.get(), bio1.get());
2199
2200 // From there, rbio may be switched to something else, but, for historical
2201 // reasons, it takes a reference to both parameters.
2202 BIO_up_ref(bio1.get());
2203 BIO_up_ref(bio2.get());
2204 SSL_set_bio(ssl.get(), bio2.get(), bio1.get());
2205
2206 // ASAN builds will implicitly test that the internal |BIO| reference-counting
2207 // is correct.
David Benjamin4501bd52016-08-01 13:39:41 -04002208}
2209
David Benjamin25490f22016-07-14 00:22:54 -04002210static int VerifySucceed(X509_STORE_CTX *store_ctx, void *arg) { return 1; }
2211
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002212TEST_P(SSLVersionTest, GetPeerCertificate) {
2213 ASSERT_TRUE(UseCertAndKey(client_ctx_.get()));
David Benjaminadd5e522016-07-14 00:33:24 -04002214
David Benjamin0fef3052016-11-18 15:11:10 +09002215 // Configure both client and server to accept any certificate.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002216 SSL_CTX_set_verify(client_ctx_.get(),
2217 SSL_VERIFY_PEER | SSL_VERIFY_FAIL_IF_NO_PEER_CERT,
2218 nullptr);
2219 SSL_CTX_set_cert_verify_callback(client_ctx_.get(), VerifySucceed, NULL);
2220 SSL_CTX_set_verify(server_ctx_.get(),
2221 SSL_VERIFY_PEER | SSL_VERIFY_FAIL_IF_NO_PEER_CERT,
2222 nullptr);
2223 SSL_CTX_set_cert_verify_callback(server_ctx_.get(), VerifySucceed, NULL);
David Benjaminadd5e522016-07-14 00:33:24 -04002224
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002225 ASSERT_TRUE(Connect());
David Benjaminadd5e522016-07-14 00:33:24 -04002226
David Benjamin0fef3052016-11-18 15:11:10 +09002227 // Client and server should both see the leaf certificate.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002228 bssl::UniquePtr<X509> peer(SSL_get_peer_certificate(server_.get()));
2229 ASSERT_TRUE(peer);
2230 ASSERT_EQ(X509_cmp(cert_.get(), peer.get()), 0);
David Benjaminadd5e522016-07-14 00:33:24 -04002231
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002232 peer.reset(SSL_get_peer_certificate(client_.get()));
2233 ASSERT_TRUE(peer);
2234 ASSERT_EQ(X509_cmp(cert_.get(), peer.get()), 0);
David Benjaminadd5e522016-07-14 00:33:24 -04002235
David Benjamine664a532017-07-20 20:19:36 -04002236 // However, for historical reasons, the X509 chain includes the leaf on the
David Benjamin0fef3052016-11-18 15:11:10 +09002237 // client, but does not on the server.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002238 EXPECT_EQ(sk_X509_num(SSL_get_peer_cert_chain(client_.get())), 1u);
2239 EXPECT_EQ(sk_CRYPTO_BUFFER_num(SSL_get0_peer_certificates(client_.get())),
2240 1u);
David Benjaminadd5e522016-07-14 00:33:24 -04002241
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002242 EXPECT_EQ(sk_X509_num(SSL_get_peer_cert_chain(server_.get())), 0u);
2243 EXPECT_EQ(sk_CRYPTO_BUFFER_num(SSL_get0_peer_certificates(server_.get())),
2244 1u);
David Benjaminadd5e522016-07-14 00:33:24 -04002245}
2246
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002247TEST_P(SSLVersionTest, NoPeerCertificate) {
2248 SSL_CTX_set_verify(server_ctx_.get(), SSL_VERIFY_PEER, nullptr);
2249 SSL_CTX_set_cert_verify_callback(server_ctx_.get(), VerifySucceed, NULL);
2250 SSL_CTX_set_cert_verify_callback(client_ctx_.get(), VerifySucceed, NULL);
David Benjamine664a532017-07-20 20:19:36 -04002251
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002252 ASSERT_TRUE(Connect());
David Benjamine664a532017-07-20 20:19:36 -04002253
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002254 // Server should not see a peer certificate.
2255 bssl::UniquePtr<X509> peer(SSL_get_peer_certificate(server_.get()));
2256 ASSERT_FALSE(peer);
2257 ASSERT_FALSE(SSL_get0_peer_certificates(server_.get()));
David Benjamine664a532017-07-20 20:19:36 -04002258}
2259
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002260TEST_P(SSLVersionTest, RetainOnlySHA256OfCerts) {
David Benjamin25490f22016-07-14 00:22:54 -04002261 uint8_t *cert_der = NULL;
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002262 int cert_der_len = i2d_X509(cert_.get(), &cert_der);
2263 ASSERT_GE(cert_der_len, 0);
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002264 bssl::UniquePtr<uint8_t> free_cert_der(cert_der);
David Benjamin25490f22016-07-14 00:22:54 -04002265
2266 uint8_t cert_sha256[SHA256_DIGEST_LENGTH];
2267 SHA256(cert_der, cert_der_len, cert_sha256);
2268
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002269 ASSERT_TRUE(UseCertAndKey(client_ctx_.get()));
2270
David Benjamin0fef3052016-11-18 15:11:10 +09002271 // Configure both client and server to accept any certificate, but the
2272 // server must retain only the SHA-256 of the peer.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002273 SSL_CTX_set_verify(client_ctx_.get(),
2274 SSL_VERIFY_PEER | SSL_VERIFY_FAIL_IF_NO_PEER_CERT,
2275 nullptr);
2276 SSL_CTX_set_verify(server_ctx_.get(),
2277 SSL_VERIFY_PEER | SSL_VERIFY_FAIL_IF_NO_PEER_CERT,
2278 nullptr);
2279 SSL_CTX_set_cert_verify_callback(client_ctx_.get(), VerifySucceed, NULL);
2280 SSL_CTX_set_cert_verify_callback(server_ctx_.get(), VerifySucceed, NULL);
2281 SSL_CTX_set_retain_only_sha256_of_client_certs(server_ctx_.get(), 1);
David Benjamin25490f22016-07-14 00:22:54 -04002282
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002283 ASSERT_TRUE(Connect());
David Benjamin25490f22016-07-14 00:22:54 -04002284
David Benjamin0fef3052016-11-18 15:11:10 +09002285 // The peer certificate has been dropped.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002286 bssl::UniquePtr<X509> peer(SSL_get_peer_certificate(server_.get()));
2287 EXPECT_FALSE(peer);
David Benjamin25490f22016-07-14 00:22:54 -04002288
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002289 SSL_SESSION *session = SSL_get_session(server_.get());
David Benjamin02de7bd2018-05-08 18:13:54 -04002290 EXPECT_TRUE(SSL_SESSION_has_peer_sha256(session));
David Benjamin25490f22016-07-14 00:22:54 -04002291
David Benjamin02de7bd2018-05-08 18:13:54 -04002292 const uint8_t *peer_sha256;
2293 size_t peer_sha256_len;
2294 SSL_SESSION_get0_peer_sha256(session, &peer_sha256, &peer_sha256_len);
2295 EXPECT_EQ(Bytes(cert_sha256), Bytes(peer_sha256, peer_sha256_len));
David Benjamin25490f22016-07-14 00:22:54 -04002296}
2297
David Benjamin737d2df2017-09-25 15:05:19 -04002298// Tests that our ClientHellos do not change unexpectedly. These are purely
2299// change detection tests. If they fail as part of an intentional ClientHello
2300// change, update the test vector.
2301TEST(SSLTest, ClientHello) {
2302 struct {
2303 uint16_t max_version;
2304 std::vector<uint8_t> expected;
2305 } kTests[] = {
David Benjamin737d2df2017-09-25 15:05:19 -04002306 {TLS1_VERSION,
2307 {0x16, 0x03, 0x01, 0x00, 0x5a, 0x01, 0x00, 0x00, 0x56, 0x03, 0x01, 0x00,
2308 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
2309 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
2310 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0e, 0xc0, 0x09,
2311 0xc0, 0x13, 0xc0, 0x0a, 0xc0, 0x14, 0x00, 0x2f, 0x00, 0x35, 0x00, 0x0a,
Adam Langleyd6680952018-08-23 08:01:23 -07002312 0x01, 0x00, 0x00, 0x1f, 0x00, 0x17, 0x00, 0x00, 0xff, 0x01, 0x00, 0x01,
2313 0x00, 0x00, 0x0a, 0x00, 0x08, 0x00, 0x06, 0x00, 0x1d, 0x00, 0x17, 0x00,
2314 0x18, 0x00, 0x0b, 0x00, 0x02, 0x01, 0x00, 0x00, 0x23, 0x00, 0x00}},
David Benjamin737d2df2017-09-25 15:05:19 -04002315 {TLS1_1_VERSION,
2316 {0x16, 0x03, 0x01, 0x00, 0x5a, 0x01, 0x00, 0x00, 0x56, 0x03, 0x02, 0x00,
2317 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
2318 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
2319 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0e, 0xc0, 0x09,
2320 0xc0, 0x13, 0xc0, 0x0a, 0xc0, 0x14, 0x00, 0x2f, 0x00, 0x35, 0x00, 0x0a,
Adam Langleyd6680952018-08-23 08:01:23 -07002321 0x01, 0x00, 0x00, 0x1f, 0x00, 0x17, 0x00, 0x00, 0xff, 0x01, 0x00, 0x01,
2322 0x00, 0x00, 0x0a, 0x00, 0x08, 0x00, 0x06, 0x00, 0x1d, 0x00, 0x17, 0x00,
2323 0x18, 0x00, 0x0b, 0x00, 0x02, 0x01, 0x00, 0x00, 0x23, 0x00, 0x00}},
David Benjamin737d2df2017-09-25 15:05:19 -04002324 {TLS1_2_VERSION,
David Benjamin6e678ee2018-04-16 19:54:42 -04002325 {0x16, 0x03, 0x01, 0x00, 0x82, 0x01, 0x00, 0x00, 0x7e, 0x03, 0x03, 0x00,
David Benjamin737d2df2017-09-25 15:05:19 -04002326 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
2327 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
David Benjamin6e678ee2018-04-16 19:54:42 -04002328 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1e, 0xcc, 0xa9,
David Benjamin737d2df2017-09-25 15:05:19 -04002329 0xcc, 0xa8, 0xc0, 0x2b, 0xc0, 0x2f, 0xc0, 0x2c, 0xc0, 0x30, 0xc0, 0x09,
David Benjamin6e678ee2018-04-16 19:54:42 -04002330 0xc0, 0x13, 0xc0, 0x0a, 0xc0, 0x14, 0x00, 0x9c, 0x00, 0x9d, 0x00, 0x2f,
Adam Langleyd6680952018-08-23 08:01:23 -07002331 0x00, 0x35, 0x00, 0x0a, 0x01, 0x00, 0x00, 0x37, 0x00, 0x17, 0x00, 0x00,
2332 0xff, 0x01, 0x00, 0x01, 0x00, 0x00, 0x0a, 0x00, 0x08, 0x00, 0x06, 0x00,
2333 0x1d, 0x00, 0x17, 0x00, 0x18, 0x00, 0x0b, 0x00, 0x02, 0x01, 0x00, 0x00,
2334 0x23, 0x00, 0x00, 0x00, 0x0d, 0x00, 0x14, 0x00, 0x12, 0x04, 0x03, 0x08,
2335 0x04, 0x04, 0x01, 0x05, 0x03, 0x08, 0x05, 0x05, 0x01, 0x08, 0x06, 0x06,
2336 0x01, 0x02, 0x01}},
David Benjamin737d2df2017-09-25 15:05:19 -04002337 // TODO(davidben): Add a change detector for TLS 1.3 once the spec and our
2338 // implementation has settled enough that it won't change.
David Benjaminafc64de2016-07-19 17:12:41 +02002339 };
David Benjamin737d2df2017-09-25 15:05:19 -04002340
2341 for (const auto &t : kTests) {
2342 SCOPED_TRACE(t.max_version);
2343
2344 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
2345 ASSERT_TRUE(ctx);
2346 // Our default cipher list varies by CPU capabilities, so manually place the
2347 // ChaCha20 ciphers in front.
2348 const char *cipher_list = "CHACHA20:ALL";
David Benjamin737d2df2017-09-25 15:05:19 -04002349 ASSERT_TRUE(SSL_CTX_set_max_proto_version(ctx.get(), t.max_version));
2350 ASSERT_TRUE(SSL_CTX_set_strict_cipher_list(ctx.get(), cipher_list));
2351
2352 bssl::UniquePtr<SSL> ssl(SSL_new(ctx.get()));
2353 ASSERT_TRUE(ssl);
2354 std::vector<uint8_t> client_hello;
2355 ASSERT_TRUE(GetClientHello(ssl.get(), &client_hello));
2356
2357 // Zero the client_random.
2358 constexpr size_t kRandomOffset = 1 + 2 + 2 + // record header
2359 1 + 3 + // handshake message header
2360 2; // client_version
2361 ASSERT_GE(client_hello.size(), kRandomOffset + SSL3_RANDOM_SIZE);
2362 OPENSSL_memset(client_hello.data() + kRandomOffset, 0, SSL3_RANDOM_SIZE);
2363
2364 if (client_hello != t.expected) {
2365 ADD_FAILURE() << "ClientHellos did not match.";
2366 // Print the value manually so it is easier to update the test vector.
2367 for (size_t i = 0; i < client_hello.size(); i += 12) {
2368 printf(" %c", i == 0 ? '{' : ' ');
2369 for (size_t j = i; j < client_hello.size() && j < i + 12; j++) {
2370 if (j > i) {
2371 printf(" ");
2372 }
2373 printf("0x%02x", client_hello[j]);
2374 if (j < client_hello.size() - 1) {
2375 printf(",");
2376 }
2377 }
2378 if (i + 12 >= client_hello.size()) {
Adam Langleyd6680952018-08-23 08:01:23 -07002379 printf("}},");
David Benjamin737d2df2017-09-25 15:05:19 -04002380 }
2381 printf("\n");
2382 }
2383 }
David Benjaminafc64de2016-07-19 17:12:41 +02002384 }
David Benjaminafc64de2016-07-19 17:12:41 +02002385}
2386
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002387static bssl::UniquePtr<SSL_SESSION> g_last_session;
David Benjamina20e5352016-08-02 19:09:41 -04002388
2389static int SaveLastSession(SSL *ssl, SSL_SESSION *session) {
2390 // Save the most recent session.
2391 g_last_session.reset(session);
2392 return 1;
2393}
2394
David Benjamina8614602017-09-06 15:40:19 -04002395static bssl::UniquePtr<SSL_SESSION> CreateClientSession(
2396 SSL_CTX *client_ctx, SSL_CTX *server_ctx,
2397 const ClientConfig &config = ClientConfig()) {
David Benjamina20e5352016-08-02 19:09:41 -04002398 g_last_session = nullptr;
2399 SSL_CTX_sess_set_new_cb(client_ctx, SaveLastSession);
2400
2401 // Connect client and server to get a session.
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002402 bssl::UniquePtr<SSL> client, server;
David Benjamina20e5352016-08-02 19:09:41 -04002403 if (!ConnectClientAndServer(&client, &server, client_ctx, server_ctx,
Steven Valdez777a2392019-02-21 11:30:47 -05002404 config) ||
2405 !FlushNewSessionTickets(client.get(), server.get())) {
David Benjamina20e5352016-08-02 19:09:41 -04002406 fprintf(stderr, "Failed to connect client and server.\n");
2407 return nullptr;
2408 }
2409
David Benjamina20e5352016-08-02 19:09:41 -04002410 SSL_CTX_sess_set_new_cb(client_ctx, nullptr);
2411
2412 if (!g_last_session) {
2413 fprintf(stderr, "Client did not receive a session.\n");
2414 return nullptr;
2415 }
2416 return std::move(g_last_session);
2417}
2418
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002419static void ExpectSessionReused(SSL_CTX *client_ctx, SSL_CTX *server_ctx,
2420 SSL_SESSION *session, bool want_reused) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002421 bssl::UniquePtr<SSL> client, server;
David Benjamina8614602017-09-06 15:40:19 -04002422 ClientConfig config;
2423 config.session = session;
2424 EXPECT_TRUE(
2425 ConnectClientAndServer(&client, &server, client_ctx, server_ctx, config));
David Benjamina20e5352016-08-02 19:09:41 -04002426
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002427 EXPECT_EQ(SSL_session_reused(client.get()), SSL_session_reused(server.get()));
David Benjamina20e5352016-08-02 19:09:41 -04002428
2429 bool was_reused = !!SSL_session_reused(client.get());
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002430 EXPECT_EQ(was_reused, want_reused);
David Benjamina20e5352016-08-02 19:09:41 -04002431}
2432
David Benjamin3c51d9b2016-11-01 17:50:42 -04002433static bssl::UniquePtr<SSL_SESSION> ExpectSessionRenewed(SSL_CTX *client_ctx,
2434 SSL_CTX *server_ctx,
2435 SSL_SESSION *session) {
2436 g_last_session = nullptr;
2437 SSL_CTX_sess_set_new_cb(client_ctx, SaveLastSession);
2438
2439 bssl::UniquePtr<SSL> client, server;
David Benjamina8614602017-09-06 15:40:19 -04002440 ClientConfig config;
2441 config.session = session;
2442 if (!ConnectClientAndServer(&client, &server, client_ctx, server_ctx,
Steven Valdez777a2392019-02-21 11:30:47 -05002443 config) ||
2444 !FlushNewSessionTickets(client.get(), server.get())) {
David Benjamin3c51d9b2016-11-01 17:50:42 -04002445 fprintf(stderr, "Failed to connect client and server.\n");
2446 return nullptr;
2447 }
2448
2449 if (SSL_session_reused(client.get()) != SSL_session_reused(server.get())) {
2450 fprintf(stderr, "Client and server were inconsistent.\n");
2451 return nullptr;
2452 }
2453
2454 if (!SSL_session_reused(client.get())) {
2455 fprintf(stderr, "Session was not reused.\n");
2456 return nullptr;
2457 }
2458
David Benjamin3c51d9b2016-11-01 17:50:42 -04002459 SSL_CTX_sess_set_new_cb(client_ctx, nullptr);
2460
2461 if (!g_last_session) {
2462 fprintf(stderr, "Client did not receive a renewed session.\n");
2463 return nullptr;
2464 }
2465 return std::move(g_last_session);
2466}
2467
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002468static void ExpectTicketKeyChanged(SSL_CTX *ctx, uint8_t *inout_key,
Martin Kreichgauer72912d22017-08-04 12:06:43 -07002469 bool changed) {
2470 uint8_t new_key[kTicketKeyLen];
David Benjaminc11ea9422017-08-29 16:33:21 -04002471 // May return 0, 1 or 48.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002472 ASSERT_EQ(SSL_CTX_get_tlsext_ticket_keys(ctx, new_key, kTicketKeyLen), 1);
2473 if (changed) {
2474 ASSERT_NE(Bytes(inout_key, kTicketKeyLen), Bytes(new_key));
2475 } else {
2476 ASSERT_EQ(Bytes(inout_key, kTicketKeyLen), Bytes(new_key));
Martin Kreichgauer72912d22017-08-04 12:06:43 -07002477 }
2478 OPENSSL_memcpy(inout_key, new_key, kTicketKeyLen);
Martin Kreichgauer72912d22017-08-04 12:06:43 -07002479}
2480
David Benjamina933c382016-10-28 00:10:03 -04002481static int SwitchSessionIDContextSNI(SSL *ssl, int *out_alert, void *arg) {
2482 static const uint8_t kContext[] = {3};
2483
2484 if (!SSL_set_session_id_context(ssl, kContext, sizeof(kContext))) {
2485 return SSL_TLSEXT_ERR_ALERT_FATAL;
2486 }
2487
2488 return SSL_TLSEXT_ERR_OK;
2489}
2490
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002491TEST_P(SSLVersionTest, SessionIDContext) {
David Benjamina20e5352016-08-02 19:09:41 -04002492 static const uint8_t kContext1[] = {1};
2493 static const uint8_t kContext2[] = {2};
2494
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002495 ASSERT_TRUE(SSL_CTX_set_session_id_context(server_ctx_.get(), kContext1,
2496 sizeof(kContext1)));
David Benjamina20e5352016-08-02 19:09:41 -04002497
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002498 SSL_CTX_set_session_cache_mode(client_ctx_.get(), SSL_SESS_CACHE_BOTH);
2499 SSL_CTX_set_session_cache_mode(server_ctx_.get(), SSL_SESS_CACHE_BOTH);
David Benjamina20e5352016-08-02 19:09:41 -04002500
David Benjamin0fef3052016-11-18 15:11:10 +09002501 bssl::UniquePtr<SSL_SESSION> session =
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002502 CreateClientSession(client_ctx_.get(), server_ctx_.get());
2503 ASSERT_TRUE(session);
David Benjamina20e5352016-08-02 19:09:41 -04002504
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002505 TRACED_CALL(ExpectSessionReused(client_ctx_.get(), server_ctx_.get(),
2506 session.get(),
2507 true /* expect session reused */));
David Benjamina20e5352016-08-02 19:09:41 -04002508
David Benjamin0fef3052016-11-18 15:11:10 +09002509 // Change the session ID context.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002510 ASSERT_TRUE(SSL_CTX_set_session_id_context(server_ctx_.get(), kContext2,
2511 sizeof(kContext2)));
David Benjamina20e5352016-08-02 19:09:41 -04002512
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002513 TRACED_CALL(ExpectSessionReused(client_ctx_.get(), server_ctx_.get(),
2514 session.get(),
2515 false /* expect session not reused */));
David Benjamina933c382016-10-28 00:10:03 -04002516
David Benjamin0fef3052016-11-18 15:11:10 +09002517 // Change the session ID context back and install an SNI callback to switch
2518 // it.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002519 ASSERT_TRUE(SSL_CTX_set_session_id_context(server_ctx_.get(), kContext1,
2520 sizeof(kContext1)));
David Benjamina933c382016-10-28 00:10:03 -04002521
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002522 SSL_CTX_set_tlsext_servername_callback(server_ctx_.get(),
David Benjamin0fef3052016-11-18 15:11:10 +09002523 SwitchSessionIDContextSNI);
David Benjamina933c382016-10-28 00:10:03 -04002524
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002525 TRACED_CALL(ExpectSessionReused(client_ctx_.get(), server_ctx_.get(),
2526 session.get(),
2527 false /* expect session not reused */));
David Benjamina933c382016-10-28 00:10:03 -04002528
David Benjamin0fef3052016-11-18 15:11:10 +09002529 // Switch the session ID context with the early callback instead.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002530 SSL_CTX_set_tlsext_servername_callback(server_ctx_.get(), nullptr);
Alessandro Ghedini57e81e62017-03-14 23:36:00 +00002531 SSL_CTX_set_select_certificate_cb(
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002532 server_ctx_.get(),
Alessandro Ghedini57e81e62017-03-14 23:36:00 +00002533 [](const SSL_CLIENT_HELLO *client_hello) -> ssl_select_cert_result_t {
2534 static const uint8_t kContext[] = {3};
2535
2536 if (!SSL_set_session_id_context(client_hello->ssl, kContext,
2537 sizeof(kContext))) {
2538 return ssl_select_cert_error;
2539 }
2540
2541 return ssl_select_cert_success;
2542 });
David Benjamina933c382016-10-28 00:10:03 -04002543
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002544 TRACED_CALL(ExpectSessionReused(client_ctx_.get(), server_ctx_.get(),
2545 session.get(),
2546 false /* expect session not reused */));
David Benjamina20e5352016-08-02 19:09:41 -04002547}
2548
David Benjamin721e8b72016-08-03 13:13:17 -04002549static timeval g_current_time;
2550
2551static void CurrentTimeCallback(const SSL *ssl, timeval *out_clock) {
2552 *out_clock = g_current_time;
2553}
2554
David Benjamin17b30832017-01-28 14:00:32 -05002555static void FrozenTimeCallback(const SSL *ssl, timeval *out_clock) {
2556 out_clock->tv_sec = 1000;
2557 out_clock->tv_usec = 0;
2558}
2559
David Benjamin3c51d9b2016-11-01 17:50:42 -04002560static int RenewTicketCallback(SSL *ssl, uint8_t *key_name, uint8_t *iv,
2561 EVP_CIPHER_CTX *ctx, HMAC_CTX *hmac_ctx,
2562 int encrypt) {
2563 static const uint8_t kZeros[16] = {0};
2564
2565 if (encrypt) {
David Benjamin17cf2cb2016-12-13 01:07:13 -05002566 OPENSSL_memcpy(key_name, kZeros, sizeof(kZeros));
David Benjamin3c51d9b2016-11-01 17:50:42 -04002567 RAND_bytes(iv, 16);
David Benjamin17cf2cb2016-12-13 01:07:13 -05002568 } else if (OPENSSL_memcmp(key_name, kZeros, 16) != 0) {
David Benjamin3c51d9b2016-11-01 17:50:42 -04002569 return 0;
2570 }
2571
2572 if (!HMAC_Init_ex(hmac_ctx, kZeros, sizeof(kZeros), EVP_sha256(), NULL) ||
2573 !EVP_CipherInit_ex(ctx, EVP_aes_128_cbc(), NULL, kZeros, iv, encrypt)) {
2574 return -1;
2575 }
2576
2577 // Returning two from the callback in decrypt mode renews the
2578 // session in TLS 1.2 and below.
2579 return encrypt ? 1 : 2;
2580}
2581
David Benjamin123db572016-11-03 16:59:25 -04002582static bool GetServerTicketTime(long *out, const SSL_SESSION *session) {
David Benjaminaaef8332018-06-29 16:45:49 -04002583 const uint8_t *ticket;
2584 size_t ticket_len;
2585 SSL_SESSION_get0_ticket(session, &ticket, &ticket_len);
2586 if (ticket_len < 16 + 16 + SHA256_DIGEST_LENGTH) {
David Benjamin123db572016-11-03 16:59:25 -04002587 return false;
2588 }
2589
David Benjaminaaef8332018-06-29 16:45:49 -04002590 const uint8_t *ciphertext = ticket + 16 + 16;
2591 size_t len = ticket_len - 16 - 16 - SHA256_DIGEST_LENGTH;
David Benjamin123db572016-11-03 16:59:25 -04002592 std::unique_ptr<uint8_t[]> plaintext(new uint8_t[len]);
2593
David Benjamin9b63f292016-11-15 00:44:05 -05002594#if defined(BORINGSSL_UNSAFE_FUZZER_MODE)
2595 // Fuzzer-mode tickets are unencrypted.
David Benjamin17cf2cb2016-12-13 01:07:13 -05002596 OPENSSL_memcpy(plaintext.get(), ciphertext, len);
David Benjamin9b63f292016-11-15 00:44:05 -05002597#else
2598 static const uint8_t kZeros[16] = {0};
David Benjaminaaef8332018-06-29 16:45:49 -04002599 const uint8_t *iv = ticket + 16;
David Benjamin123db572016-11-03 16:59:25 -04002600 bssl::ScopedEVP_CIPHER_CTX ctx;
2601 int len1, len2;
2602 if (!EVP_DecryptInit_ex(ctx.get(), EVP_aes_128_cbc(), nullptr, kZeros, iv) ||
2603 !EVP_DecryptUpdate(ctx.get(), plaintext.get(), &len1, ciphertext, len) ||
2604 !EVP_DecryptFinal_ex(ctx.get(), plaintext.get() + len1, &len2)) {
2605 return false;
2606 }
2607
2608 len = static_cast<size_t>(len1 + len2);
David Benjamin9b63f292016-11-15 00:44:05 -05002609#endif
David Benjamin123db572016-11-03 16:59:25 -04002610
Adam Langley46db7af2017-02-01 15:49:37 -08002611 bssl::UniquePtr<SSL_CTX> ssl_ctx(SSL_CTX_new(TLS_method()));
2612 if (!ssl_ctx) {
2613 return false;
2614 }
David Benjamin123db572016-11-03 16:59:25 -04002615 bssl::UniquePtr<SSL_SESSION> server_session(
Adam Langley46db7af2017-02-01 15:49:37 -08002616 SSL_SESSION_from_bytes(plaintext.get(), len, ssl_ctx.get()));
David Benjamin123db572016-11-03 16:59:25 -04002617 if (!server_session) {
2618 return false;
2619 }
2620
David Benjaminaaef8332018-06-29 16:45:49 -04002621 *out = SSL_SESSION_get_time(server_session.get());
David Benjamin123db572016-11-03 16:59:25 -04002622 return true;
2623}
2624
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002625TEST_P(SSLVersionTest, SessionTimeout) {
2626 for (bool server_test : {false, true}) {
2627 SCOPED_TRACE(server_test);
David Benjamin721e8b72016-08-03 13:13:17 -04002628
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002629 ResetContexts();
2630 SSL_CTX_set_session_cache_mode(client_ctx_.get(), SSL_SESS_CACHE_BOTH);
2631 SSL_CTX_set_session_cache_mode(server_ctx_.get(), SSL_SESS_CACHE_BOTH);
2632
David Benjamin17b30832017-01-28 14:00:32 -05002633 static const time_t kStartTime = 1000;
David Benjamin0fef3052016-11-18 15:11:10 +09002634 g_current_time.tv_sec = kStartTime;
David Benjamin1b22f852016-10-27 16:36:32 -04002635
David Benjamin17b30832017-01-28 14:00:32 -05002636 // We are willing to use a longer lifetime for TLS 1.3 sessions as
2637 // resumptions still perform ECDHE.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002638 const time_t timeout = version() == TLS1_3_VERSION
David Benjamin17b30832017-01-28 14:00:32 -05002639 ? SSL_DEFAULT_SESSION_PSK_DHE_TIMEOUT
2640 : SSL_DEFAULT_SESSION_TIMEOUT;
2641
David Benjamin17b30832017-01-28 14:00:32 -05002642 // Both client and server must enforce session timeouts. We configure the
2643 // other side with a frozen clock so it never expires tickets.
David Benjamin0fef3052016-11-18 15:11:10 +09002644 if (server_test) {
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002645 SSL_CTX_set_current_time_cb(client_ctx_.get(), FrozenTimeCallback);
2646 SSL_CTX_set_current_time_cb(server_ctx_.get(), CurrentTimeCallback);
David Benjamin0fef3052016-11-18 15:11:10 +09002647 } else {
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002648 SSL_CTX_set_current_time_cb(client_ctx_.get(), CurrentTimeCallback);
2649 SSL_CTX_set_current_time_cb(server_ctx_.get(), FrozenTimeCallback);
David Benjamin0fef3052016-11-18 15:11:10 +09002650 }
2651
2652 // Configure a ticket callback which renews tickets.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002653 SSL_CTX_set_tlsext_ticket_key_cb(server_ctx_.get(), RenewTicketCallback);
David Benjamin0fef3052016-11-18 15:11:10 +09002654
2655 bssl::UniquePtr<SSL_SESSION> session =
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002656 CreateClientSession(client_ctx_.get(), server_ctx_.get());
2657 ASSERT_TRUE(session);
David Benjamin0fef3052016-11-18 15:11:10 +09002658
2659 // Advance the clock just behind the timeout.
David Benjamin17b30832017-01-28 14:00:32 -05002660 g_current_time.tv_sec += timeout - 1;
David Benjamin0fef3052016-11-18 15:11:10 +09002661
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002662 TRACED_CALL(ExpectSessionReused(client_ctx_.get(), server_ctx_.get(),
2663 session.get(),
2664 true /* expect session reused */));
David Benjamin0fef3052016-11-18 15:11:10 +09002665
2666 // Advance the clock one more second.
2667 g_current_time.tv_sec++;
2668
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002669 TRACED_CALL(ExpectSessionReused(client_ctx_.get(), server_ctx_.get(),
2670 session.get(),
2671 false /* expect session not reused */));
David Benjamin0fef3052016-11-18 15:11:10 +09002672
2673 // Rewind the clock to before the session was minted.
2674 g_current_time.tv_sec = kStartTime - 1;
2675
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002676 TRACED_CALL(ExpectSessionReused(client_ctx_.get(), server_ctx_.get(),
2677 session.get(),
2678 false /* expect session not reused */));
David Benjamin0fef3052016-11-18 15:11:10 +09002679
David Benjamin0fef3052016-11-18 15:11:10 +09002680 // Renew the session 10 seconds before expiration.
David Benjamin17b30832017-01-28 14:00:32 -05002681 time_t new_start_time = kStartTime + timeout - 10;
2682 g_current_time.tv_sec = new_start_time;
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002683 bssl::UniquePtr<SSL_SESSION> new_session = ExpectSessionRenewed(
2684 client_ctx_.get(), server_ctx_.get(), session.get());
2685 ASSERT_TRUE(new_session);
David Benjamin0fef3052016-11-18 15:11:10 +09002686
2687 // This new session is not the same object as before.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002688 EXPECT_NE(session.get(), new_session.get());
David Benjamin0fef3052016-11-18 15:11:10 +09002689
2690 // Check the sessions have timestamps measured from issuance.
2691 long session_time = 0;
2692 if (server_test) {
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002693 ASSERT_TRUE(GetServerTicketTime(&session_time, new_session.get()));
David Benjamin0fef3052016-11-18 15:11:10 +09002694 } else {
David Benjaminaaef8332018-06-29 16:45:49 -04002695 session_time = SSL_SESSION_get_time(new_session.get());
David Benjamin0fef3052016-11-18 15:11:10 +09002696 }
David Benjamin721e8b72016-08-03 13:13:17 -04002697
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002698 ASSERT_EQ(session_time, g_current_time.tv_sec);
David Benjamin721e8b72016-08-03 13:13:17 -04002699
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002700 if (version() == TLS1_3_VERSION) {
David Benjamin17b30832017-01-28 14:00:32 -05002701 // Renewal incorporates fresh key material in TLS 1.3, so we extend the
2702 // lifetime TLS 1.3.
2703 g_current_time.tv_sec = new_start_time + timeout - 1;
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002704 TRACED_CALL(ExpectSessionReused(client_ctx_.get(), server_ctx_.get(),
2705 new_session.get(),
2706 true /* expect session reused */));
David Benjamin721e8b72016-08-03 13:13:17 -04002707
David Benjamin17b30832017-01-28 14:00:32 -05002708 // The new session expires after the new timeout.
2709 g_current_time.tv_sec = new_start_time + timeout + 1;
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002710 TRACED_CALL(ExpectSessionReused(client_ctx_.get(), server_ctx_.get(),
2711 new_session.get(),
2712 false /* expect session ot reused */));
David Benjamin17b30832017-01-28 14:00:32 -05002713
2714 // Renew the session until it begins just past the auth timeout.
2715 time_t auth_end_time = kStartTime + SSL_DEFAULT_SESSION_AUTH_TIMEOUT;
2716 while (new_start_time < auth_end_time - 1000) {
2717 // Get as close as possible to target start time.
2718 new_start_time =
2719 std::min(auth_end_time - 1000, new_start_time + timeout - 1);
2720 g_current_time.tv_sec = new_start_time;
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002721 new_session = ExpectSessionRenewed(client_ctx_.get(), server_ctx_.get(),
David Benjamin17b30832017-01-28 14:00:32 -05002722 new_session.get());
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002723 ASSERT_TRUE(new_session);
David Benjamin17b30832017-01-28 14:00:32 -05002724 }
2725
2726 // Now the session's lifetime is bound by the auth timeout.
2727 g_current_time.tv_sec = auth_end_time - 1;
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002728 TRACED_CALL(ExpectSessionReused(client_ctx_.get(), server_ctx_.get(),
2729 new_session.get(),
2730 true /* expect session reused */));
David Benjamin17b30832017-01-28 14:00:32 -05002731
2732 g_current_time.tv_sec = auth_end_time + 1;
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002733 TRACED_CALL(ExpectSessionReused(client_ctx_.get(), server_ctx_.get(),
2734 new_session.get(),
2735 false /* expect session ot reused */));
David Benjamin17b30832017-01-28 14:00:32 -05002736 } else {
2737 // The new session is usable just before the old expiration.
2738 g_current_time.tv_sec = kStartTime + timeout - 1;
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002739 TRACED_CALL(ExpectSessionReused(client_ctx_.get(), server_ctx_.get(),
2740 new_session.get(),
2741 true /* expect session reused */));
David Benjamin17b30832017-01-28 14:00:32 -05002742
2743 // Renewal does not extend the lifetime, so it is not usable beyond the
2744 // old expiration.
2745 g_current_time.tv_sec = kStartTime + timeout + 1;
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002746 TRACED_CALL(ExpectSessionReused(client_ctx_.get(), server_ctx_.get(),
2747 new_session.get(),
2748 false /* expect session not reused */));
David Benjamin1b22f852016-10-27 16:36:32 -04002749 }
David Benjamin721e8b72016-08-03 13:13:17 -04002750 }
David Benjamin721e8b72016-08-03 13:13:17 -04002751}
2752
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002753TEST_P(SSLVersionTest, DefaultTicketKeyInitialization) {
Martin Kreichgauer72912d22017-08-04 12:06:43 -07002754 static const uint8_t kZeroKey[kTicketKeyLen] = {};
2755 uint8_t ticket_key[kTicketKeyLen];
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002756 ASSERT_EQ(1, SSL_CTX_get_tlsext_ticket_keys(server_ctx_.get(), ticket_key,
Martin Kreichgauer72912d22017-08-04 12:06:43 -07002757 kTicketKeyLen));
2758 ASSERT_NE(0, OPENSSL_memcmp(ticket_key, kZeroKey, kTicketKeyLen));
2759}
2760
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002761TEST_P(SSLVersionTest, DefaultTicketKeyRotation) {
Martin Kreichgauer72912d22017-08-04 12:06:43 -07002762 static const time_t kStartTime = 1001;
2763 g_current_time.tv_sec = kStartTime;
Martin Kreichgauer72912d22017-08-04 12:06:43 -07002764
David Benjaminc11ea9422017-08-29 16:33:21 -04002765 // We use session reuse as a proxy for ticket decryption success, hence
2766 // disable session timeouts.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002767 SSL_CTX_set_timeout(server_ctx_.get(), std::numeric_limits<uint32_t>::max());
2768 SSL_CTX_set_session_psk_dhe_timeout(server_ctx_.get(),
Martin Kreichgauer72912d22017-08-04 12:06:43 -07002769 std::numeric_limits<uint32_t>::max());
2770
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002771 SSL_CTX_set_current_time_cb(client_ctx_.get(), FrozenTimeCallback);
2772 SSL_CTX_set_current_time_cb(server_ctx_.get(), CurrentTimeCallback);
Martin Kreichgauer72912d22017-08-04 12:06:43 -07002773
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002774 SSL_CTX_set_session_cache_mode(client_ctx_.get(), SSL_SESS_CACHE_BOTH);
2775 SSL_CTX_set_session_cache_mode(server_ctx_.get(), SSL_SESS_CACHE_OFF);
Martin Kreichgauer72912d22017-08-04 12:06:43 -07002776
David Benjamin1f0d54b2018-08-09 16:19:13 -05002777 // Initialize ticket_key with the current key and check that it was
2778 // initialized to something, not all zeros.
2779 uint8_t ticket_key[kTicketKeyLen] = {0};
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002780 TRACED_CALL(ExpectTicketKeyChanged(server_ctx_.get(), ticket_key,
2781 true /* changed */));
Martin Kreichgauer72912d22017-08-04 12:06:43 -07002782
David Benjaminc11ea9422017-08-29 16:33:21 -04002783 // Verify ticket resumption actually works.
Martin Kreichgauer72912d22017-08-04 12:06:43 -07002784 bssl::UniquePtr<SSL> client, server;
2785 bssl::UniquePtr<SSL_SESSION> session =
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002786 CreateClientSession(client_ctx_.get(), server_ctx_.get());
Martin Kreichgauer72912d22017-08-04 12:06:43 -07002787 ASSERT_TRUE(session);
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002788 TRACED_CALL(ExpectSessionReused(client_ctx_.get(), server_ctx_.get(),
Martin Kreichgauer72912d22017-08-04 12:06:43 -07002789 session.get(), true /* reused */));
2790
David Benjaminc11ea9422017-08-29 16:33:21 -04002791 // Advance time to just before key rotation.
Martin Kreichgauer72912d22017-08-04 12:06:43 -07002792 g_current_time.tv_sec += SSL_DEFAULT_TICKET_KEY_ROTATION_INTERVAL - 1;
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002793 TRACED_CALL(ExpectSessionReused(client_ctx_.get(), server_ctx_.get(),
Martin Kreichgauer72912d22017-08-04 12:06:43 -07002794 session.get(), true /* reused */));
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002795 TRACED_CALL(ExpectTicketKeyChanged(server_ctx_.get(), ticket_key,
Martin Kreichgauer72912d22017-08-04 12:06:43 -07002796 false /* NOT changed */));
2797
David Benjaminc11ea9422017-08-29 16:33:21 -04002798 // Force key rotation.
Martin Kreichgauer72912d22017-08-04 12:06:43 -07002799 g_current_time.tv_sec += 1;
2800 bssl::UniquePtr<SSL_SESSION> new_session =
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002801 CreateClientSession(client_ctx_.get(), server_ctx_.get());
2802 TRACED_CALL(ExpectTicketKeyChanged(server_ctx_.get(), ticket_key,
2803 true /* changed */));
Martin Kreichgauer72912d22017-08-04 12:06:43 -07002804
David Benjaminc11ea9422017-08-29 16:33:21 -04002805 // Resumption with both old and new ticket should work.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002806 TRACED_CALL(ExpectSessionReused(client_ctx_.get(), server_ctx_.get(),
Martin Kreichgauer72912d22017-08-04 12:06:43 -07002807 session.get(), true /* reused */));
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002808 TRACED_CALL(ExpectSessionReused(client_ctx_.get(), server_ctx_.get(),
Martin Kreichgauer72912d22017-08-04 12:06:43 -07002809 new_session.get(), true /* reused */));
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002810 TRACED_CALL(ExpectTicketKeyChanged(server_ctx_.get(), ticket_key,
Martin Kreichgauer72912d22017-08-04 12:06:43 -07002811 false /* NOT changed */));
2812
David Benjaminc11ea9422017-08-29 16:33:21 -04002813 // Force key rotation again. Resumption with the old ticket now fails.
Martin Kreichgauer72912d22017-08-04 12:06:43 -07002814 g_current_time.tv_sec += SSL_DEFAULT_TICKET_KEY_ROTATION_INTERVAL;
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002815 TRACED_CALL(ExpectSessionReused(client_ctx_.get(), server_ctx_.get(),
Martin Kreichgauer72912d22017-08-04 12:06:43 -07002816 session.get(), false /* NOT reused */));
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002817 TRACED_CALL(ExpectTicketKeyChanged(server_ctx_.get(), ticket_key,
2818 true /* changed */));
Martin Kreichgauer72912d22017-08-04 12:06:43 -07002819
David Benjaminc11ea9422017-08-29 16:33:21 -04002820 // But resumption with the newer session still works.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002821 TRACED_CALL(ExpectSessionReused(client_ctx_.get(), server_ctx_.get(),
Martin Kreichgauer72912d22017-08-04 12:06:43 -07002822 new_session.get(), true /* reused */));
2823}
2824
David Benjamin0fc37ef2016-08-17 15:29:46 -04002825static int SwitchContext(SSL *ssl, int *out_alert, void *arg) {
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002826 SSL_CTX *ctx = reinterpret_cast<SSL_CTX *>(arg);
David Benjamin0fc37ef2016-08-17 15:29:46 -04002827 SSL_set_SSL_CTX(ssl, ctx);
2828 return SSL_TLSEXT_ERR_OK;
2829}
2830
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002831TEST_P(SSLVersionTest, SNICallback) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002832 bssl::UniquePtr<X509> cert2 = GetECDSATestCertificate();
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002833 ASSERT_TRUE(cert2);
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002834 bssl::UniquePtr<EVP_PKEY> key2 = GetECDSATestKey();
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002835 ASSERT_TRUE(key2);
David Benjamin0fc37ef2016-08-17 15:29:46 -04002836
David Benjamin0fef3052016-11-18 15:11:10 +09002837 // Test that switching the |SSL_CTX| at the SNI callback behaves correctly.
2838 static const uint16_t kECDSAWithSHA256 = SSL_SIGN_ECDSA_SECP256R1_SHA256;
David Benjamin0fc37ef2016-08-17 15:29:46 -04002839
David Benjamin83a32122017-02-14 18:34:54 -05002840 static const uint8_t kSCTList[] = {0, 6, 0, 4, 5, 6, 7, 8};
2841 static const uint8_t kOCSPResponse[] = {1, 2, 3, 4};
2842
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002843 bssl::UniquePtr<SSL_CTX> server_ctx2 = CreateContext();
2844 ASSERT_TRUE(server_ctx2);
2845 ASSERT_TRUE(SSL_CTX_use_certificate(server_ctx2.get(), cert2.get()));
2846 ASSERT_TRUE(SSL_CTX_use_PrivateKey(server_ctx2.get(), key2.get()));
2847 ASSERT_TRUE(SSL_CTX_set_signed_cert_timestamp_list(
2848 server_ctx2.get(), kSCTList, sizeof(kSCTList)));
2849 ASSERT_TRUE(SSL_CTX_set_ocsp_response(server_ctx2.get(), kOCSPResponse,
2850 sizeof(kOCSPResponse)));
2851 // Historically signing preferences would be lost in some cases with the
2852 // SNI callback, which triggers the TLS 1.2 SHA-1 default. To ensure
2853 // this doesn't happen when |version| is TLS 1.2, configure the private
2854 // key to only sign SHA-256.
2855 ASSERT_TRUE(SSL_CTX_set_signing_algorithm_prefs(server_ctx2.get(),
2856 &kECDSAWithSHA256, 1));
David Benjamin0fc37ef2016-08-17 15:29:46 -04002857
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002858 SSL_CTX_set_tlsext_servername_callback(server_ctx_.get(), SwitchContext);
2859 SSL_CTX_set_tlsext_servername_arg(server_ctx_.get(), server_ctx2.get());
David Benjamin0fc37ef2016-08-17 15:29:46 -04002860
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002861 SSL_CTX_enable_signed_cert_timestamps(client_ctx_.get());
2862 SSL_CTX_enable_ocsp_stapling(client_ctx_.get());
David Benjamin83a32122017-02-14 18:34:54 -05002863
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002864 ASSERT_TRUE(Connect());
David Benjamin0fc37ef2016-08-17 15:29:46 -04002865
David Benjamin0fef3052016-11-18 15:11:10 +09002866 // The client should have received |cert2|.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002867 bssl::UniquePtr<X509> peer(SSL_get_peer_certificate(client_.get()));
2868 ASSERT_TRUE(peer);
2869 EXPECT_EQ(X509_cmp(peer.get(), cert2.get()), 0);
David Benjamin0fc37ef2016-08-17 15:29:46 -04002870
David Benjamin83a32122017-02-14 18:34:54 -05002871 // The client should have received |server_ctx2|'s SCT list.
2872 const uint8_t *data;
2873 size_t len;
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002874 SSL_get0_signed_cert_timestamp_list(client_.get(), &data, &len);
2875 EXPECT_EQ(Bytes(kSCTList), Bytes(data, len));
David Benjamin83a32122017-02-14 18:34:54 -05002876
2877 // The client should have received |server_ctx2|'s OCSP response.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002878 SSL_get0_ocsp_response(client_.get(), &data, &len);
2879 EXPECT_EQ(Bytes(kOCSPResponse), Bytes(data, len));
David Benjamin0fc37ef2016-08-17 15:29:46 -04002880}
2881
David Benjaminf0d8e222017-02-04 10:58:26 -05002882// Test that the early callback can swap the maximum version.
2883TEST(SSLTest, EarlyCallbackVersionSwitch) {
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002884 bssl::UniquePtr<X509> cert = GetTestCertificate();
2885 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
2886 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(TLS_method()));
2887 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLS_method()));
David Benjaminf0d8e222017-02-04 10:58:26 -05002888 ASSERT_TRUE(cert);
2889 ASSERT_TRUE(key);
2890 ASSERT_TRUE(server_ctx);
2891 ASSERT_TRUE(client_ctx);
2892 ASSERT_TRUE(SSL_CTX_use_certificate(server_ctx.get(), cert.get()));
2893 ASSERT_TRUE(SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()));
2894 ASSERT_TRUE(SSL_CTX_set_max_proto_version(client_ctx.get(), TLS1_3_VERSION));
2895 ASSERT_TRUE(SSL_CTX_set_max_proto_version(server_ctx.get(), TLS1_3_VERSION));
David Benjamin99620572016-08-30 00:35:36 -04002896
David Benjaminf0d8e222017-02-04 10:58:26 -05002897 SSL_CTX_set_select_certificate_cb(
Alessandro Ghedini57e81e62017-03-14 23:36:00 +00002898 server_ctx.get(),
2899 [](const SSL_CLIENT_HELLO *client_hello) -> ssl_select_cert_result_t {
David Benjaminf0d8e222017-02-04 10:58:26 -05002900 if (!SSL_set_max_proto_version(client_hello->ssl, TLS1_2_VERSION)) {
Alessandro Ghedini57e81e62017-03-14 23:36:00 +00002901 return ssl_select_cert_error;
David Benjaminf0d8e222017-02-04 10:58:26 -05002902 }
2903
Alessandro Ghedini57e81e62017-03-14 23:36:00 +00002904 return ssl_select_cert_success;
David Benjaminf0d8e222017-02-04 10:58:26 -05002905 });
David Benjamin99620572016-08-30 00:35:36 -04002906
Matt Braithwaited17d74d2016-08-17 20:10:28 -07002907 bssl::UniquePtr<SSL> client, server;
David Benjaminf0d8e222017-02-04 10:58:26 -05002908 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx.get(),
David Benjamina8614602017-09-06 15:40:19 -04002909 server_ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05002910 EXPECT_EQ(TLS1_2_VERSION, SSL_version(client.get()));
David Benjamin99620572016-08-30 00:35:36 -04002911}
2912
David Benjaminf0d8e222017-02-04 10:58:26 -05002913TEST(SSLTest, SetVersion) {
David Benjamin2dc02042016-09-19 19:57:37 -04002914 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
David Benjaminf0d8e222017-02-04 10:58:26 -05002915 ASSERT_TRUE(ctx);
David Benjamin2dc02042016-09-19 19:57:37 -04002916
David Benjaminf0d8e222017-02-04 10:58:26 -05002917 // Set valid TLS versions.
2918 EXPECT_TRUE(SSL_CTX_set_max_proto_version(ctx.get(), TLS1_VERSION));
2919 EXPECT_TRUE(SSL_CTX_set_max_proto_version(ctx.get(), TLS1_1_VERSION));
2920 EXPECT_TRUE(SSL_CTX_set_min_proto_version(ctx.get(), TLS1_VERSION));
2921 EXPECT_TRUE(SSL_CTX_set_min_proto_version(ctx.get(), TLS1_1_VERSION));
David Benjamin2dc02042016-09-19 19:57:37 -04002922
David Benjaminf0d8e222017-02-04 10:58:26 -05002923 // Invalid TLS versions are rejected.
2924 EXPECT_FALSE(SSL_CTX_set_max_proto_version(ctx.get(), DTLS1_VERSION));
2925 EXPECT_FALSE(SSL_CTX_set_max_proto_version(ctx.get(), 0x0200));
2926 EXPECT_FALSE(SSL_CTX_set_max_proto_version(ctx.get(), 0x1234));
2927 EXPECT_FALSE(SSL_CTX_set_min_proto_version(ctx.get(), DTLS1_VERSION));
2928 EXPECT_FALSE(SSL_CTX_set_min_proto_version(ctx.get(), 0x0200));
2929 EXPECT_FALSE(SSL_CTX_set_min_proto_version(ctx.get(), 0x1234));
David Benjamin2dc02042016-09-19 19:57:37 -04002930
David Benjaminf0d8e222017-02-04 10:58:26 -05002931 // Zero is the default version.
2932 EXPECT_TRUE(SSL_CTX_set_max_proto_version(ctx.get(), 0));
Matthew Braithwaite58d56f42019-11-04 13:20:01 -08002933 EXPECT_EQ(TLS1_3_VERSION, SSL_CTX_get_max_proto_version(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05002934 EXPECT_TRUE(SSL_CTX_set_min_proto_version(ctx.get(), 0));
Nitish Sakhawalkara4af5f82019-03-25 17:26:59 -07002935 EXPECT_EQ(TLS1_VERSION, SSL_CTX_get_min_proto_version(ctx.get()));
David Benjamin3cfeb952017-03-01 16:48:38 -05002936
David Benjamin9bb15f52018-06-26 00:07:40 -04002937 // TLS 1.3 is available, but not by default.
David Benjamin3cfeb952017-03-01 16:48:38 -05002938 EXPECT_TRUE(SSL_CTX_set_max_proto_version(ctx.get(), TLS1_3_VERSION));
Nitish Sakhawalkara4af5f82019-03-25 17:26:59 -07002939 EXPECT_EQ(TLS1_3_VERSION, SSL_CTX_get_max_proto_version(ctx.get()));
David Benjamine34bcc92016-09-21 16:53:09 -04002940
David Benjamin9bb15f52018-06-26 00:07:40 -04002941 // SSL 3.0 is not available.
2942 EXPECT_FALSE(SSL_CTX_set_min_proto_version(ctx.get(), SSL3_VERSION));
2943
David Benjamin2dc02042016-09-19 19:57:37 -04002944 ctx.reset(SSL_CTX_new(DTLS_method()));
David Benjaminf0d8e222017-02-04 10:58:26 -05002945 ASSERT_TRUE(ctx);
David Benjamin2dc02042016-09-19 19:57:37 -04002946
David Benjaminf0d8e222017-02-04 10:58:26 -05002947 EXPECT_TRUE(SSL_CTX_set_max_proto_version(ctx.get(), DTLS1_VERSION));
2948 EXPECT_TRUE(SSL_CTX_set_max_proto_version(ctx.get(), DTLS1_2_VERSION));
2949 EXPECT_TRUE(SSL_CTX_set_min_proto_version(ctx.get(), DTLS1_VERSION));
2950 EXPECT_TRUE(SSL_CTX_set_min_proto_version(ctx.get(), DTLS1_2_VERSION));
David Benjamin2dc02042016-09-19 19:57:37 -04002951
David Benjaminf0d8e222017-02-04 10:58:26 -05002952 EXPECT_FALSE(SSL_CTX_set_max_proto_version(ctx.get(), TLS1_VERSION));
2953 EXPECT_FALSE(SSL_CTX_set_max_proto_version(ctx.get(), 0xfefe /* DTLS 1.1 */));
2954 EXPECT_FALSE(SSL_CTX_set_max_proto_version(ctx.get(), 0xfffe /* DTLS 0.1 */));
2955 EXPECT_FALSE(SSL_CTX_set_max_proto_version(ctx.get(), 0x1234));
2956 EXPECT_FALSE(SSL_CTX_set_min_proto_version(ctx.get(), TLS1_VERSION));
2957 EXPECT_FALSE(SSL_CTX_set_min_proto_version(ctx.get(), 0xfefe /* DTLS 1.1 */));
2958 EXPECT_FALSE(SSL_CTX_set_min_proto_version(ctx.get(), 0xfffe /* DTLS 0.1 */));
2959 EXPECT_FALSE(SSL_CTX_set_min_proto_version(ctx.get(), 0x1234));
David Benjamin2dc02042016-09-19 19:57:37 -04002960
David Benjaminf0d8e222017-02-04 10:58:26 -05002961 EXPECT_TRUE(SSL_CTX_set_max_proto_version(ctx.get(), 0));
Nitish Sakhawalkara4af5f82019-03-25 17:26:59 -07002962 EXPECT_EQ(DTLS1_2_VERSION, SSL_CTX_get_max_proto_version(ctx.get()));
David Benjaminf0d8e222017-02-04 10:58:26 -05002963 EXPECT_TRUE(SSL_CTX_set_min_proto_version(ctx.get(), 0));
Nitish Sakhawalkara4af5f82019-03-25 17:26:59 -07002964 EXPECT_EQ(DTLS1_VERSION, SSL_CTX_get_min_proto_version(ctx.get()));
David Benjamin2dc02042016-09-19 19:57:37 -04002965}
2966
David Benjamin458334a2016-12-15 13:53:25 -05002967static const char *GetVersionName(uint16_t version) {
2968 switch (version) {
David Benjamin458334a2016-12-15 13:53:25 -05002969 case TLS1_VERSION:
2970 return "TLSv1";
2971 case TLS1_1_VERSION:
2972 return "TLSv1.1";
2973 case TLS1_2_VERSION:
2974 return "TLSv1.2";
2975 case TLS1_3_VERSION:
2976 return "TLSv1.3";
2977 case DTLS1_VERSION:
2978 return "DTLSv1";
2979 case DTLS1_2_VERSION:
2980 return "DTLSv1.2";
2981 default:
2982 return "???";
2983 }
2984}
2985
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002986TEST_P(SSLVersionTest, Version) {
2987 ASSERT_TRUE(Connect());
David Benjamincb18ac22016-09-27 14:09:15 -04002988
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002989 EXPECT_EQ(SSL_version(client_.get()), version());
2990 EXPECT_EQ(SSL_version(server_.get()), version());
David Benjamincb18ac22016-09-27 14:09:15 -04002991
David Benjamin458334a2016-12-15 13:53:25 -05002992 // Test the version name is reported as expected.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002993 const char *version_name = GetVersionName(version());
2994 EXPECT_EQ(strcmp(version_name, SSL_get_version(client_.get())), 0);
2995 EXPECT_EQ(strcmp(version_name, SSL_get_version(server_.get())), 0);
David Benjamin458334a2016-12-15 13:53:25 -05002996
2997 // Test SSL_SESSION reports the same name.
2998 const char *client_name =
Martin Kreichgauer1a663262017-08-16 14:54:04 -07002999 SSL_SESSION_get_version(SSL_get_session(client_.get()));
David Benjamin458334a2016-12-15 13:53:25 -05003000 const char *server_name =
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003001 SSL_SESSION_get_version(SSL_get_session(server_.get()));
3002 EXPECT_EQ(strcmp(version_name, client_name), 0);
3003 EXPECT_EQ(strcmp(version_name, server_name), 0);
David Benjamincb18ac22016-09-27 14:09:15 -04003004}
3005
David Benjamin9ef31f02016-10-31 18:01:13 -04003006// Tests that that |SSL_get_pending_cipher| is available during the ALPN
3007// selection callback.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003008TEST_P(SSLVersionTest, ALPNCipherAvailable) {
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003009 ASSERT_TRUE(UseCertAndKey(client_ctx_.get()));
3010
David Benjamin9ef31f02016-10-31 18:01:13 -04003011 static const uint8_t kALPNProtos[] = {0x03, 'f', 'o', 'o'};
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003012 ASSERT_EQ(SSL_CTX_set_alpn_protos(client_ctx_.get(), kALPNProtos,
3013 sizeof(kALPNProtos)),
3014 0);
David Benjamin0fef3052016-11-18 15:11:10 +09003015
3016 // The ALPN callback does not fail the handshake on error, so have the
3017 // callback write a boolean.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003018 std::pair<uint16_t, bool> callback_state(version(), false);
David Benjamin0fef3052016-11-18 15:11:10 +09003019 SSL_CTX_set_alpn_select_cb(
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003020 server_ctx_.get(),
David Benjamin0fef3052016-11-18 15:11:10 +09003021 [](SSL *ssl, const uint8_t **out, uint8_t *out_len, const uint8_t *in,
3022 unsigned in_len, void *arg) -> int {
3023 auto state = reinterpret_cast<std::pair<uint16_t, bool> *>(arg);
3024 if (SSL_get_pending_cipher(ssl) != nullptr &&
3025 SSL_version(ssl) == state->first) {
3026 state->second = true;
3027 }
3028 return SSL_TLSEXT_ERR_NOACK;
3029 },
3030 &callback_state);
3031
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003032 ASSERT_TRUE(Connect());
David Benjamin0fef3052016-11-18 15:11:10 +09003033
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003034 ASSERT_TRUE(callback_state.second);
David Benjamin0fef3052016-11-18 15:11:10 +09003035}
3036
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003037TEST_P(SSLVersionTest, SSLClearSessionResumption) {
David Benjaminb79cc842016-12-07 15:57:14 -05003038 // Skip this for TLS 1.3. TLS 1.3's ticket mechanism is incompatible with this
3039 // API pattern.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003040 if (version() == TLS1_3_VERSION) {
3041 return;
David Benjaminb79cc842016-12-07 15:57:14 -05003042 }
3043
Matthew Braithwaiteb7bc80a2018-04-13 15:51:30 -07003044 shed_handshake_config_ = false;
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003045 ASSERT_TRUE(Connect());
David Benjaminb79cc842016-12-07 15:57:14 -05003046
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003047 EXPECT_FALSE(SSL_session_reused(client_.get()));
3048 EXPECT_FALSE(SSL_session_reused(server_.get()));
David Benjaminb79cc842016-12-07 15:57:14 -05003049
3050 // Reset everything.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003051 ASSERT_TRUE(SSL_clear(client_.get()));
3052 ASSERT_TRUE(SSL_clear(server_.get()));
David Benjaminb79cc842016-12-07 15:57:14 -05003053
3054 // Attempt to connect a second time.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003055 ASSERT_TRUE(CompleteHandshakes(client_.get(), server_.get()));
David Benjaminb79cc842016-12-07 15:57:14 -05003056
3057 // |SSL_clear| should implicitly offer the previous session to the server.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003058 EXPECT_TRUE(SSL_session_reused(client_.get()));
3059 EXPECT_TRUE(SSL_session_reused(server_.get()));
David Benjaminb79cc842016-12-07 15:57:14 -05003060}
3061
Matthew Braithwaiteb7bc80a2018-04-13 15:51:30 -07003062TEST_P(SSLVersionTest, SSLClearFailsWithShedding) {
3063 shed_handshake_config_ = false;
3064 ASSERT_TRUE(Connect());
3065 ASSERT_TRUE(CompleteHandshakes(client_.get(), server_.get()));
3066
3067 // Reset everything.
3068 ASSERT_TRUE(SSL_clear(client_.get()));
3069 ASSERT_TRUE(SSL_clear(server_.get()));
3070
3071 // Now enable shedding, and connect a second time.
3072 shed_handshake_config_ = true;
3073 ASSERT_TRUE(Connect());
3074 ASSERT_TRUE(CompleteHandshakes(client_.get(), server_.get()));
3075
3076 // |SSL_clear| should now fail.
3077 ASSERT_FALSE(SSL_clear(client_.get()));
3078 ASSERT_FALSE(SSL_clear(server_.get()));
3079}
3080
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003081static bool ChainsEqual(STACK_OF(X509) * chain,
3082 const std::vector<X509 *> &expected) {
David Benjamin1444c3a2016-12-20 17:23:11 -05003083 if (sk_X509_num(chain) != expected.size()) {
3084 return false;
3085 }
3086
3087 for (size_t i = 0; i < expected.size(); i++) {
3088 if (X509_cmp(sk_X509_value(chain, i), expected[i]) != 0) {
3089 return false;
3090 }
3091 }
3092
3093 return true;
3094}
3095
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003096TEST_P(SSLVersionTest, AutoChain) {
3097 cert_ = GetChainTestCertificate();
3098 ASSERT_TRUE(cert_);
3099 key_ = GetChainTestKey();
3100 ASSERT_TRUE(key_);
David Benjamin1444c3a2016-12-20 17:23:11 -05003101 bssl::UniquePtr<X509> intermediate = GetChainTestIntermediate();
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003102 ASSERT_TRUE(intermediate);
3103
3104 ASSERT_TRUE(UseCertAndKey(client_ctx_.get()));
3105 ASSERT_TRUE(UseCertAndKey(server_ctx_.get()));
David Benjamin1444c3a2016-12-20 17:23:11 -05003106
3107 // Configure both client and server to accept any certificate. Add
3108 // |intermediate| to the cert store.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003109 ASSERT_TRUE(X509_STORE_add_cert(SSL_CTX_get_cert_store(client_ctx_.get()),
3110 intermediate.get()));
3111 ASSERT_TRUE(X509_STORE_add_cert(SSL_CTX_get_cert_store(server_ctx_.get()),
3112 intermediate.get()));
3113 SSL_CTX_set_verify(client_ctx_.get(),
3114 SSL_VERIFY_PEER | SSL_VERIFY_FAIL_IF_NO_PEER_CERT,
3115 nullptr);
3116 SSL_CTX_set_verify(server_ctx_.get(),
3117 SSL_VERIFY_PEER | SSL_VERIFY_FAIL_IF_NO_PEER_CERT,
3118 nullptr);
3119 SSL_CTX_set_cert_verify_callback(client_ctx_.get(), VerifySucceed, NULL);
3120 SSL_CTX_set_cert_verify_callback(server_ctx_.get(), VerifySucceed, NULL);
David Benjamin1444c3a2016-12-20 17:23:11 -05003121
3122 // By default, the client and server should each only send the leaf.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003123 ASSERT_TRUE(Connect());
David Benjamin1444c3a2016-12-20 17:23:11 -05003124
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003125 EXPECT_TRUE(
3126 ChainsEqual(SSL_get_peer_full_cert_chain(client_.get()), {cert_.get()}));
3127 EXPECT_TRUE(
3128 ChainsEqual(SSL_get_peer_full_cert_chain(server_.get()), {cert_.get()}));
David Benjamin1444c3a2016-12-20 17:23:11 -05003129
3130 // If auto-chaining is enabled, then the intermediate is sent.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003131 SSL_CTX_clear_mode(client_ctx_.get(), SSL_MODE_NO_AUTO_CHAIN);
3132 SSL_CTX_clear_mode(server_ctx_.get(), SSL_MODE_NO_AUTO_CHAIN);
3133 ASSERT_TRUE(Connect());
David Benjamin1444c3a2016-12-20 17:23:11 -05003134
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003135 EXPECT_TRUE(ChainsEqual(SSL_get_peer_full_cert_chain(client_.get()),
3136 {cert_.get(), intermediate.get()}));
3137 EXPECT_TRUE(ChainsEqual(SSL_get_peer_full_cert_chain(server_.get()),
3138 {cert_.get(), intermediate.get()}));
David Benjamin1444c3a2016-12-20 17:23:11 -05003139
3140 // Auto-chaining does not override explicitly-configured intermediates.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003141 ASSERT_TRUE(SSL_CTX_add1_chain_cert(client_ctx_.get(), cert_.get()));
3142 ASSERT_TRUE(SSL_CTX_add1_chain_cert(server_ctx_.get(), cert_.get()));
3143 ASSERT_TRUE(Connect());
David Benjamin1444c3a2016-12-20 17:23:11 -05003144
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003145 EXPECT_TRUE(ChainsEqual(SSL_get_peer_full_cert_chain(client_.get()),
3146 {cert_.get(), cert_.get()}));
David Benjamin1444c3a2016-12-20 17:23:11 -05003147
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003148 EXPECT_TRUE(ChainsEqual(SSL_get_peer_full_cert_chain(server_.get()),
3149 {cert_.get(), cert_.get()}));
David Benjamin1444c3a2016-12-20 17:23:11 -05003150}
3151
David Benjamin48063c22017-01-01 23:56:36 -05003152static bool ExpectBadWriteRetry() {
3153 int err = ERR_get_error();
3154 if (ERR_GET_LIB(err) != ERR_LIB_SSL ||
3155 ERR_GET_REASON(err) != SSL_R_BAD_WRITE_RETRY) {
3156 char buf[ERR_ERROR_STRING_BUF_LEN];
3157 ERR_error_string_n(err, buf, sizeof(buf));
3158 fprintf(stderr, "Wanted SSL_R_BAD_WRITE_RETRY, got: %s.\n", buf);
3159 return false;
3160 }
3161
3162 if (ERR_peek_error() != 0) {
3163 fprintf(stderr, "Unexpected error following SSL_R_BAD_WRITE_RETRY.\n");
3164 return false;
3165 }
3166
3167 return true;
3168}
3169
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003170TEST_P(SSLVersionTest, SSLWriteRetry) {
3171 if (is_dtls()) {
3172 return;
David Benjamin48063c22017-01-01 23:56:36 -05003173 }
3174
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003175 for (bool enable_partial_write : {false, true}) {
3176 SCOPED_TRACE(enable_partial_write);
3177
David Benjamin48063c22017-01-01 23:56:36 -05003178 // Connect a client and server.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003179 ASSERT_TRUE(UseCertAndKey(client_ctx_.get()));
3180
3181 ASSERT_TRUE(Connect());
David Benjamin48063c22017-01-01 23:56:36 -05003182
3183 if (enable_partial_write) {
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003184 SSL_set_mode(client_.get(), SSL_MODE_ENABLE_PARTIAL_WRITE);
David Benjamin48063c22017-01-01 23:56:36 -05003185 }
3186
3187 // Write without reading until the buffer is full and we have an unfinished
3188 // write. Keep a count so we may reread it again later. "hello!" will be
3189 // written in two chunks, "hello" and "!".
3190 char data[] = "hello!";
3191 static const int kChunkLen = 5; // The length of "hello".
3192 unsigned count = 0;
3193 for (;;) {
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003194 int ret = SSL_write(client_.get(), data, kChunkLen);
David Benjamin48063c22017-01-01 23:56:36 -05003195 if (ret <= 0) {
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003196 ASSERT_EQ(SSL_get_error(client_.get(), ret), SSL_ERROR_WANT_WRITE);
3197 break;
David Benjamin48063c22017-01-01 23:56:36 -05003198 }
3199
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003200 ASSERT_EQ(ret, 5);
David Benjamin48063c22017-01-01 23:56:36 -05003201
3202 count++;
3203 }
3204
3205 // Retrying with the same parameters is legal.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003206 ASSERT_EQ(
3207 SSL_get_error(client_.get(), SSL_write(client_.get(), data, kChunkLen)),
3208 SSL_ERROR_WANT_WRITE);
David Benjamin48063c22017-01-01 23:56:36 -05003209
3210 // Retrying with the same buffer but shorter length is not legal.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003211 ASSERT_EQ(SSL_get_error(client_.get(),
3212 SSL_write(client_.get(), data, kChunkLen - 1)),
3213 SSL_ERROR_SSL);
3214 ASSERT_TRUE(ExpectBadWriteRetry());
David Benjamin48063c22017-01-01 23:56:36 -05003215
3216 // Retrying with a different buffer pointer is not legal.
3217 char data2[] = "hello";
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003218 ASSERT_EQ(SSL_get_error(client_.get(),
3219 SSL_write(client_.get(), data2, kChunkLen)),
3220 SSL_ERROR_SSL);
3221 ASSERT_TRUE(ExpectBadWriteRetry());
David Benjamin48063c22017-01-01 23:56:36 -05003222
3223 // With |SSL_MODE_ACCEPT_MOVING_WRITE_BUFFER|, the buffer may move.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003224 SSL_set_mode(client_.get(), SSL_MODE_ACCEPT_MOVING_WRITE_BUFFER);
3225 ASSERT_EQ(SSL_get_error(client_.get(),
3226 SSL_write(client_.get(), data2, kChunkLen)),
3227 SSL_ERROR_WANT_WRITE);
David Benjamin48063c22017-01-01 23:56:36 -05003228
3229 // |SSL_MODE_ACCEPT_MOVING_WRITE_BUFFER| does not disable length checks.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003230 ASSERT_EQ(SSL_get_error(client_.get(),
3231 SSL_write(client_.get(), data2, kChunkLen - 1)),
3232 SSL_ERROR_SSL);
3233 ASSERT_TRUE(ExpectBadWriteRetry());
David Benjamin48063c22017-01-01 23:56:36 -05003234
3235 // Retrying with a larger buffer is legal.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003236 ASSERT_EQ(SSL_get_error(client_.get(),
3237 SSL_write(client_.get(), data, kChunkLen + 1)),
3238 SSL_ERROR_WANT_WRITE);
David Benjamin48063c22017-01-01 23:56:36 -05003239
3240 // Drain the buffer.
3241 char buf[20];
3242 for (unsigned i = 0; i < count; i++) {
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003243 ASSERT_EQ(SSL_read(server_.get(), buf, sizeof(buf)), kChunkLen);
3244 ASSERT_EQ(OPENSSL_memcmp(buf, "hello", kChunkLen), 0);
David Benjamin48063c22017-01-01 23:56:36 -05003245 }
3246
3247 // Now that there is space, a retry with a larger buffer should flush the
3248 // pending record, skip over that many bytes of input (on assumption they
3249 // are the same), and write the remainder. If SSL_MODE_ENABLE_PARTIAL_WRITE
3250 // is set, this will complete in two steps.
3251 char data3[] = "_____!";
3252 if (enable_partial_write) {
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003253 ASSERT_EQ(SSL_write(client_.get(), data3, kChunkLen + 1), kChunkLen);
3254 ASSERT_EQ(SSL_write(client_.get(), data3 + kChunkLen, 1), 1);
3255 } else {
3256 ASSERT_EQ(SSL_write(client_.get(), data3, kChunkLen + 1), kChunkLen + 1);
David Benjamin48063c22017-01-01 23:56:36 -05003257 }
3258
3259 // Check the last write was correct. The data will be spread over two
3260 // records, so SSL_read returns twice.
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003261 ASSERT_EQ(SSL_read(server_.get(), buf, sizeof(buf)), kChunkLen);
3262 ASSERT_EQ(OPENSSL_memcmp(buf, "hello", kChunkLen), 0);
3263 ASSERT_EQ(SSL_read(server_.get(), buf, sizeof(buf)), 1);
3264 ASSERT_EQ(buf[0], '!');
David Benjamin48063c22017-01-01 23:56:36 -05003265 }
David Benjamin48063c22017-01-01 23:56:36 -05003266}
3267
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003268TEST_P(SSLVersionTest, RecordCallback) {
3269 for (bool test_server : {true, false}) {
3270 SCOPED_TRACE(test_server);
3271 ResetContexts();
David Benjamin5df5be12017-06-22 19:43:11 -04003272
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003273 bool read_seen = false;
3274 bool write_seen = false;
3275 auto cb = [&](int is_write, int cb_version, int cb_type, const void *buf,
3276 size_t len, SSL *ssl) {
3277 if (cb_type != SSL3_RT_HEADER) {
3278 return;
Martin Kreichgauer72912d22017-08-04 12:06:43 -07003279 }
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003280
3281 // The callback does not report a version for records.
3282 EXPECT_EQ(0, cb_version);
3283
3284 if (is_write) {
3285 write_seen = true;
3286 } else {
3287 read_seen = true;
3288 }
3289
3290 // Sanity-check that the record header is plausible.
3291 CBS cbs;
3292 CBS_init(&cbs, reinterpret_cast<const uint8_t *>(buf), len);
3293 uint8_t type;
3294 uint16_t record_version, length;
3295 ASSERT_TRUE(CBS_get_u8(&cbs, &type));
3296 ASSERT_TRUE(CBS_get_u16(&cbs, &record_version));
Steven Valdez64cc1212017-12-04 11:15:37 -05003297 EXPECT_EQ(record_version & 0xff00, version() & 0xff00);
Martin Kreichgauer1a663262017-08-16 14:54:04 -07003298 if (is_dtls()) {
3299 uint16_t epoch;
3300 ASSERT_TRUE(CBS_get_u16(&cbs, &epoch));
3301 EXPECT_TRUE(epoch == 0 || epoch == 1) << "Invalid epoch: " << epoch;
3302 ASSERT_TRUE(CBS_skip(&cbs, 6));
3303 }
3304 ASSERT_TRUE(CBS_get_u16(&cbs, &length));
3305 EXPECT_EQ(0u, CBS_len(&cbs));
3306 };
3307 using CallbackType = decltype(cb);
3308 SSL_CTX *ctx = test_server ? server_ctx_.get() : client_ctx_.get();
3309 SSL_CTX_set_msg_callback(
3310 ctx, [](int is_write, int cb_version, int cb_type, const void *buf,
3311 size_t len, SSL *ssl, void *arg) {
3312 CallbackType *cb_ptr = reinterpret_cast<CallbackType *>(arg);
3313 (*cb_ptr)(is_write, cb_version, cb_type, buf, len, ssl);
3314 });
3315 SSL_CTX_set_msg_callback_arg(ctx, &cb);
3316
3317 ASSERT_TRUE(Connect());
3318
3319 EXPECT_TRUE(read_seen);
3320 EXPECT_TRUE(write_seen);
David Benjamin0fef3052016-11-18 15:11:10 +09003321 }
David Benjamin9ef31f02016-10-31 18:01:13 -04003322}
3323
David Benjamina8614602017-09-06 15:40:19 -04003324TEST_P(SSLVersionTest, GetServerName) {
David Benjamina8614602017-09-06 15:40:19 -04003325 ClientConfig config;
3326 config.servername = "host1";
3327
3328 SSL_CTX_set_tlsext_servername_callback(
3329 server_ctx_.get(), [](SSL *ssl, int *out_alert, void *arg) -> int {
3330 // During the handshake, |SSL_get_servername| must match |config|.
3331 ClientConfig *config_p = reinterpret_cast<ClientConfig *>(arg);
3332 EXPECT_STREQ(config_p->servername.c_str(),
3333 SSL_get_servername(ssl, TLSEXT_NAMETYPE_host_name));
3334 return SSL_TLSEXT_ERR_OK;
3335 });
3336 SSL_CTX_set_tlsext_servername_arg(server_ctx_.get(), &config);
3337
3338 ASSERT_TRUE(Connect(config));
3339 // After the handshake, it must also be available.
3340 EXPECT_STREQ(config.servername.c_str(),
3341 SSL_get_servername(server_.get(), TLSEXT_NAMETYPE_host_name));
3342
3343 // Establish a session under host1.
3344 SSL_CTX_set_session_cache_mode(client_ctx_.get(), SSL_SESS_CACHE_BOTH);
3345 SSL_CTX_set_session_cache_mode(server_ctx_.get(), SSL_SESS_CACHE_BOTH);
3346 bssl::UniquePtr<SSL_SESSION> session =
3347 CreateClientSession(client_ctx_.get(), server_ctx_.get(), config);
3348
3349 // If the client resumes a session with a different name, |SSL_get_servername|
3350 // must return the new name.
3351 ASSERT_TRUE(session);
3352 config.session = session.get();
3353 config.servername = "host2";
3354 ASSERT_TRUE(Connect(config));
3355 EXPECT_STREQ(config.servername.c_str(),
3356 SSL_get_servername(server_.get(), TLSEXT_NAMETYPE_host_name));
3357}
3358
David Benjamin3d8f0802017-09-06 16:12:52 -04003359// Test that session cache mode bits are honored in the client session callback.
3360TEST_P(SSLVersionTest, ClientSessionCacheMode) {
3361 SSL_CTX_set_session_cache_mode(client_ctx_.get(), SSL_SESS_CACHE_OFF);
3362 EXPECT_FALSE(CreateClientSession(client_ctx_.get(), server_ctx_.get()));
3363
3364 SSL_CTX_set_session_cache_mode(client_ctx_.get(), SSL_SESS_CACHE_CLIENT);
3365 EXPECT_TRUE(CreateClientSession(client_ctx_.get(), server_ctx_.get()));
3366
3367 SSL_CTX_set_session_cache_mode(client_ctx_.get(), SSL_SESS_CACHE_SERVER);
3368 EXPECT_FALSE(CreateClientSession(client_ctx_.get(), server_ctx_.get()));
3369}
3370
Steven Valdez777a2392019-02-21 11:30:47 -05003371// Test that all versions survive tiny write buffers. In particular, TLS 1.3
3372// NewSessionTickets are written post-handshake. Servers that block
3373// |SSL_do_handshake| on writing them will deadlock if clients are not draining
3374// the buffer. Test that we do not do this.
3375TEST_P(SSLVersionTest, SmallBuffer) {
3376 // DTLS is a datagram protocol and requires packet-sized buffers.
3377 if (is_dtls()) {
3378 return;
3379 }
3380
3381 // Test both flushing NewSessionTickets with a zero-sized write and
3382 // non-zero-sized write.
3383 for (bool use_zero_write : {false, true}) {
3384 SCOPED_TRACE(use_zero_write);
3385
3386 g_last_session = nullptr;
3387 SSL_CTX_set_session_cache_mode(client_ctx_.get(), SSL_SESS_CACHE_BOTH);
3388 SSL_CTX_sess_set_new_cb(client_ctx_.get(), SaveLastSession);
3389
3390 bssl::UniquePtr<SSL> client(SSL_new(client_ctx_.get())),
3391 server(SSL_new(server_ctx_.get()));
3392 ASSERT_TRUE(client);
3393 ASSERT_TRUE(server);
3394 SSL_set_connect_state(client.get());
3395 SSL_set_accept_state(server.get());
3396
3397 // Use a tiny buffer.
3398 BIO *bio1, *bio2;
3399 ASSERT_TRUE(BIO_new_bio_pair(&bio1, 1, &bio2, 1));
3400
3401 // SSL_set_bio takes ownership.
3402 SSL_set_bio(client.get(), bio1, bio1);
3403 SSL_set_bio(server.get(), bio2, bio2);
3404
3405 ASSERT_TRUE(CompleteHandshakes(client.get(), server.get()));
3406 if (version() >= TLS1_3_VERSION) {
3407 // The post-handshake ticket should not have been processed yet.
3408 EXPECT_FALSE(g_last_session);
3409 }
3410
3411 if (use_zero_write) {
3412 ASSERT_TRUE(FlushNewSessionTickets(client.get(), server.get()));
3413 EXPECT_TRUE(g_last_session);
3414 }
3415
3416 // Send some data from server to client. If |use_zero_write| is false, this
3417 // will also flush the NewSessionTickets.
3418 static const char kMessage[] = "hello world";
3419 char buf[sizeof(kMessage)];
3420 for (;;) {
3421 int server_ret = SSL_write(server.get(), kMessage, sizeof(kMessage));
3422 int server_err = SSL_get_error(server.get(), server_ret);
3423 int client_ret = SSL_read(client.get(), buf, sizeof(buf));
3424 int client_err = SSL_get_error(client.get(), client_ret);
3425
3426 // The server will write a single record, so every iteration should see
3427 // |SSL_ERROR_WANT_WRITE| and |SSL_ERROR_WANT_READ|, until the final
3428 // iteration, where both will complete.
3429 if (server_ret > 0) {
3430 EXPECT_EQ(server_ret, static_cast<int>(sizeof(kMessage)));
3431 EXPECT_EQ(client_ret, static_cast<int>(sizeof(kMessage)));
3432 EXPECT_EQ(Bytes(buf), Bytes(kMessage));
3433 break;
3434 }
3435
3436 ASSERT_EQ(server_ret, -1);
3437 ASSERT_EQ(server_err, SSL_ERROR_WANT_WRITE);
3438 ASSERT_EQ(client_ret, -1);
3439 ASSERT_EQ(client_err, SSL_ERROR_WANT_READ);
3440 }
3441
3442 // The NewSessionTickets should have been flushed and processed.
3443 EXPECT_TRUE(g_last_session);
3444 }
3445}
3446
Adam Langleye1e78132017-01-31 15:24:31 -08003447TEST(SSLTest, AddChainCertHack) {
3448 // Ensure that we don't accidently break the hack that we have in place to
3449 // keep curl and serf happy when they use an |X509| even after transfering
3450 // ownership.
3451
3452 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
3453 ASSERT_TRUE(ctx);
3454 X509 *cert = GetTestCertificate().release();
3455 ASSERT_TRUE(cert);
3456 SSL_CTX_add0_chain_cert(ctx.get(), cert);
3457
3458 // This should not trigger a use-after-free.
3459 X509_cmp(cert, cert);
3460}
3461
David Benjaminb2ff2622017-02-03 17:06:18 -05003462TEST(SSLTest, GetCertificate) {
3463 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
3464 ASSERT_TRUE(ctx);
3465 bssl::UniquePtr<X509> cert = GetTestCertificate();
3466 ASSERT_TRUE(cert);
3467 ASSERT_TRUE(SSL_CTX_use_certificate(ctx.get(), cert.get()));
3468 bssl::UniquePtr<SSL> ssl(SSL_new(ctx.get()));
3469 ASSERT_TRUE(ssl);
3470
3471 X509 *cert2 = SSL_CTX_get0_certificate(ctx.get());
3472 ASSERT_TRUE(cert2);
3473 X509 *cert3 = SSL_get_certificate(ssl.get());
3474 ASSERT_TRUE(cert3);
3475
3476 // The old and new certificates must be identical.
3477 EXPECT_EQ(0, X509_cmp(cert.get(), cert2));
3478 EXPECT_EQ(0, X509_cmp(cert.get(), cert3));
3479
3480 uint8_t *der = nullptr;
3481 long der_len = i2d_X509(cert.get(), &der);
3482 ASSERT_LT(0, der_len);
3483 bssl::UniquePtr<uint8_t> free_der(der);
3484
3485 uint8_t *der2 = nullptr;
3486 long der2_len = i2d_X509(cert2, &der2);
3487 ASSERT_LT(0, der2_len);
3488 bssl::UniquePtr<uint8_t> free_der2(der2);
3489
3490 uint8_t *der3 = nullptr;
3491 long der3_len = i2d_X509(cert3, &der3);
3492 ASSERT_LT(0, der3_len);
3493 bssl::UniquePtr<uint8_t> free_der3(der3);
3494
3495 // They must also encode identically.
David Benjamin7d7554b2017-02-04 11:48:59 -05003496 EXPECT_EQ(Bytes(der, der_len), Bytes(der2, der2_len));
3497 EXPECT_EQ(Bytes(der, der_len), Bytes(der3, der3_len));
David Benjaminb2ff2622017-02-03 17:06:18 -05003498}
3499
Adam Langleyd04ca952017-02-28 11:26:51 -08003500TEST(SSLTest, SetChainAndKeyMismatch) {
3501 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_with_buffers_method()));
3502 ASSERT_TRUE(ctx);
3503
3504 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
3505 ASSERT_TRUE(key);
3506 bssl::UniquePtr<CRYPTO_BUFFER> leaf = GetChainTestCertificateBuffer();
3507 ASSERT_TRUE(leaf);
3508 std::vector<CRYPTO_BUFFER*> chain = {
3509 leaf.get(),
3510 };
3511
3512 // Should fail because |GetTestKey| doesn't match the chain-test certificate.
3513 ASSERT_FALSE(SSL_CTX_set_chain_and_key(ctx.get(), &chain[0], chain.size(),
3514 key.get(), nullptr));
3515 ERR_clear_error();
3516}
3517
3518TEST(SSLTest, SetChainAndKey) {
3519 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLS_with_buffers_method()));
3520 ASSERT_TRUE(client_ctx);
3521 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(TLS_with_buffers_method()));
3522 ASSERT_TRUE(server_ctx);
3523
Adam Langley964256d2020-03-19 11:57:12 -07003524 ASSERT_EQ(nullptr, SSL_CTX_get0_chain(server_ctx.get()));
3525
Adam Langleyd04ca952017-02-28 11:26:51 -08003526 bssl::UniquePtr<EVP_PKEY> key = GetChainTestKey();
3527 ASSERT_TRUE(key);
3528 bssl::UniquePtr<CRYPTO_BUFFER> leaf = GetChainTestCertificateBuffer();
3529 ASSERT_TRUE(leaf);
3530 bssl::UniquePtr<CRYPTO_BUFFER> intermediate =
3531 GetChainTestIntermediateBuffer();
3532 ASSERT_TRUE(intermediate);
3533 std::vector<CRYPTO_BUFFER*> chain = {
3534 leaf.get(), intermediate.get(),
3535 };
3536 ASSERT_TRUE(SSL_CTX_set_chain_and_key(server_ctx.get(), &chain[0],
3537 chain.size(), key.get(), nullptr));
3538
Adam Langley964256d2020-03-19 11:57:12 -07003539 ASSERT_EQ(chain.size(),
3540 sk_CRYPTO_BUFFER_num(SSL_CTX_get0_chain(server_ctx.get())));
3541
David Benjamin3a1dd462017-07-11 16:13:10 -04003542 SSL_CTX_set_custom_verify(
3543 client_ctx.get(), SSL_VERIFY_PEER,
3544 [](SSL *ssl, uint8_t *out_alert) -> ssl_verify_result_t {
3545 return ssl_verify_ok;
3546 });
Adam Langleyd04ca952017-02-28 11:26:51 -08003547
3548 bssl::UniquePtr<SSL> client, server;
3549 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx.get(),
David Benjamina8614602017-09-06 15:40:19 -04003550 server_ctx.get()));
Adam Langleyd04ca952017-02-28 11:26:51 -08003551}
3552
Matthew Braithwaite5301c102018-01-23 12:08:55 -08003553TEST(SSLTest, BuffersFailWithoutCustomVerify) {
3554 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLS_with_buffers_method()));
3555 ASSERT_TRUE(client_ctx);
3556 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(TLS_with_buffers_method()));
3557 ASSERT_TRUE(server_ctx);
3558
3559 bssl::UniquePtr<EVP_PKEY> key = GetChainTestKey();
3560 ASSERT_TRUE(key);
3561 bssl::UniquePtr<CRYPTO_BUFFER> leaf = GetChainTestCertificateBuffer();
3562 ASSERT_TRUE(leaf);
3563 std::vector<CRYPTO_BUFFER*> chain = { leaf.get() };
3564 ASSERT_TRUE(SSL_CTX_set_chain_and_key(server_ctx.get(), &chain[0],
3565 chain.size(), key.get(), nullptr));
3566
3567 // Without SSL_CTX_set_custom_verify(), i.e. with everything in the default
3568 // configuration, certificate verification should fail.
3569 bssl::UniquePtr<SSL> client, server;
3570 ASSERT_FALSE(ConnectClientAndServer(&client, &server, client_ctx.get(),
3571 server_ctx.get()));
3572
3573 // Whereas with a verifier, the connection should succeed.
3574 SSL_CTX_set_custom_verify(
3575 client_ctx.get(), SSL_VERIFY_PEER,
3576 [](SSL *ssl, uint8_t *out_alert) -> ssl_verify_result_t {
3577 return ssl_verify_ok;
3578 });
3579 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx.get(),
3580 server_ctx.get()));
3581}
3582
3583TEST(SSLTest, CustomVerify) {
3584 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLS_with_buffers_method()));
3585 ASSERT_TRUE(client_ctx);
3586 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(TLS_with_buffers_method()));
3587 ASSERT_TRUE(server_ctx);
3588
3589 bssl::UniquePtr<EVP_PKEY> key = GetChainTestKey();
3590 ASSERT_TRUE(key);
3591 bssl::UniquePtr<CRYPTO_BUFFER> leaf = GetChainTestCertificateBuffer();
3592 ASSERT_TRUE(leaf);
3593 std::vector<CRYPTO_BUFFER*> chain = { leaf.get() };
3594 ASSERT_TRUE(SSL_CTX_set_chain_and_key(server_ctx.get(), &chain[0],
3595 chain.size(), key.get(), nullptr));
3596
3597 SSL_CTX_set_custom_verify(
3598 client_ctx.get(), SSL_VERIFY_PEER,
3599 [](SSL *ssl, uint8_t *out_alert) -> ssl_verify_result_t {
3600 return ssl_verify_ok;
3601 });
3602
3603 bssl::UniquePtr<SSL> client, server;
3604 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx.get(),
3605 server_ctx.get()));
3606
3607 // With SSL_VERIFY_PEER, ssl_verify_invalid should result in a dropped
3608 // connection.
3609 SSL_CTX_set_custom_verify(
3610 client_ctx.get(), SSL_VERIFY_PEER,
3611 [](SSL *ssl, uint8_t *out_alert) -> ssl_verify_result_t {
3612 return ssl_verify_invalid;
3613 });
3614
3615 ASSERT_FALSE(ConnectClientAndServer(&client, &server, client_ctx.get(),
3616 server_ctx.get()));
3617
3618 // But with SSL_VERIFY_NONE, ssl_verify_invalid should not cause a dropped
3619 // connection.
3620 SSL_CTX_set_custom_verify(
3621 client_ctx.get(), SSL_VERIFY_NONE,
3622 [](SSL *ssl, uint8_t *out_alert) -> ssl_verify_result_t {
3623 return ssl_verify_invalid;
3624 });
3625
3626 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx.get(),
3627 server_ctx.get()));
3628}
3629
David Benjamin71dfad42017-07-16 17:27:39 -04003630TEST(SSLTest, ClientCABuffers) {
3631 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLS_with_buffers_method()));
3632 ASSERT_TRUE(client_ctx);
3633 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(TLS_with_buffers_method()));
3634 ASSERT_TRUE(server_ctx);
3635
3636 bssl::UniquePtr<EVP_PKEY> key = GetChainTestKey();
3637 ASSERT_TRUE(key);
3638 bssl::UniquePtr<CRYPTO_BUFFER> leaf = GetChainTestCertificateBuffer();
3639 ASSERT_TRUE(leaf);
3640 bssl::UniquePtr<CRYPTO_BUFFER> intermediate =
3641 GetChainTestIntermediateBuffer();
3642 ASSERT_TRUE(intermediate);
3643 std::vector<CRYPTO_BUFFER *> chain = {
3644 leaf.get(),
3645 intermediate.get(),
3646 };
3647 ASSERT_TRUE(SSL_CTX_set_chain_and_key(server_ctx.get(), &chain[0],
3648 chain.size(), key.get(), nullptr));
3649
3650 bssl::UniquePtr<CRYPTO_BUFFER> ca_name(
3651 CRYPTO_BUFFER_new(kTestName, sizeof(kTestName), nullptr));
3652 ASSERT_TRUE(ca_name);
3653 bssl::UniquePtr<STACK_OF(CRYPTO_BUFFER)> ca_names(
3654 sk_CRYPTO_BUFFER_new_null());
3655 ASSERT_TRUE(ca_names);
David Benjamin2908dd12018-06-29 17:46:42 -04003656 ASSERT_TRUE(PushToStack(ca_names.get(), std::move(ca_name)));
David Benjamin71dfad42017-07-16 17:27:39 -04003657 SSL_CTX_set0_client_CAs(server_ctx.get(), ca_names.release());
3658
3659 // Configure client and server to accept all certificates.
3660 SSL_CTX_set_custom_verify(
3661 client_ctx.get(), SSL_VERIFY_PEER,
3662 [](SSL *ssl, uint8_t *out_alert) -> ssl_verify_result_t {
3663 return ssl_verify_ok;
3664 });
3665 SSL_CTX_set_custom_verify(
3666 server_ctx.get(), SSL_VERIFY_PEER,
3667 [](SSL *ssl, uint8_t *out_alert) -> ssl_verify_result_t {
3668 return ssl_verify_ok;
3669 });
3670
3671 bool cert_cb_called = false;
3672 SSL_CTX_set_cert_cb(
3673 client_ctx.get(),
3674 [](SSL *ssl, void *arg) -> int {
David Benjamin5f001d12018-05-08 16:46:48 -04003675 const STACK_OF(CRYPTO_BUFFER) *peer_names =
David Benjamin71dfad42017-07-16 17:27:39 -04003676 SSL_get0_server_requested_CAs(ssl);
3677 EXPECT_EQ(1u, sk_CRYPTO_BUFFER_num(peer_names));
3678 CRYPTO_BUFFER *peer_name = sk_CRYPTO_BUFFER_value(peer_names, 0);
3679 EXPECT_EQ(Bytes(kTestName), Bytes(CRYPTO_BUFFER_data(peer_name),
3680 CRYPTO_BUFFER_len(peer_name)));
3681 *reinterpret_cast<bool *>(arg) = true;
3682 return 1;
3683 },
3684 &cert_cb_called);
3685
3686 bssl::UniquePtr<SSL> client, server;
3687 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx.get(),
David Benjamina8614602017-09-06 15:40:19 -04003688 server_ctx.get()));
David Benjamin71dfad42017-07-16 17:27:39 -04003689 EXPECT_TRUE(cert_cb_called);
3690}
3691
David Benjamin91222b82017-03-09 20:10:56 -05003692// Configuring the empty cipher list, though an error, should still modify the
3693// configuration.
3694TEST(SSLTest, EmptyCipherList) {
3695 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
3696 ASSERT_TRUE(ctx);
3697
3698 // Initially, the cipher list is not empty.
3699 EXPECT_NE(0u, sk_SSL_CIPHER_num(SSL_CTX_get_ciphers(ctx.get())));
3700
3701 // Configuring the empty cipher list fails.
3702 EXPECT_FALSE(SSL_CTX_set_cipher_list(ctx.get(), ""));
3703 ERR_clear_error();
3704
3705 // But the cipher list is still updated to empty.
3706 EXPECT_EQ(0u, sk_SSL_CIPHER_num(SSL_CTX_get_ciphers(ctx.get())));
3707}
3708
Adam Langley4c341d02017-03-08 19:33:21 -08003709// ssl_test_ticket_aead_failure_mode enumerates the possible ways in which the
3710// test |SSL_TICKET_AEAD_METHOD| can fail.
3711enum ssl_test_ticket_aead_failure_mode {
3712 ssl_test_ticket_aead_ok = 0,
3713 ssl_test_ticket_aead_seal_fail,
3714 ssl_test_ticket_aead_open_soft_fail,
3715 ssl_test_ticket_aead_open_hard_fail,
3716};
3717
3718struct ssl_test_ticket_aead_state {
3719 unsigned retry_count;
3720 ssl_test_ticket_aead_failure_mode failure_mode;
3721};
3722
3723static int ssl_test_ticket_aead_ex_index_dup(CRYPTO_EX_DATA *to,
3724 const CRYPTO_EX_DATA *from,
3725 void **from_d, int index,
3726 long argl, void *argp) {
3727 abort();
3728}
3729
3730static void ssl_test_ticket_aead_ex_index_free(void *parent, void *ptr,
3731 CRYPTO_EX_DATA *ad, int index,
3732 long argl, void *argp) {
3733 auto state = reinterpret_cast<ssl_test_ticket_aead_state*>(ptr);
3734 if (state == nullptr) {
3735 return;
3736 }
3737
3738 OPENSSL_free(state);
3739}
3740
3741static CRYPTO_once_t g_ssl_test_ticket_aead_ex_index_once = CRYPTO_ONCE_INIT;
3742static int g_ssl_test_ticket_aead_ex_index;
3743
3744static int ssl_test_ticket_aead_get_ex_index() {
3745 CRYPTO_once(&g_ssl_test_ticket_aead_ex_index_once, [] {
3746 g_ssl_test_ticket_aead_ex_index = SSL_get_ex_new_index(
3747 0, nullptr, nullptr, ssl_test_ticket_aead_ex_index_dup,
3748 ssl_test_ticket_aead_ex_index_free);
3749 });
3750 return g_ssl_test_ticket_aead_ex_index;
3751}
3752
3753static size_t ssl_test_ticket_aead_max_overhead(SSL *ssl) {
3754 return 1;
3755}
3756
3757static int ssl_test_ticket_aead_seal(SSL *ssl, uint8_t *out, size_t *out_len,
3758 size_t max_out_len, const uint8_t *in,
3759 size_t in_len) {
3760 auto state = reinterpret_cast<ssl_test_ticket_aead_state *>(
3761 SSL_get_ex_data(ssl, ssl_test_ticket_aead_get_ex_index()));
3762
3763 if (state->failure_mode == ssl_test_ticket_aead_seal_fail ||
3764 max_out_len < in_len + 1) {
3765 return 0;
3766 }
3767
3768 OPENSSL_memmove(out, in, in_len);
3769 out[in_len] = 0xff;
3770 *out_len = in_len + 1;
3771
3772 return 1;
3773}
3774
3775static ssl_ticket_aead_result_t ssl_test_ticket_aead_open(
3776 SSL *ssl, uint8_t *out, size_t *out_len, size_t max_out_len,
3777 const uint8_t *in, size_t in_len) {
3778 auto state = reinterpret_cast<ssl_test_ticket_aead_state *>(
3779 SSL_get_ex_data(ssl, ssl_test_ticket_aead_get_ex_index()));
3780
3781 if (state->retry_count > 0) {
3782 state->retry_count--;
3783 return ssl_ticket_aead_retry;
3784 }
3785
3786 switch (state->failure_mode) {
3787 case ssl_test_ticket_aead_ok:
3788 break;
3789 case ssl_test_ticket_aead_seal_fail:
3790 // If |seal| failed then there shouldn't be any ticket to try and
3791 // decrypt.
3792 abort();
3793 break;
3794 case ssl_test_ticket_aead_open_soft_fail:
3795 return ssl_ticket_aead_ignore_ticket;
3796 case ssl_test_ticket_aead_open_hard_fail:
3797 return ssl_ticket_aead_error;
3798 }
3799
3800 if (in_len == 0 || in[in_len - 1] != 0xff) {
3801 return ssl_ticket_aead_ignore_ticket;
3802 }
3803
3804 if (max_out_len < in_len - 1) {
3805 return ssl_ticket_aead_error;
3806 }
3807
3808 OPENSSL_memmove(out, in, in_len - 1);
3809 *out_len = in_len - 1;
3810 return ssl_ticket_aead_success;
3811}
3812
3813static const SSL_TICKET_AEAD_METHOD kSSLTestTicketMethod = {
3814 ssl_test_ticket_aead_max_overhead,
3815 ssl_test_ticket_aead_seal,
3816 ssl_test_ticket_aead_open,
3817};
3818
3819static void ConnectClientAndServerWithTicketMethod(
3820 bssl::UniquePtr<SSL> *out_client, bssl::UniquePtr<SSL> *out_server,
3821 SSL_CTX *client_ctx, SSL_CTX *server_ctx, unsigned retry_count,
3822 ssl_test_ticket_aead_failure_mode failure_mode, SSL_SESSION *session) {
3823 bssl::UniquePtr<SSL> client(SSL_new(client_ctx)), server(SSL_new(server_ctx));
3824 ASSERT_TRUE(client);
3825 ASSERT_TRUE(server);
3826 SSL_set_connect_state(client.get());
3827 SSL_set_accept_state(server.get());
3828
3829 auto state = reinterpret_cast<ssl_test_ticket_aead_state *>(
3830 OPENSSL_malloc(sizeof(ssl_test_ticket_aead_state)));
3831 ASSERT_TRUE(state);
3832 OPENSSL_memset(state, 0, sizeof(ssl_test_ticket_aead_state));
3833 state->retry_count = retry_count;
3834 state->failure_mode = failure_mode;
3835
3836 ASSERT_TRUE(SSL_set_ex_data(server.get(), ssl_test_ticket_aead_get_ex_index(),
3837 state));
3838
3839 SSL_set_session(client.get(), session);
3840
3841 BIO *bio1, *bio2;
3842 ASSERT_TRUE(BIO_new_bio_pair(&bio1, 0, &bio2, 0));
3843
3844 // SSL_set_bio takes ownership.
3845 SSL_set_bio(client.get(), bio1, bio1);
3846 SSL_set_bio(server.get(), bio2, bio2);
3847
3848 if (CompleteHandshakes(client.get(), server.get())) {
3849 *out_client = std::move(client);
3850 *out_server = std::move(server);
3851 } else {
3852 out_client->reset();
3853 out_server->reset();
3854 }
3855}
3856
David Benjaminc9775322018-04-13 16:39:12 -04003857using TicketAEADMethodParam =
3858 testing::tuple<uint16_t, unsigned, ssl_test_ticket_aead_failure_mode>;
3859
Adam Langley4c341d02017-03-08 19:33:21 -08003860class TicketAEADMethodTest
David Benjaminc9775322018-04-13 16:39:12 -04003861 : public ::testing::TestWithParam<TicketAEADMethodParam> {};
Adam Langley4c341d02017-03-08 19:33:21 -08003862
3863TEST_P(TicketAEADMethodTest, Resume) {
3864 bssl::UniquePtr<X509> cert = GetTestCertificate();
3865 ASSERT_TRUE(cert);
3866 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
3867 ASSERT_TRUE(key);
3868
3869 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(TLS_method()));
3870 ASSERT_TRUE(server_ctx);
3871 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLS_method()));
3872 ASSERT_TRUE(client_ctx);
3873
3874 const uint16_t version = testing::get<0>(GetParam());
3875 const unsigned retry_count = testing::get<1>(GetParam());
3876 const ssl_test_ticket_aead_failure_mode failure_mode =
3877 testing::get<2>(GetParam());
3878
3879 ASSERT_TRUE(SSL_CTX_use_certificate(server_ctx.get(), cert.get()));
3880 ASSERT_TRUE(SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()));
3881 ASSERT_TRUE(SSL_CTX_set_min_proto_version(client_ctx.get(), version));
3882 ASSERT_TRUE(SSL_CTX_set_max_proto_version(client_ctx.get(), version));
3883 ASSERT_TRUE(SSL_CTX_set_min_proto_version(server_ctx.get(), version));
3884 ASSERT_TRUE(SSL_CTX_set_max_proto_version(server_ctx.get(), version));
3885
3886 SSL_CTX_set_session_cache_mode(client_ctx.get(), SSL_SESS_CACHE_BOTH);
3887 SSL_CTX_set_session_cache_mode(server_ctx.get(), SSL_SESS_CACHE_BOTH);
3888 SSL_CTX_set_current_time_cb(client_ctx.get(), FrozenTimeCallback);
3889 SSL_CTX_set_current_time_cb(server_ctx.get(), FrozenTimeCallback);
David Benjamin707af292017-03-10 17:47:18 -05003890 SSL_CTX_sess_set_new_cb(client_ctx.get(), SaveLastSession);
Adam Langley4c341d02017-03-08 19:33:21 -08003891
3892 SSL_CTX_set_ticket_aead_method(server_ctx.get(), &kSSLTestTicketMethod);
3893
3894 bssl::UniquePtr<SSL> client, server;
3895 ConnectClientAndServerWithTicketMethod(&client, &server, client_ctx.get(),
3896 server_ctx.get(), retry_count,
3897 failure_mode, nullptr);
3898 switch (failure_mode) {
3899 case ssl_test_ticket_aead_ok:
3900 case ssl_test_ticket_aead_open_hard_fail:
3901 case ssl_test_ticket_aead_open_soft_fail:
3902 ASSERT_TRUE(client);
3903 break;
3904 case ssl_test_ticket_aead_seal_fail:
3905 EXPECT_FALSE(client);
3906 return;
3907 }
3908 EXPECT_FALSE(SSL_session_reused(client.get()));
3909 EXPECT_FALSE(SSL_session_reused(server.get()));
3910
Steven Valdez777a2392019-02-21 11:30:47 -05003911 ASSERT_TRUE(FlushNewSessionTickets(client.get(), server.get()));
David Benjamin707af292017-03-10 17:47:18 -05003912 bssl::UniquePtr<SSL_SESSION> session = std::move(g_last_session);
Adam Langley4c341d02017-03-08 19:33:21 -08003913 ConnectClientAndServerWithTicketMethod(&client, &server, client_ctx.get(),
3914 server_ctx.get(), retry_count,
David Benjamin707af292017-03-10 17:47:18 -05003915 failure_mode, session.get());
Adam Langley4c341d02017-03-08 19:33:21 -08003916 switch (failure_mode) {
3917 case ssl_test_ticket_aead_ok:
3918 ASSERT_TRUE(client);
3919 EXPECT_TRUE(SSL_session_reused(client.get()));
3920 EXPECT_TRUE(SSL_session_reused(server.get()));
3921 break;
3922 case ssl_test_ticket_aead_seal_fail:
3923 abort();
3924 break;
3925 case ssl_test_ticket_aead_open_hard_fail:
3926 EXPECT_FALSE(client);
3927 break;
3928 case ssl_test_ticket_aead_open_soft_fail:
3929 ASSERT_TRUE(client);
3930 EXPECT_FALSE(SSL_session_reused(client.get()));
3931 EXPECT_FALSE(SSL_session_reused(server.get()));
3932 }
3933}
3934
David Benjaminc9775322018-04-13 16:39:12 -04003935std::string TicketAEADMethodParamToString(
3936 const testing::TestParamInfo<TicketAEADMethodParam> &params) {
3937 std::string ret = GetVersionName(std::get<0>(params.param));
3938 // GTest only allows alphanumeric characters and '_' in the parameter
3939 // string. Additionally filter out the 'v' to get "TLS13" over "TLSv13".
3940 for (auto it = ret.begin(); it != ret.end();) {
3941 if (*it == '.' || *it == 'v') {
3942 it = ret.erase(it);
3943 } else {
3944 ++it;
3945 }
3946 }
3947 char retry_count[256];
3948 snprintf(retry_count, sizeof(retry_count), "%d", std::get<1>(params.param));
3949 ret += "_";
3950 ret += retry_count;
3951 ret += "Retries_";
3952 switch (std::get<2>(params.param)) {
3953 case ssl_test_ticket_aead_ok:
3954 ret += "OK";
3955 break;
3956 case ssl_test_ticket_aead_seal_fail:
3957 ret += "SealFail";
3958 break;
3959 case ssl_test_ticket_aead_open_soft_fail:
3960 ret += "OpenSoftFail";
3961 break;
3962 case ssl_test_ticket_aead_open_hard_fail:
3963 ret += "OpenHardFail";
3964 break;
3965 }
3966 return ret;
3967}
3968
David Benjaminbe7006a2019-04-09 18:05:02 -05003969INSTANTIATE_TEST_SUITE_P(
Adam Langley4c341d02017-03-08 19:33:21 -08003970 TicketAEADMethodTests, TicketAEADMethodTest,
David Benjaminc9775322018-04-13 16:39:12 -04003971 testing::Combine(testing::Values(TLS1_2_VERSION, TLS1_3_VERSION),
3972 testing::Values(0, 1, 2),
3973 testing::Values(ssl_test_ticket_aead_ok,
3974 ssl_test_ticket_aead_seal_fail,
3975 ssl_test_ticket_aead_open_soft_fail,
3976 ssl_test_ticket_aead_open_hard_fail)),
3977 TicketAEADMethodParamToString);
Adam Langley4c341d02017-03-08 19:33:21 -08003978
David Benjaminca743582017-06-15 17:51:35 -04003979TEST(SSLTest, SelectNextProto) {
3980 uint8_t *result;
3981 uint8_t result_len;
3982
3983 // If there is an overlap, it should be returned.
3984 EXPECT_EQ(OPENSSL_NPN_NEGOTIATED,
3985 SSL_select_next_proto(&result, &result_len,
3986 (const uint8_t *)"\1a\2bb\3ccc", 9,
3987 (const uint8_t *)"\1x\1y\1a\1z", 8));
3988 EXPECT_EQ(Bytes("a"), Bytes(result, result_len));
3989
3990 EXPECT_EQ(OPENSSL_NPN_NEGOTIATED,
3991 SSL_select_next_proto(&result, &result_len,
3992 (const uint8_t *)"\1a\2bb\3ccc", 9,
3993 (const uint8_t *)"\1x\1y\2bb\1z", 9));
3994 EXPECT_EQ(Bytes("bb"), Bytes(result, result_len));
3995
3996 EXPECT_EQ(OPENSSL_NPN_NEGOTIATED,
3997 SSL_select_next_proto(&result, &result_len,
3998 (const uint8_t *)"\1a\2bb\3ccc", 9,
3999 (const uint8_t *)"\1x\1y\3ccc\1z", 10));
4000 EXPECT_EQ(Bytes("ccc"), Bytes(result, result_len));
4001
4002 // Peer preference order takes precedence over local.
4003 EXPECT_EQ(OPENSSL_NPN_NEGOTIATED,
4004 SSL_select_next_proto(&result, &result_len,
4005 (const uint8_t *)"\1a\2bb\3ccc", 9,
4006 (const uint8_t *)"\3ccc\2bb\1a", 9));
4007 EXPECT_EQ(Bytes("a"), Bytes(result, result_len));
4008
4009 // If there is no overlap, return the first local protocol.
4010 EXPECT_EQ(OPENSSL_NPN_NO_OVERLAP,
4011 SSL_select_next_proto(&result, &result_len,
4012 (const uint8_t *)"\1a\2bb\3ccc", 9,
4013 (const uint8_t *)"\1x\2yy\3zzz", 9));
4014 EXPECT_EQ(Bytes("x"), Bytes(result, result_len));
4015
4016 EXPECT_EQ(OPENSSL_NPN_NO_OVERLAP,
4017 SSL_select_next_proto(&result, &result_len, nullptr, 0,
4018 (const uint8_t *)"\1x\2yy\3zzz", 9));
4019 EXPECT_EQ(Bytes("x"), Bytes(result, result_len));
4020}
4021
Martin Kreichgauer17c30572017-07-18 12:42:18 -07004022TEST(SSLTest, SealRecord) {
Matthew Braithwaite58d56f42019-11-04 13:20:01 -08004023 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLSv1_2_method())),
4024 server_ctx(SSL_CTX_new(TLSv1_2_method()));
Martin Kreichgauer17c30572017-07-18 12:42:18 -07004025 ASSERT_TRUE(client_ctx);
4026 ASSERT_TRUE(server_ctx);
4027
4028 bssl::UniquePtr<X509> cert = GetTestCertificate();
4029 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
4030 ASSERT_TRUE(cert);
4031 ASSERT_TRUE(key);
4032 ASSERT_TRUE(SSL_CTX_use_certificate(server_ctx.get(), cert.get()));
4033 ASSERT_TRUE(SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()));
4034
4035 bssl::UniquePtr<SSL> client, server;
4036 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx.get(),
David Benjamina8614602017-09-06 15:40:19 -04004037 server_ctx.get()));
Martin Kreichgauer17c30572017-07-18 12:42:18 -07004038
4039 const std::vector<uint8_t> record = {1, 2, 3, 4, 5};
4040 std::vector<uint8_t> prefix(
4041 bssl::SealRecordPrefixLen(client.get(), record.size())),
Martin Kreichgauerabbf3652017-07-21 16:27:54 -07004042 body(record.size()),
4043 suffix(bssl::SealRecordSuffixLen(client.get(), record.size()));
Martin Kreichgauer17c30572017-07-18 12:42:18 -07004044 ASSERT_TRUE(bssl::SealRecord(client.get(), bssl::MakeSpan(prefix),
4045 bssl::MakeSpan(body), bssl::MakeSpan(suffix),
Martin Kreichgauerabbf3652017-07-21 16:27:54 -07004046 record));
Martin Kreichgauer17c30572017-07-18 12:42:18 -07004047
4048 std::vector<uint8_t> sealed;
4049 sealed.insert(sealed.end(), prefix.begin(), prefix.end());
4050 sealed.insert(sealed.end(), body.begin(), body.end());
4051 sealed.insert(sealed.end(), suffix.begin(), suffix.end());
4052 std::vector<uint8_t> sealed_copy = sealed;
4053
4054 bssl::Span<uint8_t> plaintext;
4055 size_t record_len;
4056 uint8_t alert = 255;
4057 EXPECT_EQ(bssl::OpenRecord(server.get(), &plaintext, &record_len, &alert,
4058 bssl::MakeSpan(sealed)),
4059 bssl::OpenRecordResult::kOK);
4060 EXPECT_EQ(record_len, sealed.size());
4061 EXPECT_EQ(plaintext, record);
4062 EXPECT_EQ(255, alert);
4063}
4064
4065TEST(SSLTest, SealRecordInPlace) {
Matthew Braithwaite58d56f42019-11-04 13:20:01 -08004066 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLSv1_2_method())),
4067 server_ctx(SSL_CTX_new(TLSv1_2_method()));
Martin Kreichgauer17c30572017-07-18 12:42:18 -07004068 ASSERT_TRUE(client_ctx);
4069 ASSERT_TRUE(server_ctx);
4070
4071 bssl::UniquePtr<X509> cert = GetTestCertificate();
4072 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
4073 ASSERT_TRUE(cert);
4074 ASSERT_TRUE(key);
4075 ASSERT_TRUE(SSL_CTX_use_certificate(server_ctx.get(), cert.get()));
4076 ASSERT_TRUE(SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()));
4077
4078 bssl::UniquePtr<SSL> client, server;
4079 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx.get(),
David Benjamina8614602017-09-06 15:40:19 -04004080 server_ctx.get()));
Martin Kreichgauer17c30572017-07-18 12:42:18 -07004081
4082 const std::vector<uint8_t> plaintext = {1, 2, 3, 4, 5};
4083 std::vector<uint8_t> record = plaintext;
4084 std::vector<uint8_t> prefix(
4085 bssl::SealRecordPrefixLen(client.get(), record.size())),
Martin Kreichgauerabbf3652017-07-21 16:27:54 -07004086 suffix(bssl::SealRecordSuffixLen(client.get(), record.size()));
Martin Kreichgauer17c30572017-07-18 12:42:18 -07004087 ASSERT_TRUE(bssl::SealRecord(client.get(), bssl::MakeSpan(prefix),
4088 bssl::MakeSpan(record), bssl::MakeSpan(suffix),
Martin Kreichgauerabbf3652017-07-21 16:27:54 -07004089 record));
Martin Kreichgauer17c30572017-07-18 12:42:18 -07004090 record.insert(record.begin(), prefix.begin(), prefix.end());
4091 record.insert(record.end(), suffix.begin(), suffix.end());
4092
4093 bssl::Span<uint8_t> result;
4094 size_t record_len;
4095 uint8_t alert;
4096 EXPECT_EQ(bssl::OpenRecord(server.get(), &result, &record_len, &alert,
4097 bssl::MakeSpan(record)),
4098 bssl::OpenRecordResult::kOK);
4099 EXPECT_EQ(record_len, record.size());
4100 EXPECT_EQ(plaintext, result);
4101}
4102
4103TEST(SSLTest, SealRecordTrailingData) {
Matthew Braithwaite58d56f42019-11-04 13:20:01 -08004104 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLSv1_2_method())),
4105 server_ctx(SSL_CTX_new(TLSv1_2_method()));
Martin Kreichgauer17c30572017-07-18 12:42:18 -07004106 ASSERT_TRUE(client_ctx);
4107 ASSERT_TRUE(server_ctx);
4108
4109 bssl::UniquePtr<X509> cert = GetTestCertificate();
4110 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
4111 ASSERT_TRUE(cert);
4112 ASSERT_TRUE(key);
4113 ASSERT_TRUE(SSL_CTX_use_certificate(server_ctx.get(), cert.get()));
4114 ASSERT_TRUE(SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()));
4115
4116 bssl::UniquePtr<SSL> client, server;
4117 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx.get(),
David Benjamina8614602017-09-06 15:40:19 -04004118 server_ctx.get()));
Martin Kreichgauer17c30572017-07-18 12:42:18 -07004119
4120 const std::vector<uint8_t> plaintext = {1, 2, 3, 4, 5};
4121 std::vector<uint8_t> record = plaintext;
4122 std::vector<uint8_t> prefix(
4123 bssl::SealRecordPrefixLen(client.get(), record.size())),
Martin Kreichgauerabbf3652017-07-21 16:27:54 -07004124 suffix(bssl::SealRecordSuffixLen(client.get(), record.size()));
Martin Kreichgauer17c30572017-07-18 12:42:18 -07004125 ASSERT_TRUE(bssl::SealRecord(client.get(), bssl::MakeSpan(prefix),
4126 bssl::MakeSpan(record), bssl::MakeSpan(suffix),
Martin Kreichgauerabbf3652017-07-21 16:27:54 -07004127 record));
Martin Kreichgauer17c30572017-07-18 12:42:18 -07004128 record.insert(record.begin(), prefix.begin(), prefix.end());
4129 record.insert(record.end(), suffix.begin(), suffix.end());
4130 record.insert(record.end(), {5, 4, 3, 2, 1});
4131
4132 bssl::Span<uint8_t> result;
4133 size_t record_len;
4134 uint8_t alert;
4135 EXPECT_EQ(bssl::OpenRecord(server.get(), &result, &record_len, &alert,
4136 bssl::MakeSpan(record)),
4137 bssl::OpenRecordResult::kOK);
4138 EXPECT_EQ(record_len, record.size() - 5);
4139 EXPECT_EQ(plaintext, result);
4140}
4141
4142TEST(SSLTest, SealRecordInvalidSpanSize) {
Matthew Braithwaite58d56f42019-11-04 13:20:01 -08004143 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLSv1_2_method())),
4144 server_ctx(SSL_CTX_new(TLSv1_2_method()));
Martin Kreichgauer17c30572017-07-18 12:42:18 -07004145 ASSERT_TRUE(client_ctx);
4146 ASSERT_TRUE(server_ctx);
4147
4148 bssl::UniquePtr<X509> cert = GetTestCertificate();
4149 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
4150 ASSERT_TRUE(cert);
4151 ASSERT_TRUE(key);
4152 ASSERT_TRUE(SSL_CTX_use_certificate(server_ctx.get(), cert.get()));
4153 ASSERT_TRUE(SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()));
4154
4155 bssl::UniquePtr<SSL> client, server;
4156 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx.get(),
David Benjamina8614602017-09-06 15:40:19 -04004157 server_ctx.get()));
Martin Kreichgauer17c30572017-07-18 12:42:18 -07004158
4159 std::vector<uint8_t> record = {1, 2, 3, 4, 5};
4160 std::vector<uint8_t> prefix(
4161 bssl::SealRecordPrefixLen(client.get(), record.size())),
Martin Kreichgauerabbf3652017-07-21 16:27:54 -07004162 body(record.size()),
4163 suffix(bssl::SealRecordSuffixLen(client.get(), record.size()));
Martin Kreichgauer17c30572017-07-18 12:42:18 -07004164
4165 auto expect_err = []() {
4166 int err = ERR_get_error();
4167 EXPECT_EQ(ERR_GET_LIB(err), ERR_LIB_SSL);
4168 EXPECT_EQ(ERR_GET_REASON(err), SSL_R_BUFFER_TOO_SMALL);
4169 ERR_clear_error();
4170 };
4171 EXPECT_FALSE(bssl::SealRecord(
4172 client.get(), bssl::MakeSpan(prefix.data(), prefix.size() - 1),
Martin Kreichgauerabbf3652017-07-21 16:27:54 -07004173 bssl::MakeSpan(record), bssl::MakeSpan(suffix), record));
Martin Kreichgauer17c30572017-07-18 12:42:18 -07004174 expect_err();
4175 EXPECT_FALSE(bssl::SealRecord(
4176 client.get(), bssl::MakeSpan(prefix.data(), prefix.size() + 1),
Martin Kreichgauerabbf3652017-07-21 16:27:54 -07004177 bssl::MakeSpan(record), bssl::MakeSpan(suffix), record));
Martin Kreichgauer17c30572017-07-18 12:42:18 -07004178 expect_err();
4179
4180 EXPECT_FALSE(
4181 bssl::SealRecord(client.get(), bssl::MakeSpan(prefix),
4182 bssl::MakeSpan(record.data(), record.size() - 1),
Martin Kreichgauerabbf3652017-07-21 16:27:54 -07004183 bssl::MakeSpan(suffix), record));
Martin Kreichgauer17c30572017-07-18 12:42:18 -07004184 expect_err();
4185 EXPECT_FALSE(
4186 bssl::SealRecord(client.get(), bssl::MakeSpan(prefix),
4187 bssl::MakeSpan(record.data(), record.size() + 1),
Martin Kreichgauerabbf3652017-07-21 16:27:54 -07004188 bssl::MakeSpan(suffix), record));
Martin Kreichgauer17c30572017-07-18 12:42:18 -07004189 expect_err();
4190
4191 EXPECT_FALSE(bssl::SealRecord(
4192 client.get(), bssl::MakeSpan(prefix), bssl::MakeSpan(record),
Martin Kreichgauerabbf3652017-07-21 16:27:54 -07004193 bssl::MakeSpan(suffix.data(), suffix.size() - 1), record));
Martin Kreichgauer17c30572017-07-18 12:42:18 -07004194 expect_err();
4195 EXPECT_FALSE(bssl::SealRecord(
4196 client.get(), bssl::MakeSpan(prefix), bssl::MakeSpan(record),
Martin Kreichgauerabbf3652017-07-21 16:27:54 -07004197 bssl::MakeSpan(suffix.data(), suffix.size() + 1), record));
Martin Kreichgauer17c30572017-07-18 12:42:18 -07004198 expect_err();
4199}
4200
David Benjamin617b8182017-08-29 15:33:10 -04004201// The client should gracefully handle no suitable ciphers being enabled.
4202TEST(SSLTest, NoCiphersAvailable) {
4203 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
4204 ASSERT_TRUE(ctx);
4205
4206 // Configure |client_ctx| with a cipher list that does not intersect with its
4207 // version configuration.
4208 ASSERT_TRUE(SSL_CTX_set_strict_cipher_list(
4209 ctx.get(), "TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256"));
4210 ASSERT_TRUE(SSL_CTX_set_max_proto_version(ctx.get(), TLS1_1_VERSION));
4211
4212 bssl::UniquePtr<SSL> ssl(SSL_new(ctx.get()));
4213 ASSERT_TRUE(ssl);
4214 SSL_set_connect_state(ssl.get());
4215
4216 UniquePtr<BIO> rbio(BIO_new(BIO_s_mem())), wbio(BIO_new(BIO_s_mem()));
4217 ASSERT_TRUE(rbio);
4218 ASSERT_TRUE(wbio);
4219 SSL_set0_rbio(ssl.get(), rbio.release());
4220 SSL_set0_wbio(ssl.get(), wbio.release());
4221
4222 int ret = SSL_do_handshake(ssl.get());
4223 EXPECT_EQ(-1, ret);
4224 EXPECT_EQ(SSL_ERROR_SSL, SSL_get_error(ssl.get(), ret));
4225 uint32_t err = ERR_get_error();
4226 EXPECT_EQ(ERR_LIB_SSL, ERR_GET_LIB(err));
4227 EXPECT_EQ(SSL_R_NO_CIPHERS_AVAILABLE, ERR_GET_REASON(err));
4228}
4229
David Benjamina4bafd32017-10-03 15:06:29 -04004230TEST_P(SSLVersionTest, SessionVersion) {
4231 SSL_CTX_set_session_cache_mode(client_ctx_.get(), SSL_SESS_CACHE_BOTH);
4232 SSL_CTX_set_session_cache_mode(server_ctx_.get(), SSL_SESS_CACHE_BOTH);
4233
4234 bssl::UniquePtr<SSL_SESSION> session =
4235 CreateClientSession(client_ctx_.get(), server_ctx_.get());
4236 ASSERT_TRUE(session);
4237 EXPECT_EQ(version(), SSL_SESSION_get_protocol_version(session.get()));
4238
4239 // Sessions in TLS 1.3 and later should be single-use.
4240 EXPECT_EQ(version() == TLS1_3_VERSION,
4241 !!SSL_SESSION_should_be_single_use(session.get()));
4242
4243 // Making fake sessions for testing works.
4244 session.reset(SSL_SESSION_new(client_ctx_.get()));
4245 ASSERT_TRUE(session);
4246 ASSERT_TRUE(SSL_SESSION_set_protocol_version(session.get(), version()));
4247 EXPECT_EQ(version(), SSL_SESSION_get_protocol_version(session.get()));
4248}
4249
David Benjaminfdb7a352017-10-12 17:34:18 -04004250TEST_P(SSLVersionTest, SSLPending) {
4251 UniquePtr<SSL> ssl(SSL_new(client_ctx_.get()));
4252 ASSERT_TRUE(ssl);
4253 EXPECT_EQ(0, SSL_pending(ssl.get()));
4254
4255 ASSERT_TRUE(Connect());
4256 EXPECT_EQ(0, SSL_pending(client_.get()));
4257
4258 ASSERT_EQ(5, SSL_write(server_.get(), "hello", 5));
4259 ASSERT_EQ(5, SSL_write(server_.get(), "world", 5));
4260 EXPECT_EQ(0, SSL_pending(client_.get()));
4261
4262 char buf[10];
4263 ASSERT_EQ(1, SSL_peek(client_.get(), buf, 1));
4264 EXPECT_EQ(5, SSL_pending(client_.get()));
4265
4266 ASSERT_EQ(1, SSL_read(client_.get(), buf, 1));
4267 EXPECT_EQ(4, SSL_pending(client_.get()));
4268
4269 ASSERT_EQ(4, SSL_read(client_.get(), buf, 10));
4270 EXPECT_EQ(0, SSL_pending(client_.get()));
4271
4272 ASSERT_EQ(2, SSL_read(client_.get(), buf, 2));
4273 EXPECT_EQ(3, SSL_pending(client_.get()));
4274}
4275
David Benjamina031b612017-10-11 20:48:25 -04004276// Test that post-handshake tickets consumed by |SSL_shutdown| are ignored.
4277TEST(SSLTest, ShutdownIgnoresTickets) {
4278 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
4279 ASSERT_TRUE(ctx);
4280 ASSERT_TRUE(SSL_CTX_set_min_proto_version(ctx.get(), TLS1_3_VERSION));
4281 ASSERT_TRUE(SSL_CTX_set_max_proto_version(ctx.get(), TLS1_3_VERSION));
4282
4283 bssl::UniquePtr<X509> cert = GetTestCertificate();
4284 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
4285 ASSERT_TRUE(cert);
4286 ASSERT_TRUE(key);
4287 ASSERT_TRUE(SSL_CTX_use_certificate(ctx.get(), cert.get()));
4288 ASSERT_TRUE(SSL_CTX_use_PrivateKey(ctx.get(), key.get()));
4289
4290 SSL_CTX_set_session_cache_mode(ctx.get(), SSL_SESS_CACHE_BOTH);
4291
4292 bssl::UniquePtr<SSL> client, server;
4293 ASSERT_TRUE(ConnectClientAndServer(&client, &server, ctx.get(), ctx.get()));
4294
4295 SSL_CTX_sess_set_new_cb(ctx.get(), [](SSL *ssl, SSL_SESSION *session) -> int {
4296 ADD_FAILURE() << "New session callback called during SSL_shutdown";
4297 return 0;
4298 });
4299
4300 // Send close_notify.
4301 EXPECT_EQ(0, SSL_shutdown(server.get()));
4302 EXPECT_EQ(0, SSL_shutdown(client.get()));
4303
4304 // Receive close_notify.
4305 EXPECT_EQ(1, SSL_shutdown(server.get()));
4306 EXPECT_EQ(1, SSL_shutdown(client.get()));
4307}
4308
David Benjamin6cc352e2017-11-02 17:21:39 -04004309TEST(SSLTest, SignatureAlgorithmProperties) {
4310 EXPECT_EQ(EVP_PKEY_NONE, SSL_get_signature_algorithm_key_type(0x1234));
4311 EXPECT_EQ(nullptr, SSL_get_signature_algorithm_digest(0x1234));
4312 EXPECT_FALSE(SSL_is_signature_algorithm_rsa_pss(0x1234));
4313
4314 EXPECT_EQ(EVP_PKEY_RSA,
4315 SSL_get_signature_algorithm_key_type(SSL_SIGN_RSA_PKCS1_MD5_SHA1));
4316 EXPECT_EQ(EVP_md5_sha1(),
4317 SSL_get_signature_algorithm_digest(SSL_SIGN_RSA_PKCS1_MD5_SHA1));
4318 EXPECT_FALSE(SSL_is_signature_algorithm_rsa_pss(SSL_SIGN_RSA_PKCS1_MD5_SHA1));
4319
4320 EXPECT_EQ(EVP_PKEY_EC, SSL_get_signature_algorithm_key_type(
4321 SSL_SIGN_ECDSA_SECP256R1_SHA256));
4322 EXPECT_EQ(EVP_sha256(), SSL_get_signature_algorithm_digest(
4323 SSL_SIGN_ECDSA_SECP256R1_SHA256));
4324 EXPECT_FALSE(
4325 SSL_is_signature_algorithm_rsa_pss(SSL_SIGN_ECDSA_SECP256R1_SHA256));
4326
4327 EXPECT_EQ(EVP_PKEY_RSA,
David Benjamin6879e192018-04-13 16:01:02 -04004328 SSL_get_signature_algorithm_key_type(SSL_SIGN_RSA_PSS_RSAE_SHA384));
David Benjamin6cc352e2017-11-02 17:21:39 -04004329 EXPECT_EQ(EVP_sha384(),
David Benjamin6879e192018-04-13 16:01:02 -04004330 SSL_get_signature_algorithm_digest(SSL_SIGN_RSA_PSS_RSAE_SHA384));
4331 EXPECT_TRUE(SSL_is_signature_algorithm_rsa_pss(SSL_SIGN_RSA_PSS_RSAE_SHA384));
David Benjamin6cc352e2017-11-02 17:21:39 -04004332}
4333
Adam Langley85967952018-07-03 08:04:58 -07004334static int XORCompressFunc(SSL *ssl, CBB *out, const uint8_t *in,
4335 size_t in_len) {
4336 for (size_t i = 0; i < in_len; i++) {
Adam Langley0080d832018-06-07 16:39:49 -07004337 if (!CBB_add_u8(out, in[i] ^ 0x55)) {
Adam Langley85967952018-07-03 08:04:58 -07004338 return 0;
Adam Langley0080d832018-06-07 16:39:49 -07004339 }
4340 }
4341
4342 SSL_set_app_data(ssl, XORCompressFunc);
4343
Adam Langley85967952018-07-03 08:04:58 -07004344 return 1;
Adam Langley0080d832018-06-07 16:39:49 -07004345}
4346
Adam Langley85967952018-07-03 08:04:58 -07004347static int XORDecompressFunc(SSL *ssl, CRYPTO_BUFFER **out,
4348 size_t uncompressed_len, const uint8_t *in,
4349 size_t in_len) {
4350 if (in_len != uncompressed_len) {
4351 return 0;
Adam Langley0080d832018-06-07 16:39:49 -07004352 }
4353
4354 uint8_t *data;
Adam Langley85967952018-07-03 08:04:58 -07004355 *out = CRYPTO_BUFFER_alloc(&data, uncompressed_len);
4356 if (*out == nullptr) {
4357 return 0;
Adam Langley0080d832018-06-07 16:39:49 -07004358 }
4359
Adam Langley85967952018-07-03 08:04:58 -07004360 for (size_t i = 0; i < in_len; i++) {
Adam Langley0080d832018-06-07 16:39:49 -07004361 data[i] = in[i] ^ 0x55;
4362 }
4363
4364 SSL_set_app_data(ssl, XORDecompressFunc);
4365
Adam Langley85967952018-07-03 08:04:58 -07004366 return 1;
Adam Langley0080d832018-06-07 16:39:49 -07004367}
4368
4369TEST(SSLTest, CertCompression) {
4370 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLS_method()));
4371 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(TLS_method()));
4372 ASSERT_TRUE(client_ctx);
4373 ASSERT_TRUE(server_ctx);
4374
4375 bssl::UniquePtr<X509> cert = GetTestCertificate();
4376 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
4377 ASSERT_TRUE(cert);
4378 ASSERT_TRUE(key);
4379 ASSERT_TRUE(SSL_CTX_use_certificate(server_ctx.get(), cert.get()));
4380 ASSERT_TRUE(SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()));
4381
4382 ASSERT_TRUE(SSL_CTX_set_max_proto_version(client_ctx.get(), TLS1_3_VERSION));
4383 ASSERT_TRUE(SSL_CTX_set_max_proto_version(server_ctx.get(), TLS1_3_VERSION));
4384 ASSERT_TRUE(SSL_CTX_add_cert_compression_alg(
4385 client_ctx.get(), 0x1234, XORCompressFunc, XORDecompressFunc));
4386 ASSERT_TRUE(SSL_CTX_add_cert_compression_alg(
4387 server_ctx.get(), 0x1234, XORCompressFunc, XORDecompressFunc));
4388
4389 bssl::UniquePtr<SSL> client, server;
4390 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx.get(),
4391 server_ctx.get()));
4392
4393 EXPECT_TRUE(SSL_get_app_data(client.get()) == XORDecompressFunc);
4394 EXPECT_TRUE(SSL_get_app_data(server.get()) == XORCompressFunc);
4395}
4396
Adam Langleyddb57cf2018-01-26 09:17:53 -08004397void MoveBIOs(SSL *dest, SSL *src) {
4398 BIO *rbio = SSL_get_rbio(src);
4399 BIO_up_ref(rbio);
4400 SSL_set0_rbio(dest, rbio);
4401
4402 BIO *wbio = SSL_get_wbio(src);
4403 BIO_up_ref(wbio);
4404 SSL_set0_wbio(dest, wbio);
4405
4406 SSL_set0_rbio(src, nullptr);
4407 SSL_set0_wbio(src, nullptr);
4408}
4409
4410TEST(SSLTest, Handoff) {
4411 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLS_method()));
4412 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(TLS_method()));
4413 bssl::UniquePtr<SSL_CTX> handshaker_ctx(SSL_CTX_new(TLS_method()));
4414 ASSERT_TRUE(client_ctx);
4415 ASSERT_TRUE(server_ctx);
4416 ASSERT_TRUE(handshaker_ctx);
4417
Matthew Braithwaite134fb892019-11-26 17:56:11 -08004418 SSL_CTX_set_session_cache_mode(client_ctx.get(), SSL_SESS_CACHE_CLIENT);
4419 SSL_CTX_sess_set_new_cb(client_ctx.get(), SaveLastSession);
Adam Langleyddb57cf2018-01-26 09:17:53 -08004420 SSL_CTX_set_handoff_mode(server_ctx.get(), 1);
Matthew Braithwaite134fb892019-11-26 17:56:11 -08004421 uint8_t keys[48];
David Benjamin243b5cc2019-12-04 11:23:50 -05004422 SSL_CTX_get_tlsext_ticket_keys(server_ctx.get(), &keys, sizeof(keys));
Matthew Braithwaite134fb892019-11-26 17:56:11 -08004423 SSL_CTX_set_tlsext_ticket_keys(handshaker_ctx.get(), &keys, sizeof(keys));
Adam Langleyddb57cf2018-01-26 09:17:53 -08004424
4425 bssl::UniquePtr<X509> cert = GetTestCertificate();
4426 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
4427 ASSERT_TRUE(cert);
4428 ASSERT_TRUE(key);
4429 ASSERT_TRUE(SSL_CTX_use_certificate(handshaker_ctx.get(), cert.get()));
4430 ASSERT_TRUE(SSL_CTX_use_PrivateKey(handshaker_ctx.get(), key.get()));
4431
Matthew Braithwaite4f3e8212020-01-08 16:56:48 -08004432 for (bool early_data : {false, true}) {
4433 SCOPED_TRACE(early_data);
4434 for (bool is_resume : {false, true}) {
4435 SCOPED_TRACE(is_resume);
4436 bssl::UniquePtr<SSL> client, server;
4437 auto config = ClientConfig();
4438 config.early_data = early_data;
4439 if (is_resume) {
4440 ASSERT_TRUE(g_last_session);
4441 config.session = g_last_session.get();
4442 }
4443 if (is_resume && config.early_data) {
4444 EXPECT_GT(g_last_session->ticket_max_early_data, 0u);
4445 }
4446 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx.get(),
4447 server_ctx.get(), config,
4448 false /* don't handshake */));
4449
4450 int client_ret = SSL_do_handshake(client.get());
4451 int client_err = SSL_get_error(client.get(), client_ret);
4452
4453 uint8_t byte_written;
4454 if (config.early_data && is_resume) {
4455 ASSERT_EQ(client_err, 0);
4456 EXPECT_TRUE(SSL_in_early_data(client.get()));
4457 // Attempt to write early data.
4458 byte_written = 43;
4459 EXPECT_EQ(SSL_write(client.get(), &byte_written, 1), 1);
4460 } else {
4461 ASSERT_EQ(client_err, SSL_ERROR_WANT_READ);
4462 }
4463
4464 int server_ret = SSL_do_handshake(server.get());
4465 int server_err = SSL_get_error(server.get(), server_ret);
4466 ASSERT_EQ(server_err, SSL_ERROR_HANDOFF);
4467
4468 ScopedCBB cbb;
4469 Array<uint8_t> handoff;
4470 SSL_CLIENT_HELLO hello;
4471 ASSERT_TRUE(CBB_init(cbb.get(), 256));
4472 ASSERT_TRUE(SSL_serialize_handoff(server.get(), cbb.get(), &hello));
4473 ASSERT_TRUE(CBBFinishArray(cbb.get(), &handoff));
4474
4475 bssl::UniquePtr<SSL> handshaker(SSL_new(handshaker_ctx.get()));
4476 // Note split handshakes determines 0-RTT support, for both the current
4477 // handshake and newly-issued tickets, entirely by |handshaker|. There is
4478 // no need to call |SSL_set_early_data_enabled| on |server|.
4479 SSL_set_early_data_enabled(handshaker.get(), 1);
4480 ASSERT_TRUE(SSL_apply_handoff(handshaker.get(), handoff));
4481
4482 MoveBIOs(handshaker.get(), server.get());
4483
4484 int handshake_ret = SSL_do_handshake(handshaker.get());
4485 int handshake_err = SSL_get_error(handshaker.get(), handshake_ret);
4486 ASSERT_EQ(handshake_err, SSL_ERROR_HANDBACK);
4487
4488 // Double-check that additional calls to |SSL_do_handshake| continue
Adam Langley472d91c2020-02-18 12:12:35 -08004489 // to get |SSL_ERROR_HANDBACK|.
Matthew Braithwaite4f3e8212020-01-08 16:56:48 -08004490 handshake_ret = SSL_do_handshake(handshaker.get());
4491 handshake_err = SSL_get_error(handshaker.get(), handshake_ret);
4492 ASSERT_EQ(handshake_err, SSL_ERROR_HANDBACK);
4493
4494 ScopedCBB cbb_handback;
4495 Array<uint8_t> handback;
4496 ASSERT_TRUE(CBB_init(cbb_handback.get(), 1024));
4497 ASSERT_TRUE(SSL_serialize_handback(handshaker.get(), cbb_handback.get()));
4498 ASSERT_TRUE(CBBFinishArray(cbb_handback.get(), &handback));
4499
4500 bssl::UniquePtr<SSL> server2(SSL_new(server_ctx.get()));
4501 ASSERT_TRUE(SSL_apply_handback(server2.get(), handback));
4502
4503 MoveBIOs(server2.get(), handshaker.get());
4504 ASSERT_TRUE(CompleteHandshakes(client.get(), server2.get()));
4505 EXPECT_EQ(is_resume, SSL_session_reused(client.get()));
4506
4507 if (config.early_data && is_resume) {
4508 // In this case, one byte of early data has already been written above.
4509 EXPECT_TRUE(SSL_early_data_accepted(client.get()));
4510 } else {
4511 byte_written = 42;
4512 EXPECT_EQ(SSL_write(client.get(), &byte_written, 1), 1);
4513 }
4514 uint8_t byte;
4515 EXPECT_EQ(SSL_read(server2.get(), &byte, 1), 1);
4516 EXPECT_EQ(byte_written, byte);
4517
4518 byte = 44;
4519 EXPECT_EQ(SSL_write(server2.get(), &byte, 1), 1);
4520 EXPECT_EQ(SSL_read(client.get(), &byte, 1), 1);
4521 EXPECT_EQ(44, byte);
Matthew Braithwaite134fb892019-11-26 17:56:11 -08004522 }
Matthew Braithwaite134fb892019-11-26 17:56:11 -08004523 }
Adam Langleyddb57cf2018-01-26 09:17:53 -08004524}
4525
4526TEST(SSLTest, HandoffDeclined) {
4527 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLS_method()));
4528 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(TLS_method()));
4529 ASSERT_TRUE(client_ctx);
4530 ASSERT_TRUE(server_ctx);
4531
4532 SSL_CTX_set_handoff_mode(server_ctx.get(), 1);
4533 ASSERT_TRUE(SSL_CTX_set_max_proto_version(server_ctx.get(), TLS1_2_VERSION));
4534
4535 bssl::UniquePtr<X509> cert = GetTestCertificate();
4536 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
4537 ASSERT_TRUE(cert);
4538 ASSERT_TRUE(key);
4539 ASSERT_TRUE(SSL_CTX_use_certificate(server_ctx.get(), cert.get()));
4540 ASSERT_TRUE(SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()));
4541
4542 bssl::UniquePtr<SSL> client, server;
4543 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx.get(),
4544 server_ctx.get(), ClientConfig(),
4545 false /* don't handshake */));
4546
4547 int client_ret = SSL_do_handshake(client.get());
4548 int client_err = SSL_get_error(client.get(), client_ret);
4549 ASSERT_EQ(client_err, SSL_ERROR_WANT_READ);
4550
4551 int server_ret = SSL_do_handshake(server.get());
4552 int server_err = SSL_get_error(server.get(), server_ret);
4553 ASSERT_EQ(server_err, SSL_ERROR_HANDOFF);
4554
4555 ScopedCBB cbb;
Adam Langleyc9827e02019-04-12 14:46:50 -07004556 SSL_CLIENT_HELLO hello;
Adam Langleyddb57cf2018-01-26 09:17:53 -08004557 ASSERT_TRUE(CBB_init(cbb.get(), 256));
Adam Langleyc9827e02019-04-12 14:46:50 -07004558 ASSERT_TRUE(SSL_serialize_handoff(server.get(), cbb.get(), &hello));
Adam Langleyddb57cf2018-01-26 09:17:53 -08004559
4560 ASSERT_TRUE(SSL_decline_handoff(server.get()));
4561
4562 ASSERT_TRUE(CompleteHandshakes(client.get(), server.get()));
4563
4564 uint8_t byte = 42;
4565 EXPECT_EQ(SSL_write(client.get(), &byte, 1), 1);
4566 EXPECT_EQ(SSL_read(server.get(), &byte, 1), 1);
4567 EXPECT_EQ(42, byte);
4568
4569 byte = 43;
4570 EXPECT_EQ(SSL_write(server.get(), &byte, 1), 1);
4571 EXPECT_EQ(SSL_read(client.get(), &byte, 1), 1);
4572 EXPECT_EQ(43, byte);
4573}
4574
Adam Langley826ce152018-08-03 10:31:21 -07004575static std::string SigAlgsToString(Span<const uint16_t> sigalgs) {
4576 std::string ret = "{";
4577
4578 for (uint16_t v : sigalgs) {
4579 if (ret.size() > 1) {
4580 ret += ", ";
4581 }
4582
4583 char buf[8];
4584 snprintf(buf, sizeof(buf) - 1, "0x%02x", v);
4585 buf[sizeof(buf)-1] = 0;
4586 ret += std::string(buf);
4587 }
4588
4589 ret += "}";
4590 return ret;
4591}
4592
4593void ExpectSigAlgsEqual(Span<const uint16_t> expected,
4594 Span<const uint16_t> actual) {
4595 bool matches = false;
4596 if (expected.size() == actual.size()) {
4597 matches = true;
4598
4599 for (size_t i = 0; i < expected.size(); i++) {
4600 if (expected[i] != actual[i]) {
4601 matches = false;
4602 break;
4603 }
4604 }
4605 }
4606
4607 if (!matches) {
4608 ADD_FAILURE() << "expected: " << SigAlgsToString(expected)
4609 << " got: " << SigAlgsToString(actual);
4610 }
4611}
4612
4613TEST(SSLTest, SigAlgs) {
4614 static const struct {
4615 std::vector<int> input;
4616 bool ok;
4617 std::vector<uint16_t> expected;
4618 } kTests[] = {
4619 {{}, true, {}},
4620 {{1}, false, {}},
4621 {{1, 2, 3}, false, {}},
4622 {{NID_sha256, EVP_PKEY_ED25519}, false, {}},
4623 {{NID_sha256, EVP_PKEY_RSA, NID_sha256, EVP_PKEY_RSA}, false, {}},
4624
4625 {{NID_sha256, EVP_PKEY_RSA}, true, {SSL_SIGN_RSA_PKCS1_SHA256}},
4626 {{NID_sha512, EVP_PKEY_RSA}, true, {SSL_SIGN_RSA_PKCS1_SHA512}},
4627 {{NID_sha256, EVP_PKEY_RSA_PSS}, true, {SSL_SIGN_RSA_PSS_RSAE_SHA256}},
4628 {{NID_undef, EVP_PKEY_ED25519}, true, {SSL_SIGN_ED25519}},
4629 {{NID_undef, EVP_PKEY_ED25519, NID_sha384, EVP_PKEY_EC},
4630 true,
4631 {SSL_SIGN_ED25519, SSL_SIGN_ECDSA_SECP384R1_SHA384}},
4632 };
4633
4634 UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
4635
4636 unsigned n = 1;
4637 for (const auto &test : kTests) {
4638 SCOPED_TRACE(n++);
4639
4640 const bool ok =
4641 SSL_CTX_set1_sigalgs(ctx.get(), test.input.data(), test.input.size());
4642 EXPECT_EQ(ok, test.ok);
4643
4644 if (!ok) {
4645 ERR_clear_error();
4646 }
4647
4648 if (!test.ok) {
4649 continue;
4650 }
4651
4652 ExpectSigAlgsEqual(test.expected, ctx->cert->sigalgs);
4653 }
4654}
4655
4656TEST(SSLTest, SigAlgsList) {
4657 static const struct {
4658 const char *input;
4659 bool ok;
4660 std::vector<uint16_t> expected;
4661 } kTests[] = {
4662 {"", false, {}},
4663 {":", false, {}},
4664 {"+", false, {}},
4665 {"RSA", false, {}},
4666 {"RSA+", false, {}},
4667 {"RSA+SHA256:", false, {}},
4668 {":RSA+SHA256:", false, {}},
4669 {":RSA+SHA256+:", false, {}},
4670 {"!", false, {}},
4671 {"\x01", false, {}},
4672 {"RSA+SHA256:RSA+SHA384:RSA+SHA256", false, {}},
4673 {"RSA-PSS+SHA256:rsa_pss_rsae_sha256", false, {}},
4674
4675 {"RSA+SHA256", true, {SSL_SIGN_RSA_PKCS1_SHA256}},
4676 {"RSA+SHA256:ed25519",
4677 true,
4678 {SSL_SIGN_RSA_PKCS1_SHA256, SSL_SIGN_ED25519}},
4679 {"ECDSA+SHA256:RSA+SHA512",
4680 true,
4681 {SSL_SIGN_ECDSA_SECP256R1_SHA256, SSL_SIGN_RSA_PKCS1_SHA512}},
4682 {"ecdsa_secp256r1_sha256:rsa_pss_rsae_sha256",
4683 true,
4684 {SSL_SIGN_ECDSA_SECP256R1_SHA256, SSL_SIGN_RSA_PSS_RSAE_SHA256}},
4685 {"RSA-PSS+SHA256", true, {SSL_SIGN_RSA_PSS_RSAE_SHA256}},
4686 {"PSS+SHA256", true, {SSL_SIGN_RSA_PSS_RSAE_SHA256}},
4687 };
4688
4689 UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
4690
4691 unsigned n = 1;
4692 for (const auto &test : kTests) {
4693 SCOPED_TRACE(n++);
4694
4695 const bool ok = SSL_CTX_set1_sigalgs_list(ctx.get(), test.input);
4696 EXPECT_EQ(ok, test.ok);
4697
4698 if (!ok) {
4699 if (test.ok) {
4700 ERR_print_errors_fp(stderr);
4701 }
4702 ERR_clear_error();
4703 }
4704
4705 if (!test.ok) {
4706 continue;
4707 }
4708
4709 ExpectSigAlgsEqual(test.expected, ctx->cert->sigalgs);
4710 }
4711}
4712
Matthew Braithwaited2ed3822018-07-10 16:27:22 -07004713TEST(SSLTest, ApplyHandoffRemovesUnsupportedCiphers) {
4714 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(TLS_method()));
4715 bssl::UniquePtr<SSL> server(SSL_new(server_ctx.get()));
4716
4717 // handoff is a handoff message that has been artificially modified to pretend
4718 // that only cipher 0x0A is supported. When it is applied to |server|, all
4719 // ciphers but that one should be removed.
Matthew Braithwaitec65eb2c2018-11-02 17:29:35 -07004720 //
4721 // To make a new one of these, try sticking this in the |Handoff| test above:
4722 //
4723 // hexdump(stderr, "", handoff.data(), handoff.size());
4724 // sed -e 's/\(..\)/0x\1, /g'
4725 //
4726 // and modify serialize_features() to emit only cipher 0x0A.
4727
Matthew Braithwaited2ed3822018-07-10 16:27:22 -07004728 uint8_t handoff[] = {
Matthew Braithwaitec65eb2c2018-11-02 17:29:35 -07004729 0x30, 0x81, 0x9a, 0x02, 0x01, 0x00, 0x04, 0x00, 0x04, 0x81, 0x82, 0x01,
4730 0x00, 0x00, 0x7e, 0x03, 0x03, 0x30, 0x8e, 0x8f, 0x79, 0xd2, 0x87, 0x39,
4731 0xc2, 0x23, 0x23, 0x13, 0xca, 0x3c, 0x80, 0x44, 0xfd, 0x80, 0x83, 0x62,
4732 0x3c, 0xcc, 0xf8, 0x76, 0xd3, 0x62, 0xbb, 0x54, 0xe3, 0xc4, 0x39, 0x24,
4733 0xa5, 0x00, 0x00, 0x1e, 0xc0, 0x2b, 0xc0, 0x2f, 0xc0, 0x2c, 0xc0, 0x30,
Matthew Braithwaited2ed3822018-07-10 16:27:22 -07004734 0xcc, 0xa9, 0xcc, 0xa8, 0xc0, 0x09, 0xc0, 0x13, 0xc0, 0x0a, 0xc0, 0x14,
4735 0x00, 0x9c, 0x00, 0x9d, 0x00, 0x2f, 0x00, 0x35, 0x00, 0x0a, 0x01, 0x00,
Matthew Braithwaitec65eb2c2018-11-02 17:29:35 -07004736 0x00, 0x37, 0x00, 0x17, 0x00, 0x00, 0xff, 0x01, 0x00, 0x01, 0x00, 0x00,
4737 0x0a, 0x00, 0x08, 0x00, 0x06, 0x00, 0x1d, 0x00, 0x17, 0x00, 0x18, 0x00,
4738 0x0b, 0x00, 0x02, 0x01, 0x00, 0x00, 0x23, 0x00, 0x00, 0x00, 0x0d, 0x00,
4739 0x14, 0x00, 0x12, 0x04, 0x03, 0x08, 0x04, 0x04, 0x01, 0x05, 0x03, 0x08,
4740 0x05, 0x05, 0x01, 0x08, 0x06, 0x06, 0x01, 0x02, 0x01, 0x04, 0x02, 0x00,
4741 0x0a, 0x04, 0x0a, 0x00, 0x15, 0x00, 0x17, 0x00, 0x18, 0x00, 0x19, 0x00,
4742 0x1d,
Matthew Braithwaited2ed3822018-07-10 16:27:22 -07004743 };
4744
4745 EXPECT_EQ(20u, sk_SSL_CIPHER_num(SSL_get_ciphers(server.get())));
4746 ASSERT_TRUE(
4747 SSL_apply_handoff(server.get(), {handoff, OPENSSL_ARRAY_SIZE(handoff)}));
4748 EXPECT_EQ(1u, sk_SSL_CIPHER_num(SSL_get_ciphers(server.get())));
4749}
4750
Matthew Braithwaitec65eb2c2018-11-02 17:29:35 -07004751TEST(SSLTest, ApplyHandoffRemovesUnsupportedCurves) {
4752 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(TLS_method()));
4753 bssl::UniquePtr<SSL> server(SSL_new(server_ctx.get()));
4754
4755 // handoff is a handoff message that has been artificially modified to pretend
4756 // that only one curve is supported. When it is applied to |server|, all
4757 // curves but that one should be removed.
4758 //
4759 // See |ApplyHandoffRemovesUnsupportedCiphers| for how to make a new one of
4760 // these.
4761 uint8_t handoff[] = {
4762 0x30, 0x81, 0xc0, 0x02, 0x01, 0x00, 0x04, 0x00, 0x04, 0x81, 0x82, 0x01,
4763 0x00, 0x00, 0x7e, 0x03, 0x03, 0x98, 0x30, 0xce, 0xd9, 0xb0, 0xdf, 0x5f,
4764 0x82, 0x05, 0x4a, 0x43, 0x67, 0x7e, 0xdb, 0x6a, 0x4f, 0x21, 0x18, 0x4e,
4765 0x0d, 0x94, 0x63, 0x18, 0x8b, 0x54, 0x89, 0xdb, 0x8b, 0x1d, 0x84, 0xbc,
4766 0x09, 0x00, 0x00, 0x1e, 0xc0, 0x2b, 0xc0, 0x2f, 0xc0, 0x2c, 0xc0, 0x30,
4767 0xcc, 0xa9, 0xcc, 0xa8, 0xc0, 0x09, 0xc0, 0x13, 0xc0, 0x0a, 0xc0, 0x14,
4768 0x00, 0x9c, 0x00, 0x9d, 0x00, 0x2f, 0x00, 0x35, 0x00, 0x0a, 0x01, 0x00,
4769 0x00, 0x37, 0x00, 0x17, 0x00, 0x00, 0xff, 0x01, 0x00, 0x01, 0x00, 0x00,
4770 0x0a, 0x00, 0x08, 0x00, 0x06, 0x00, 0x1d, 0x00, 0x17, 0x00, 0x18, 0x00,
4771 0x0b, 0x00, 0x02, 0x01, 0x00, 0x00, 0x23, 0x00, 0x00, 0x00, 0x0d, 0x00,
4772 0x14, 0x00, 0x12, 0x04, 0x03, 0x08, 0x04, 0x04, 0x01, 0x05, 0x03, 0x08,
4773 0x05, 0x05, 0x01, 0x08, 0x06, 0x06, 0x01, 0x02, 0x01, 0x04, 0x30, 0x00,
4774 0x02, 0x00, 0x0a, 0x00, 0x2f, 0x00, 0x35, 0x00, 0x8c, 0x00, 0x8d, 0x00,
4775 0x9c, 0x00, 0x9d, 0x13, 0x01, 0x13, 0x02, 0x13, 0x03, 0xc0, 0x09, 0xc0,
4776 0x0a, 0xc0, 0x13, 0xc0, 0x14, 0xc0, 0x2b, 0xc0, 0x2c, 0xc0, 0x2f, 0xc0,
4777 0x30, 0xc0, 0x35, 0xc0, 0x36, 0xcc, 0xa8, 0xcc, 0xa9, 0xcc, 0xac, 0x04,
4778 0x02, 0x00, 0x17,
4779 };
4780
4781 // The zero length means that the default list of groups is used.
4782 EXPECT_EQ(0u, server->config->supported_group_list.size());
4783 ASSERT_TRUE(
4784 SSL_apply_handoff(server.get(), {handoff, OPENSSL_ARRAY_SIZE(handoff)}));
4785 EXPECT_EQ(1u, server->config->supported_group_list.size());
4786}
4787
Adam Langleyba9ad662018-12-17 13:59:38 -08004788TEST(SSLTest, ZeroSizedWiteFlushesHandshakeMessages) {
4789 // If there are pending handshake mesages, an |SSL_write| of zero bytes should
4790 // flush them.
4791 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(TLS_method()));
4792 EXPECT_TRUE(SSL_CTX_set_max_proto_version(server_ctx.get(), TLS1_3_VERSION));
4793 EXPECT_TRUE(SSL_CTX_set_min_proto_version(server_ctx.get(), TLS1_3_VERSION));
4794 bssl::UniquePtr<X509> cert = GetTestCertificate();
4795 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
4796 ASSERT_TRUE(cert);
4797 ASSERT_TRUE(key);
4798 ASSERT_TRUE(SSL_CTX_use_certificate(server_ctx.get(), cert.get()));
4799 ASSERT_TRUE(SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()));
4800
4801 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLS_method()));
4802 EXPECT_TRUE(SSL_CTX_set_max_proto_version(client_ctx.get(), TLS1_3_VERSION));
4803 EXPECT_TRUE(SSL_CTX_set_min_proto_version(client_ctx.get(), TLS1_3_VERSION));
4804
4805 bssl::UniquePtr<SSL> client, server;
4806 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx.get(),
4807 server_ctx.get()));
4808
4809 BIO *client_wbio = SSL_get_wbio(client.get());
4810 EXPECT_EQ(0u, BIO_wpending(client_wbio));
4811 EXPECT_TRUE(SSL_key_update(client.get(), SSL_KEY_UPDATE_NOT_REQUESTED));
4812 EXPECT_EQ(0u, BIO_wpending(client_wbio));
4813 EXPECT_EQ(0, SSL_write(client.get(), nullptr, 0));
4814 EXPECT_NE(0u, BIO_wpending(client_wbio));
4815}
4816
David Benjamin5869eb32018-07-17 00:59:45 -04004817TEST_P(SSLVersionTest, VerifyBeforeCertRequest) {
4818 // Configure the server to request client certificates.
4819 SSL_CTX_set_custom_verify(
4820 server_ctx_.get(), SSL_VERIFY_PEER,
4821 [](SSL *ssl, uint8_t *out_alert) { return ssl_verify_ok; });
4822
4823 // Configure the client to reject the server certificate.
4824 SSL_CTX_set_custom_verify(
4825 client_ctx_.get(), SSL_VERIFY_PEER,
4826 [](SSL *ssl, uint8_t *out_alert) { return ssl_verify_invalid; });
4827
4828 // cert_cb should not be called. Verification should fail first.
4829 SSL_CTX_set_cert_cb(client_ctx_.get(),
4830 [](SSL *ssl, void *arg) {
4831 ADD_FAILURE() << "cert_cb unexpectedly called";
4832 return 0;
4833 },
4834 nullptr);
4835
4836 bssl::UniquePtr<SSL> client, server;
4837 EXPECT_FALSE(ConnectClientAndServer(&client, &server, client_ctx_.get(),
4838 server_ctx_.get()));
4839}
4840
David Benjamin492c9aa2018-08-31 16:35:22 -05004841// Test that ticket-based sessions on the client get fake session IDs.
4842TEST_P(SSLVersionTest, FakeIDsForTickets) {
4843 SSL_CTX_set_session_cache_mode(client_ctx_.get(), SSL_SESS_CACHE_BOTH);
4844 SSL_CTX_set_session_cache_mode(server_ctx_.get(), SSL_SESS_CACHE_BOTH);
4845
4846 bssl::UniquePtr<SSL_SESSION> session =
4847 CreateClientSession(client_ctx_.get(), server_ctx_.get());
4848 ASSERT_TRUE(session);
4849
4850 EXPECT_TRUE(SSL_SESSION_has_ticket(session.get()));
4851 unsigned session_id_length;
4852 SSL_SESSION_get_id(session.get(), &session_id_length);
4853 EXPECT_NE(session_id_length, 0u);
4854}
4855
David Benjamin6c04bd12018-07-19 18:13:09 -04004856// These tests test multi-threaded behavior. They are intended to run with
4857// ThreadSanitizer.
David Benjamin5b33eff2018-09-22 16:52:48 -07004858#if defined(OPENSSL_THREADS)
David Benjamin6c04bd12018-07-19 18:13:09 -04004859TEST_P(SSLVersionTest, SessionCacheThreads) {
4860 SSL_CTX_set_options(server_ctx_.get(), SSL_OP_NO_TICKET);
4861 SSL_CTX_set_session_cache_mode(client_ctx_.get(), SSL_SESS_CACHE_BOTH);
4862 SSL_CTX_set_session_cache_mode(server_ctx_.get(), SSL_SESS_CACHE_BOTH);
4863
4864 if (version() == TLS1_3_VERSION) {
4865 // Our TLS 1.3 implementation does not support stateful resumption.
4866 ASSERT_FALSE(CreateClientSession(client_ctx_.get(), server_ctx_.get()));
4867 return;
4868 }
4869
4870 // Establish two client sessions to test with.
4871 bssl::UniquePtr<SSL_SESSION> session1 =
4872 CreateClientSession(client_ctx_.get(), server_ctx_.get());
4873 ASSERT_TRUE(session1);
4874 bssl::UniquePtr<SSL_SESSION> session2 =
4875 CreateClientSession(client_ctx_.get(), server_ctx_.get());
4876 ASSERT_TRUE(session2);
4877
4878 auto connect_with_session = [&](SSL_SESSION *session) {
4879 ClientConfig config;
4880 config.session = session;
4881 UniquePtr<SSL> client, server;
4882 EXPECT_TRUE(ConnectClientAndServer(&client, &server, client_ctx_.get(),
4883 server_ctx_.get(), config));
4884 };
4885
4886 // Resume sessions in parallel with establishing new ones.
4887 {
4888 std::vector<std::thread> threads;
4889 threads.emplace_back([&] { connect_with_session(nullptr); });
4890 threads.emplace_back([&] { connect_with_session(nullptr); });
4891 threads.emplace_back([&] { connect_with_session(session1.get()); });
4892 threads.emplace_back([&] { connect_with_session(session1.get()); });
4893 threads.emplace_back([&] { connect_with_session(session2.get()); });
4894 threads.emplace_back([&] { connect_with_session(session2.get()); });
4895 for (auto &thread : threads) {
4896 thread.join();
4897 }
4898 }
4899
4900 // Hit the maximum session cache size across multiple threads
4901 size_t limit = SSL_CTX_sess_number(server_ctx_.get()) + 2;
4902 SSL_CTX_sess_set_cache_size(server_ctx_.get(), limit);
4903 {
4904 std::vector<std::thread> threads;
4905 for (int i = 0; i < 4; i++) {
4906 threads.emplace_back([&]() {
4907 connect_with_session(nullptr);
4908 EXPECT_LE(SSL_CTX_sess_number(server_ctx_.get()), limit);
4909 });
4910 }
4911 for (auto &thread : threads) {
4912 thread.join();
4913 }
4914 EXPECT_EQ(SSL_CTX_sess_number(server_ctx_.get()), limit);
4915 }
4916}
4917
4918TEST_P(SSLVersionTest, SessionTicketThreads) {
4919 for (bool renew_ticket : {false, true}) {
4920 SCOPED_TRACE(renew_ticket);
4921 ResetContexts();
4922 SSL_CTX_set_session_cache_mode(client_ctx_.get(), SSL_SESS_CACHE_BOTH);
4923 SSL_CTX_set_session_cache_mode(server_ctx_.get(), SSL_SESS_CACHE_BOTH);
4924 if (renew_ticket) {
4925 SSL_CTX_set_tlsext_ticket_key_cb(server_ctx_.get(), RenewTicketCallback);
4926 }
4927
4928 // Establish two client sessions to test with.
4929 bssl::UniquePtr<SSL_SESSION> session1 =
4930 CreateClientSession(client_ctx_.get(), server_ctx_.get());
4931 ASSERT_TRUE(session1);
4932 bssl::UniquePtr<SSL_SESSION> session2 =
4933 CreateClientSession(client_ctx_.get(), server_ctx_.get());
4934 ASSERT_TRUE(session2);
4935
4936 auto connect_with_session = [&](SSL_SESSION *session) {
4937 ClientConfig config;
4938 config.session = session;
4939 UniquePtr<SSL> client, server;
4940 EXPECT_TRUE(ConnectClientAndServer(&client, &server, client_ctx_.get(),
4941 server_ctx_.get(), config));
4942 };
4943
4944 // Resume sessions in parallel with establishing new ones.
4945 {
4946 std::vector<std::thread> threads;
4947 threads.emplace_back([&] { connect_with_session(nullptr); });
4948 threads.emplace_back([&] { connect_with_session(nullptr); });
4949 threads.emplace_back([&] { connect_with_session(session1.get()); });
4950 threads.emplace_back([&] { connect_with_session(session1.get()); });
4951 threads.emplace_back([&] { connect_with_session(session2.get()); });
4952 threads.emplace_back([&] { connect_with_session(session2.get()); });
4953 for (auto &thread : threads) {
4954 thread.join();
4955 }
4956 }
4957 }
4958}
4959
4960// SSL_CTX_get0_certificate needs to lock internally. Test this works.
4961TEST(SSLTest, GetCertificateThreads) {
4962 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
4963 ASSERT_TRUE(ctx);
4964 bssl::UniquePtr<X509> cert = GetTestCertificate();
4965 ASSERT_TRUE(cert);
4966 ASSERT_TRUE(SSL_CTX_use_certificate(ctx.get(), cert.get()));
4967
4968 // Existing code expects |SSL_CTX_get0_certificate| to be callable from two
4969 // threads concurrently. It originally was an immutable operation. Now we
4970 // implement it with a thread-safe cache, so it is worth testing.
4971 X509 *cert2_thread;
4972 std::thread thread(
4973 [&] { cert2_thread = SSL_CTX_get0_certificate(ctx.get()); });
4974 X509 *cert2 = SSL_CTX_get0_certificate(ctx.get());
4975 thread.join();
4976
4977 EXPECT_EQ(cert2, cert2_thread);
4978 EXPECT_EQ(0, X509_cmp(cert.get(), cert2));
4979}
David Benjamin4cce9552018-12-13 12:20:54 -06004980
4981// Functions which access properties on the negotiated session are thread-safe
4982// where needed. Prior to TLS 1.3, clients resuming sessions and servers
4983// performing stateful resumption will share an underlying SSL_SESSION object,
4984// potentially across threads.
4985TEST_P(SSLVersionTest, SessionPropertiesThreads) {
4986 if (version() == TLS1_3_VERSION) {
4987 // Our TLS 1.3 implementation does not support stateful resumption.
4988 ASSERT_FALSE(CreateClientSession(client_ctx_.get(), server_ctx_.get()));
4989 return;
4990 }
4991
4992 SSL_CTX_set_options(server_ctx_.get(), SSL_OP_NO_TICKET);
4993 SSL_CTX_set_session_cache_mode(client_ctx_.get(), SSL_SESS_CACHE_BOTH);
4994 SSL_CTX_set_session_cache_mode(server_ctx_.get(), SSL_SESS_CACHE_BOTH);
4995
4996 ASSERT_TRUE(UseCertAndKey(client_ctx_.get()));
4997 ASSERT_TRUE(UseCertAndKey(server_ctx_.get()));
4998
4999 // Configure mutual authentication, so we have more session state.
5000 SSL_CTX_set_custom_verify(
5001 client_ctx_.get(), SSL_VERIFY_PEER,
5002 [](SSL *ssl, uint8_t *out_alert) { return ssl_verify_ok; });
5003 SSL_CTX_set_custom_verify(
5004 server_ctx_.get(), SSL_VERIFY_PEER,
5005 [](SSL *ssl, uint8_t *out_alert) { return ssl_verify_ok; });
5006
5007 // Establish a client session to test with.
5008 bssl::UniquePtr<SSL_SESSION> session =
5009 CreateClientSession(client_ctx_.get(), server_ctx_.get());
5010 ASSERT_TRUE(session);
5011
5012 // Resume with it twice.
5013 UniquePtr<SSL> ssls[4];
5014 ClientConfig config;
5015 config.session = session.get();
5016 ASSERT_TRUE(ConnectClientAndServer(&ssls[0], &ssls[1], client_ctx_.get(),
5017 server_ctx_.get(), config));
5018 ASSERT_TRUE(ConnectClientAndServer(&ssls[2], &ssls[3], client_ctx_.get(),
5019 server_ctx_.get(), config));
5020
5021 // Read properties in parallel.
5022 auto read_properties = [](const SSL *ssl) {
5023 EXPECT_TRUE(SSL_get_peer_cert_chain(ssl));
5024 bssl::UniquePtr<X509> peer(SSL_get_peer_certificate(ssl));
5025 EXPECT_TRUE(peer);
5026 EXPECT_TRUE(SSL_get_current_cipher(ssl));
5027 EXPECT_TRUE(SSL_get_curve_id(ssl));
5028 };
5029
5030 std::vector<std::thread> threads;
5031 for (const auto &ssl_ptr : ssls) {
5032 const SSL *ssl = ssl_ptr.get();
5033 threads.emplace_back([=] { read_properties(ssl); });
5034 }
5035 for (auto &thread : threads) {
5036 thread.join();
5037 }
5038}
David Benjamina486c6c2019-03-28 18:32:38 -05005039#endif // OPENSSL_THREADS
David Benjamin6c04bd12018-07-19 18:13:09 -04005040
Steven Valdezc8e0f902018-07-14 11:23:01 -04005041constexpr size_t kNumQUICLevels = 4;
5042static_assert(ssl_encryption_initial < kNumQUICLevels,
5043 "kNumQUICLevels is wrong");
5044static_assert(ssl_encryption_early_data < kNumQUICLevels,
5045 "kNumQUICLevels is wrong");
5046static_assert(ssl_encryption_handshake < kNumQUICLevels,
5047 "kNumQUICLevels is wrong");
5048static_assert(ssl_encryption_application < kNumQUICLevels,
5049 "kNumQUICLevels is wrong");
5050
David Benjamin1e859052020-02-09 16:04:58 -05005051const char *LevelToString(ssl_encryption_level_t level) {
5052 switch (level) {
5053 case ssl_encryption_initial:
5054 return "initial";
5055 case ssl_encryption_early_data:
5056 return "early data";
5057 case ssl_encryption_handshake:
5058 return "handshake";
5059 case ssl_encryption_application:
5060 return "application";
5061 }
5062 return "<unknown>";
5063}
5064
Steven Valdezc8e0f902018-07-14 11:23:01 -04005065class MockQUICTransport {
5066 public:
David Benjamind6343572019-08-15 17:29:02 -04005067 enum class Role { kClient, kServer };
5068
5069 explicit MockQUICTransport(Role role) : role_(role) {
Steven Valdezc8e0f902018-07-14 11:23:01 -04005070 // The caller is expected to configure initial secrets.
5071 levels_[ssl_encryption_initial].write_secret = {1};
5072 levels_[ssl_encryption_initial].read_secret = {1};
5073 }
5074
5075 void set_peer(MockQUICTransport *peer) { peer_ = peer; }
5076
5077 bool has_alert() const { return has_alert_; }
5078 ssl_encryption_level_t alert_level() const { return alert_level_; }
5079 uint8_t alert() const { return alert_; }
5080
5081 bool PeerSecretsMatch(ssl_encryption_level_t level) const {
5082 return levels_[level].write_secret == peer_->levels_[level].read_secret &&
Steven Valdez384d0ea2018-11-06 10:45:36 -05005083 levels_[level].read_secret == peer_->levels_[level].write_secret &&
5084 levels_[level].cipher == peer_->levels_[level].cipher;
Steven Valdezc8e0f902018-07-14 11:23:01 -04005085 }
5086
David Benjamin1e859052020-02-09 16:04:58 -05005087 bool HasReadSecret(ssl_encryption_level_t level) const {
5088 return !levels_[level].read_secret.empty();
Steven Valdezc8e0f902018-07-14 11:23:01 -04005089 }
5090
David Benjamin1e859052020-02-09 16:04:58 -05005091 bool HasWriteSecret(ssl_encryption_level_t level) const {
5092 return !levels_[level].write_secret.empty();
5093 }
5094
David Benjamin5298ef92020-03-13 12:17:30 -04005095 void AllowOutOfOrderWrites() { allow_out_of_order_writes_ = true; }
5096
David Benjamin1e859052020-02-09 16:04:58 -05005097 bool SetReadSecret(ssl_encryption_level_t level, const SSL_CIPHER *cipher,
5098 Span<const uint8_t> secret) {
5099 if (HasReadSecret(level)) {
5100 ADD_FAILURE() << LevelToString(level) << " read secret configured twice";
5101 return false;
5102 }
5103
5104 if (role_ == Role::kClient && level == ssl_encryption_early_data) {
5105 ADD_FAILURE() << "Unexpected early data read secret";
5106 return false;
5107 }
5108
5109 ssl_encryption_level_t ack_level =
5110 level == ssl_encryption_early_data ? ssl_encryption_application : level;
5111 if (!HasWriteSecret(ack_level)) {
5112 ADD_FAILURE() << LevelToString(level)
5113 << " read secret configured before ACK write secret";
Steven Valdezc8e0f902018-07-14 11:23:01 -04005114 return false;
5115 }
Steven Valdez384d0ea2018-11-06 10:45:36 -05005116
5117 if (cipher == nullptr) {
David Benjamin1e859052020-02-09 16:04:58 -05005118 ADD_FAILURE() << "Unexpected null cipher";
Steven Valdez384d0ea2018-11-06 10:45:36 -05005119 return false;
5120 }
5121
David Benjamin1e859052020-02-09 16:04:58 -05005122 if (level != ssl_encryption_early_data &&
5123 SSL_CIPHER_get_id(cipher) != levels_[level].cipher) {
5124 ADD_FAILURE() << "Cipher suite inconsistent";
Steven Valdezc8e0f902018-07-14 11:23:01 -04005125 return false;
5126 }
David Benjamind6343572019-08-15 17:29:02 -04005127
David Benjamin1e859052020-02-09 16:04:58 -05005128 levels_[level].read_secret.assign(secret.begin(), secret.end());
5129 levels_[level].cipher = SSL_CIPHER_get_id(cipher);
5130 return true;
5131 }
5132
5133 bool SetWriteSecret(ssl_encryption_level_t level, const SSL_CIPHER *cipher,
5134 Span<const uint8_t> secret) {
5135 if (HasWriteSecret(level)) {
5136 ADD_FAILURE() << LevelToString(level) << " write secret configured twice";
David Benjamind6343572019-08-15 17:29:02 -04005137 return false;
Steven Valdezc8e0f902018-07-14 11:23:01 -04005138 }
David Benjamind6343572019-08-15 17:29:02 -04005139
David Benjamin1e859052020-02-09 16:04:58 -05005140 if (role_ == Role::kServer && level == ssl_encryption_early_data) {
5141 ADD_FAILURE() << "Unexpected early data write secret";
5142 return false;
5143 }
5144
5145 if (cipher == nullptr) {
5146 ADD_FAILURE() << "Unexpected null cipher";
5147 return false;
5148 }
5149
5150 levels_[level].write_secret.assign(secret.begin(), secret.end());
Steven Valdez384d0ea2018-11-06 10:45:36 -05005151 levels_[level].cipher = SSL_CIPHER_get_id(cipher);
Steven Valdezc8e0f902018-07-14 11:23:01 -04005152 return true;
5153 }
5154
5155 bool WriteHandshakeData(ssl_encryption_level_t level,
5156 Span<const uint8_t> data) {
5157 if (levels_[level].write_secret.empty()) {
David Benjamin1e859052020-02-09 16:04:58 -05005158 ADD_FAILURE() << LevelToString(level)
5159 << " write secret not yet configured";
Steven Valdezc8e0f902018-07-14 11:23:01 -04005160 return false;
5161 }
David Benjamin5298ef92020-03-13 12:17:30 -04005162
5163 // Although the levels are conceptually separate, BoringSSL finishes writing
5164 // data from a previous level before installing keys for the next level.
5165 if (!allow_out_of_order_writes_) {
5166 switch (level) {
5167 case ssl_encryption_early_data:
5168 ADD_FAILURE() << "unexpected handshake data at early data level";
5169 return false;
5170 case ssl_encryption_initial:
5171 if (!levels_[ssl_encryption_handshake].write_secret.empty()) {
5172 ADD_FAILURE()
5173 << LevelToString(level)
5174 << " handshake data written after handshake keys installed";
5175 return false;
5176 }
5177 OPENSSL_FALLTHROUGH;
5178 case ssl_encryption_handshake:
5179 if (!levels_[ssl_encryption_application].write_secret.empty()) {
5180 ADD_FAILURE()
5181 << LevelToString(level)
5182 << " handshake data written after application keys installed";
5183 return false;
5184 }
5185 OPENSSL_FALLTHROUGH;
5186 case ssl_encryption_application:
5187 break;
5188 }
5189 }
5190
Steven Valdezc8e0f902018-07-14 11:23:01 -04005191 levels_[level].write_data.insert(levels_[level].write_data.end(),
5192 data.begin(), data.end());
5193 return true;
5194 }
5195
5196 bool SendAlert(ssl_encryption_level_t level, uint8_t alert_value) {
5197 if (has_alert_) {
5198 ADD_FAILURE() << "duplicate alert sent";
5199 return false;
5200 }
5201
5202 if (levels_[level].write_secret.empty()) {
David Benjamin1e859052020-02-09 16:04:58 -05005203 ADD_FAILURE() << LevelToString(level)
5204 << " write secret not yet configured";
Steven Valdezc8e0f902018-07-14 11:23:01 -04005205 return false;
5206 }
5207
5208 has_alert_ = true;
5209 alert_level_ = level;
5210 alert_ = alert_value;
5211 return true;
5212 }
5213
5214 bool ReadHandshakeData(std::vector<uint8_t> *out,
5215 ssl_encryption_level_t level,
5216 size_t num = std::numeric_limits<size_t>::max()) {
5217 if (levels_[level].read_secret.empty()) {
David Benjamind6343572019-08-15 17:29:02 -04005218 ADD_FAILURE() << "data read before keys configured in level " << level;
Steven Valdezc8e0f902018-07-14 11:23:01 -04005219 return false;
5220 }
5221 // The peer may not have configured any keys yet.
5222 if (peer_->levels_[level].write_secret.empty()) {
David Benjamind0b97942019-08-21 12:54:20 -04005223 out->clear();
Steven Valdezc8e0f902018-07-14 11:23:01 -04005224 return true;
5225 }
5226 // Check the peer computed the same key.
5227 if (peer_->levels_[level].write_secret != levels_[level].read_secret) {
David Benjamind6343572019-08-15 17:29:02 -04005228 ADD_FAILURE() << "peer write key does not match read key in level "
5229 << level;
Steven Valdezc8e0f902018-07-14 11:23:01 -04005230 return false;
5231 }
Steven Valdez384d0ea2018-11-06 10:45:36 -05005232 if (peer_->levels_[level].cipher != levels_[level].cipher) {
David Benjamind6343572019-08-15 17:29:02 -04005233 ADD_FAILURE() << "peer cipher does not match in level " << level;
Steven Valdez384d0ea2018-11-06 10:45:36 -05005234 return false;
5235 }
Steven Valdezc8e0f902018-07-14 11:23:01 -04005236 std::vector<uint8_t> *peer_data = &peer_->levels_[level].write_data;
5237 num = std::min(num, peer_data->size());
5238 out->assign(peer_data->begin(), peer_data->begin() + num);
5239 peer_data->erase(peer_data->begin(), peer_data->begin() + num);
5240 return true;
5241 }
5242
5243 private:
David Benjamind6343572019-08-15 17:29:02 -04005244 Role role_;
Steven Valdezc8e0f902018-07-14 11:23:01 -04005245 MockQUICTransport *peer_ = nullptr;
5246
David Benjamin5298ef92020-03-13 12:17:30 -04005247 bool allow_out_of_order_writes_ = false;
Steven Valdezc8e0f902018-07-14 11:23:01 -04005248 bool has_alert_ = false;
5249 ssl_encryption_level_t alert_level_ = ssl_encryption_initial;
5250 uint8_t alert_ = 0;
5251
5252 struct Level {
5253 std::vector<uint8_t> write_data;
5254 std::vector<uint8_t> write_secret;
5255 std::vector<uint8_t> read_secret;
Steven Valdez384d0ea2018-11-06 10:45:36 -05005256 uint32_t cipher = 0;
Steven Valdezc8e0f902018-07-14 11:23:01 -04005257 };
5258 Level levels_[kNumQUICLevels];
5259};
5260
5261class MockQUICTransportPair {
5262 public:
David Benjamind6343572019-08-15 17:29:02 -04005263 MockQUICTransportPair()
5264 : client_(MockQUICTransport::Role::kClient),
5265 server_(MockQUICTransport::Role::kServer) {
Steven Valdezc8e0f902018-07-14 11:23:01 -04005266 client_.set_peer(&server_);
David Benjamind6343572019-08-15 17:29:02 -04005267 server_.set_peer(&client_);
Steven Valdezc8e0f902018-07-14 11:23:01 -04005268 }
5269
5270 ~MockQUICTransportPair() {
Steven Valdezc8e0f902018-07-14 11:23:01 -04005271 client_.set_peer(nullptr);
David Benjamind6343572019-08-15 17:29:02 -04005272 server_.set_peer(nullptr);
Steven Valdezc8e0f902018-07-14 11:23:01 -04005273 }
5274
5275 MockQUICTransport *client() { return &client_; }
5276 MockQUICTransport *server() { return &server_; }
5277
5278 bool SecretsMatch(ssl_encryption_level_t level) const {
David Benjamin1e859052020-02-09 16:04:58 -05005279 // We only need to check |HasReadSecret| and |HasWriteSecret| on |client_|.
5280 // |PeerSecretsMatch| checks that |server_| is analogously configured.
5281 return client_.PeerSecretsMatch(level) &&
5282 client_.HasWriteSecret(level) &&
5283 (level == ssl_encryption_early_data || client_.HasReadSecret(level));
Steven Valdezc8e0f902018-07-14 11:23:01 -04005284 }
5285
5286 private:
5287 MockQUICTransport client_;
5288 MockQUICTransport server_;
5289};
5290
5291class QUICMethodTest : public testing::Test {
5292 protected:
5293 void SetUp() override {
5294 client_ctx_.reset(SSL_CTX_new(TLS_method()));
5295 server_ctx_.reset(SSL_CTX_new(TLS_method()));
5296 ASSERT_TRUE(client_ctx_);
5297 ASSERT_TRUE(server_ctx_);
5298
5299 bssl::UniquePtr<X509> cert = GetTestCertificate();
5300 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
5301 ASSERT_TRUE(cert);
5302 ASSERT_TRUE(key);
5303 ASSERT_TRUE(SSL_CTX_use_certificate(server_ctx_.get(), cert.get()));
5304 ASSERT_TRUE(SSL_CTX_use_PrivateKey(server_ctx_.get(), key.get()));
5305
5306 SSL_CTX_set_min_proto_version(server_ctx_.get(), TLS1_3_VERSION);
5307 SSL_CTX_set_max_proto_version(server_ctx_.get(), TLS1_3_VERSION);
5308 SSL_CTX_set_min_proto_version(client_ctx_.get(), TLS1_3_VERSION);
5309 SSL_CTX_set_max_proto_version(client_ctx_.get(), TLS1_3_VERSION);
Nick Harper74161f42020-07-24 15:35:27 -07005310
5311 static const uint8_t kALPNProtos[] = {0x03, 'f', 'o', 'o'};
5312 ASSERT_EQ(SSL_CTX_set_alpn_protos(client_ctx_.get(), kALPNProtos,
5313 sizeof(kALPNProtos)),
5314 0);
5315 SSL_CTX_set_alpn_select_cb(
5316 server_ctx_.get(),
5317 [](SSL *ssl, const uint8_t **out, uint8_t *out_len, const uint8_t *in,
5318 unsigned in_len, void *arg) -> int {
5319 return SSL_select_next_proto(
5320 const_cast<uint8_t **>(out), out_len, in, in_len,
5321 kALPNProtos, sizeof(kALPNProtos)) == OPENSSL_NPN_NEGOTIATED
5322 ? SSL_TLSEXT_ERR_OK
5323 : SSL_TLSEXT_ERR_NOACK;
5324 },
5325 nullptr);
Steven Valdezc8e0f902018-07-14 11:23:01 -04005326 }
5327
5328 static MockQUICTransport *TransportFromSSL(const SSL *ssl) {
5329 return ex_data_.Get(ssl);
5330 }
5331
5332 static bool ProvideHandshakeData(
5333 SSL *ssl, size_t num = std::numeric_limits<size_t>::max()) {
5334 MockQUICTransport *transport = TransportFromSSL(ssl);
5335 ssl_encryption_level_t level = SSL_quic_read_level(ssl);
5336 std::vector<uint8_t> data;
5337 return transport->ReadHandshakeData(&data, level, num) &&
5338 SSL_provide_quic_data(ssl, level, data.data(), data.size());
5339 }
5340
David Benjamin5298ef92020-03-13 12:17:30 -04005341 void AllowOutOfOrderWrites() {
5342 allow_out_of_order_writes_ = true;
5343 }
5344
Steven Valdezc8e0f902018-07-14 11:23:01 -04005345 bool CreateClientAndServer() {
5346 client_.reset(SSL_new(client_ctx_.get()));
5347 server_.reset(SSL_new(server_ctx_.get()));
5348 if (!client_ || !server_) {
5349 return false;
5350 }
5351
5352 SSL_set_connect_state(client_.get());
5353 SSL_set_accept_state(server_.get());
5354
David Benjamind6343572019-08-15 17:29:02 -04005355 transport_.reset(new MockQUICTransportPair);
5356 ex_data_.Set(client_.get(), transport_->client());
5357 ex_data_.Set(server_.get(), transport_->server());
David Benjamin5298ef92020-03-13 12:17:30 -04005358 if (allow_out_of_order_writes_) {
5359 transport_->client()->AllowOutOfOrderWrites();
5360 transport_->server()->AllowOutOfOrderWrites();
5361 }
Nick Harper7c522992020-04-30 14:15:49 -07005362 static const uint8_t client_transport_params[] = {0};
5363 if (!SSL_set_quic_transport_params(client_.get(), client_transport_params,
5364 sizeof(client_transport_params)) ||
5365 !SSL_set_quic_transport_params(server_.get(),
5366 server_transport_params_.data(),
5367 server_transport_params_.size()) ||
5368 !SSL_set_quic_early_data_context(
5369 server_.get(), server_quic_early_data_context_.data(),
5370 server_quic_early_data_context_.size())) {
Nick Harper72cff812020-03-26 18:06:16 -07005371 return false;
5372 }
Steven Valdezc8e0f902018-07-14 11:23:01 -04005373 return true;
5374 }
5375
Nick Harper72cff812020-03-26 18:06:16 -07005376 enum class ExpectedError {
5377 kNoError,
5378 kClientError,
5379 kServerError,
5380 };
5381
David Benjamind6343572019-08-15 17:29:02 -04005382 // CompleteHandshakesForQUIC runs |SSL_do_handshake| on |client_| and
5383 // |server_| until each completes once. It returns true on success and false
5384 // on failure.
5385 bool CompleteHandshakesForQUIC() {
Nick Harper72cff812020-03-26 18:06:16 -07005386 return RunQUICHandshakesAndExpectError(ExpectedError::kNoError);
5387 }
5388
5389 // Runs |SSL_do_handshake| on |client_| and |server_| until each completes
5390 // once. If |expect_client_error| is true, it will return true only if the
5391 // client handshake failed. Otherwise, it returns true if both handshakes
5392 // succeed and false otherwise.
5393 bool RunQUICHandshakesAndExpectError(ExpectedError expected_error) {
David Benjamind6343572019-08-15 17:29:02 -04005394 bool client_done = false, server_done = false;
5395 while (!client_done || !server_done) {
5396 if (!client_done) {
5397 if (!ProvideHandshakeData(client_.get())) {
5398 ADD_FAILURE() << "ProvideHandshakeData(client_) failed";
5399 return false;
5400 }
5401 int client_ret = SSL_do_handshake(client_.get());
David Benjamin2fb729d2020-02-20 17:37:33 -05005402 int client_err = SSL_get_error(client_.get(), client_ret);
David Benjamind6343572019-08-15 17:29:02 -04005403 if (client_ret == 1) {
5404 client_done = true;
David Benjamin2fb729d2020-02-20 17:37:33 -05005405 } else if (client_ret != -1 || client_err != SSL_ERROR_WANT_READ) {
Nick Harper72cff812020-03-26 18:06:16 -07005406 if (expected_error == ExpectedError::kClientError) {
5407 return true;
5408 }
David Benjamin2fb729d2020-02-20 17:37:33 -05005409 ADD_FAILURE() << "Unexpected client output: " << client_ret << " "
5410 << client_err;
5411 return false;
David Benjamind6343572019-08-15 17:29:02 -04005412 }
5413 }
5414
5415 if (!server_done) {
5416 if (!ProvideHandshakeData(server_.get())) {
5417 ADD_FAILURE() << "ProvideHandshakeData(server_) failed";
5418 return false;
5419 }
5420 int server_ret = SSL_do_handshake(server_.get());
David Benjamin2fb729d2020-02-20 17:37:33 -05005421 int server_err = SSL_get_error(server_.get(), server_ret);
David Benjamind6343572019-08-15 17:29:02 -04005422 if (server_ret == 1) {
5423 server_done = true;
David Benjamin2fb729d2020-02-20 17:37:33 -05005424 } else if (server_ret != -1 || server_err != SSL_ERROR_WANT_READ) {
Nick Harper72cff812020-03-26 18:06:16 -07005425 if (expected_error == ExpectedError::kServerError) {
5426 return true;
5427 }
David Benjamin2fb729d2020-02-20 17:37:33 -05005428 ADD_FAILURE() << "Unexpected server output: " << server_ret << " "
5429 << server_err;
5430 return false;
David Benjamind6343572019-08-15 17:29:02 -04005431 }
5432 }
5433 }
Nick Harper72cff812020-03-26 18:06:16 -07005434 return expected_error == ExpectedError::kNoError;
David Benjamind6343572019-08-15 17:29:02 -04005435 }
5436
5437 bssl::UniquePtr<SSL_SESSION> CreateClientSessionForQUIC() {
5438 g_last_session = nullptr;
5439 SSL_CTX_sess_set_new_cb(client_ctx_.get(), SaveLastSession);
5440 if (!CreateClientAndServer() ||
5441 !CompleteHandshakesForQUIC()) {
5442 return nullptr;
Steven Valdeze6eef1c2018-11-09 13:32:34 -05005443 }
5444
David Benjamind6343572019-08-15 17:29:02 -04005445 // The server sent NewSessionTicket messages in the handshake.
5446 if (!ProvideHandshakeData(client_.get()) ||
5447 !SSL_process_quic_post_handshake(client_.get())) {
5448 return nullptr;
5449 }
Steven Valdeze6eef1c2018-11-09 13:32:34 -05005450
David Benjamind6343572019-08-15 17:29:02 -04005451 return std::move(g_last_session);
5452 }
5453
5454 void ExpectHandshakeSuccess() {
5455 EXPECT_TRUE(transport_->SecretsMatch(ssl_encryption_application));
5456 EXPECT_EQ(ssl_encryption_application, SSL_quic_read_level(client_.get()));
5457 EXPECT_EQ(ssl_encryption_application, SSL_quic_write_level(client_.get()));
5458 EXPECT_EQ(ssl_encryption_application, SSL_quic_read_level(server_.get()));
5459 EXPECT_EQ(ssl_encryption_application, SSL_quic_write_level(server_.get()));
5460 EXPECT_FALSE(transport_->client()->has_alert());
5461 EXPECT_FALSE(transport_->server()->has_alert());
5462
5463 // SSL_do_handshake is now idempotent.
5464 EXPECT_EQ(SSL_do_handshake(client_.get()), 1);
5465 EXPECT_EQ(SSL_do_handshake(server_.get()), 1);
Steven Valdeze6eef1c2018-11-09 13:32:34 -05005466 }
5467
David Benjamin1e859052020-02-09 16:04:58 -05005468 // Returns a default SSL_QUIC_METHOD. Individual methods may be overwritten by
5469 // the test.
5470 SSL_QUIC_METHOD DefaultQUICMethod() {
5471 return SSL_QUIC_METHOD{
5472 SetReadSecretCallback, SetWriteSecretCallback, AddHandshakeDataCallback,
5473 FlushFlightCallback, SendAlertCallback,
5474 };
5475 }
Steven Valdezc8e0f902018-07-14 11:23:01 -04005476
David Benjamin1e859052020-02-09 16:04:58 -05005477 static int SetReadSecretCallback(SSL *ssl, ssl_encryption_level_t level,
5478 const SSL_CIPHER *cipher,
5479 const uint8_t *secret, size_t secret_len) {
5480 return TransportFromSSL(ssl)->SetReadSecret(
5481 level, cipher, MakeConstSpan(secret, secret_len));
5482 }
5483
5484 static int SetWriteSecretCallback(SSL *ssl, ssl_encryption_level_t level,
5485 const SSL_CIPHER *cipher,
5486 const uint8_t *secret, size_t secret_len) {
5487 return TransportFromSSL(ssl)->SetWriteSecret(
5488 level, cipher, MakeConstSpan(secret, secret_len));
Steven Valdezc8e0f902018-07-14 11:23:01 -04005489 }
5490
David Benjamincc9d9352018-10-30 19:45:22 -05005491 static int AddHandshakeDataCallback(SSL *ssl,
5492 enum ssl_encryption_level_t level,
5493 const uint8_t *data, size_t len) {
Steven Valdezc8e0f902018-07-14 11:23:01 -04005494 EXPECT_EQ(level, SSL_quic_write_level(ssl));
5495 return TransportFromSSL(ssl)->WriteHandshakeData(level,
5496 MakeConstSpan(data, len));
5497 }
5498
5499 static int FlushFlightCallback(SSL *ssl) { return 1; }
5500
5501 static int SendAlertCallback(SSL *ssl, ssl_encryption_level_t level,
5502 uint8_t alert) {
5503 EXPECT_EQ(level, SSL_quic_write_level(ssl));
5504 return TransportFromSSL(ssl)->SendAlert(level, alert);
5505 }
5506
5507 bssl::UniquePtr<SSL_CTX> client_ctx_;
5508 bssl::UniquePtr<SSL_CTX> server_ctx_;
5509
5510 static UnownedSSLExData<MockQUICTransport> ex_data_;
David Benjamind6343572019-08-15 17:29:02 -04005511 std::unique_ptr<MockQUICTransportPair> transport_;
Steven Valdezc8e0f902018-07-14 11:23:01 -04005512
5513 bssl::UniquePtr<SSL> client_;
5514 bssl::UniquePtr<SSL> server_;
David Benjamin5298ef92020-03-13 12:17:30 -04005515
Nick Harper7c522992020-04-30 14:15:49 -07005516 std::vector<uint8_t> server_transport_params_ = {1};
5517 std::vector<uint8_t> server_quic_early_data_context_ = {2};
5518
David Benjamin5298ef92020-03-13 12:17:30 -04005519 bool allow_out_of_order_writes_ = false;
Steven Valdezc8e0f902018-07-14 11:23:01 -04005520};
5521
5522UnownedSSLExData<MockQUICTransport> QUICMethodTest::ex_data_;
5523
David Benjaminfd863b62019-07-25 13:51:32 -04005524// Test a full handshake and resumption work.
Steven Valdezc8e0f902018-07-14 11:23:01 -04005525TEST_F(QUICMethodTest, Basic) {
David Benjamin1e859052020-02-09 16:04:58 -05005526 const SSL_QUIC_METHOD quic_method = DefaultQUICMethod();
Steven Valdezc8e0f902018-07-14 11:23:01 -04005527
Steven Valdeze6eef1c2018-11-09 13:32:34 -05005528 g_last_session = nullptr;
5529
5530 SSL_CTX_set_session_cache_mode(client_ctx_.get(), SSL_SESS_CACHE_BOTH);
5531 SSL_CTX_sess_set_new_cb(client_ctx_.get(), SaveLastSession);
Steven Valdezc8e0f902018-07-14 11:23:01 -04005532 ASSERT_TRUE(SSL_CTX_set_quic_method(client_ctx_.get(), &quic_method));
5533 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), &quic_method));
David Benjamind6343572019-08-15 17:29:02 -04005534
Steven Valdezc8e0f902018-07-14 11:23:01 -04005535 ASSERT_TRUE(CreateClientAndServer());
David Benjamind6343572019-08-15 17:29:02 -04005536 ASSERT_TRUE(CompleteHandshakesForQUIC());
Steven Valdezc8e0f902018-07-14 11:23:01 -04005537
David Benjamind6343572019-08-15 17:29:02 -04005538 ExpectHandshakeSuccess();
5539 EXPECT_FALSE(SSL_session_reused(client_.get()));
5540 EXPECT_FALSE(SSL_session_reused(server_.get()));
Steven Valdezc8e0f902018-07-14 11:23:01 -04005541
5542 // The server sent NewSessionTicket messages in the handshake.
Steven Valdeze6eef1c2018-11-09 13:32:34 -05005543 EXPECT_FALSE(g_last_session);
5544 ASSERT_TRUE(ProvideHandshakeData(client_.get()));
5545 EXPECT_EQ(SSL_process_quic_post_handshake(client_.get()), 1);
5546 EXPECT_TRUE(g_last_session);
5547
5548 // Create a second connection to verify resumption works.
David Benjamind6343572019-08-15 17:29:02 -04005549 ASSERT_TRUE(CreateClientAndServer());
Steven Valdeze6eef1c2018-11-09 13:32:34 -05005550 bssl::UniquePtr<SSL_SESSION> session = std::move(g_last_session);
5551 SSL_set_session(client_.get(), session.get());
5552
David Benjamind6343572019-08-15 17:29:02 -04005553 ASSERT_TRUE(CompleteHandshakesForQUIC());
Steven Valdeze6eef1c2018-11-09 13:32:34 -05005554
David Benjamind6343572019-08-15 17:29:02 -04005555 ExpectHandshakeSuccess();
Steven Valdeze6eef1c2018-11-09 13:32:34 -05005556 EXPECT_TRUE(SSL_session_reused(client_.get()));
5557 EXPECT_TRUE(SSL_session_reused(server_.get()));
Steven Valdezc8e0f902018-07-14 11:23:01 -04005558}
5559
David Benjaminfd863b62019-07-25 13:51:32 -04005560// Test that HelloRetryRequest in QUIC works.
5561TEST_F(QUICMethodTest, HelloRetryRequest) {
David Benjamin1e859052020-02-09 16:04:58 -05005562 const SSL_QUIC_METHOD quic_method = DefaultQUICMethod();
David Benjaminfd863b62019-07-25 13:51:32 -04005563
5564 ASSERT_TRUE(SSL_CTX_set_quic_method(client_ctx_.get(), &quic_method));
5565 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), &quic_method));
5566
5567 // BoringSSL predicts the most preferred curve, so using different preferences
5568 // will trigger HelloRetryRequest.
5569 static const int kClientPrefs[] = {NID_X25519, NID_X9_62_prime256v1};
5570 ASSERT_TRUE(SSL_CTX_set1_curves(client_ctx_.get(), kClientPrefs,
5571 OPENSSL_ARRAY_SIZE(kClientPrefs)));
5572 static const int kServerPrefs[] = {NID_X9_62_prime256v1, NID_X25519};
5573 ASSERT_TRUE(SSL_CTX_set1_curves(server_ctx_.get(), kServerPrefs,
5574 OPENSSL_ARRAY_SIZE(kServerPrefs)));
5575
5576 ASSERT_TRUE(CreateClientAndServer());
David Benjamind6343572019-08-15 17:29:02 -04005577 ASSERT_TRUE(CompleteHandshakesForQUIC());
5578 ExpectHandshakeSuccess();
5579}
David Benjaminfd863b62019-07-25 13:51:32 -04005580
Nick Harpere32549e2020-05-06 14:27:11 -07005581// Test that the client does not send a legacy_session_id in the ClientHello.
5582TEST_F(QUICMethodTest, NoLegacySessionId) {
5583 const SSL_QUIC_METHOD quic_method = DefaultQUICMethod();
5584
5585 ASSERT_TRUE(SSL_CTX_set_quic_method(client_ctx_.get(), &quic_method));
5586 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), &quic_method));
5587 // Check that the session ID length is 0 in an early callback.
5588 SSL_CTX_set_select_certificate_cb(
5589 server_ctx_.get(),
5590 [](const SSL_CLIENT_HELLO *client_hello) -> ssl_select_cert_result_t {
5591 EXPECT_EQ(client_hello->session_id_len, 0u);
5592 return ssl_select_cert_success;
5593 });
5594
5595 ASSERT_TRUE(CreateClientAndServer());
5596 ASSERT_TRUE(CompleteHandshakesForQUIC());
5597
5598 ExpectHandshakeSuccess();
5599}
5600
David Benjamin1e859052020-02-09 16:04:58 -05005601// Test that, even in a 1-RTT handshake, the server installs keys at the right
5602// time. Half-RTT keys are available early, but 1-RTT read keys are deferred.
5603TEST_F(QUICMethodTest, HalfRTTKeys) {
5604 const SSL_QUIC_METHOD quic_method = DefaultQUICMethod();
5605
5606 ASSERT_TRUE(SSL_CTX_set_quic_method(client_ctx_.get(), &quic_method));
5607 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), &quic_method));
5608 ASSERT_TRUE(CreateClientAndServer());
5609
5610 // The client sends ClientHello.
5611 ASSERT_EQ(SSL_do_handshake(client_.get()), -1);
5612 ASSERT_EQ(SSL_ERROR_WANT_READ, SSL_get_error(client_.get(), -1));
5613
5614 // The server reads ClientHello and sends ServerHello..Finished.
5615 ASSERT_TRUE(ProvideHandshakeData(server_.get()));
5616 ASSERT_EQ(SSL_do_handshake(server_.get()), -1);
5617 ASSERT_EQ(SSL_ERROR_WANT_READ, SSL_get_error(server_.get(), -1));
5618
5619 // At this point, the server has half-RTT write keys, but it cannot access
5620 // 1-RTT read keys until client Finished.
5621 EXPECT_TRUE(transport_->server()->HasWriteSecret(ssl_encryption_application));
5622 EXPECT_FALSE(transport_->server()->HasReadSecret(ssl_encryption_application));
5623
5624 // Finish up the client and server handshakes.
5625 ASSERT_TRUE(CompleteHandshakesForQUIC());
5626
5627 // Both sides can now exchange 1-RTT data.
5628 ExpectHandshakeSuccess();
5629}
5630
David Benjamind6343572019-08-15 17:29:02 -04005631TEST_F(QUICMethodTest, ZeroRTTAccept) {
David Benjamin1e859052020-02-09 16:04:58 -05005632 const SSL_QUIC_METHOD quic_method = DefaultQUICMethod();
David Benjamind6343572019-08-15 17:29:02 -04005633
5634 SSL_CTX_set_session_cache_mode(client_ctx_.get(), SSL_SESS_CACHE_BOTH);
5635 SSL_CTX_set_early_data_enabled(client_ctx_.get(), 1);
5636 SSL_CTX_set_early_data_enabled(server_ctx_.get(), 1);
5637 ASSERT_TRUE(SSL_CTX_set_quic_method(client_ctx_.get(), &quic_method));
5638 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), &quic_method));
5639
5640 bssl::UniquePtr<SSL_SESSION> session = CreateClientSessionForQUIC();
5641 ASSERT_TRUE(session);
5642
5643 ASSERT_TRUE(CreateClientAndServer());
5644 SSL_set_session(client_.get(), session.get());
5645
5646 // The client handshake should return immediately into the early data state.
5647 ASSERT_EQ(SSL_do_handshake(client_.get()), 1);
5648 EXPECT_TRUE(SSL_in_early_data(client_.get()));
5649 // The transport should have keys for sending 0-RTT data.
David Benjamin1e859052020-02-09 16:04:58 -05005650 EXPECT_TRUE(transport_->client()->HasWriteSecret(ssl_encryption_early_data));
David Benjamind6343572019-08-15 17:29:02 -04005651
5652 // The server will consume the ClientHello and also enter the early data
5653 // state.
5654 ASSERT_TRUE(ProvideHandshakeData(server_.get()));
5655 ASSERT_EQ(SSL_do_handshake(server_.get()), 1);
5656 EXPECT_TRUE(SSL_in_early_data(server_.get()));
5657 EXPECT_TRUE(transport_->SecretsMatch(ssl_encryption_early_data));
David Benjamin1e859052020-02-09 16:04:58 -05005658 // At this point, the server has half-RTT write keys, but it cannot access
5659 // 1-RTT read keys until client Finished.
5660 EXPECT_TRUE(transport_->server()->HasWriteSecret(ssl_encryption_application));
5661 EXPECT_FALSE(transport_->server()->HasReadSecret(ssl_encryption_application));
David Benjamind6343572019-08-15 17:29:02 -04005662
5663 // Finish up the client and server handshakes.
5664 ASSERT_TRUE(CompleteHandshakesForQUIC());
5665
5666 // Both sides can now exchange 1-RTT data.
5667 ExpectHandshakeSuccess();
5668 EXPECT_TRUE(SSL_session_reused(client_.get()));
5669 EXPECT_TRUE(SSL_session_reused(server_.get()));
5670 EXPECT_FALSE(SSL_in_early_data(client_.get()));
5671 EXPECT_FALSE(SSL_in_early_data(server_.get()));
5672 EXPECT_TRUE(SSL_early_data_accepted(client_.get()));
5673 EXPECT_TRUE(SSL_early_data_accepted(server_.get()));
Nick Harper5e086952020-09-30 13:59:14 -07005674
5675 // Finish handling post-handshake messages after the first 0-RTT resumption.
5676 EXPECT_TRUE(ProvideHandshakeData(client_.get()));
5677 EXPECT_TRUE(SSL_process_quic_post_handshake(client_.get()));
5678
5679 // Perform a second 0-RTT resumption attempt, and confirm that 0-RTT is
5680 // accepted again.
5681 ASSERT_TRUE(CreateClientAndServer());
5682 SSL_set_session(client_.get(), g_last_session.get());
5683
5684 // The client handshake should return immediately into the early data state.
5685 ASSERT_EQ(SSL_do_handshake(client_.get()), 1);
5686 EXPECT_TRUE(SSL_in_early_data(client_.get()));
5687 // The transport should have keys for sending 0-RTT data.
5688 EXPECT_TRUE(transport_->client()->HasWriteSecret(ssl_encryption_early_data));
5689
5690 // The server will consume the ClientHello and also enter the early data
5691 // state.
5692 ASSERT_TRUE(ProvideHandshakeData(server_.get()));
5693 ASSERT_EQ(SSL_do_handshake(server_.get()), 1);
5694 EXPECT_TRUE(SSL_in_early_data(server_.get()));
5695 EXPECT_TRUE(transport_->SecretsMatch(ssl_encryption_early_data));
5696 // At this point, the server has half-RTT write keys, but it cannot access
5697 // 1-RTT read keys until client Finished.
5698 EXPECT_TRUE(transport_->server()->HasWriteSecret(ssl_encryption_application));
5699 EXPECT_FALSE(transport_->server()->HasReadSecret(ssl_encryption_application));
5700
5701 // Finish up the client and server handshakes.
5702 ASSERT_TRUE(CompleteHandshakesForQUIC());
5703
5704 // Both sides can now exchange 1-RTT data.
5705 ExpectHandshakeSuccess();
5706 EXPECT_TRUE(SSL_session_reused(client_.get()));
5707 EXPECT_TRUE(SSL_session_reused(server_.get()));
5708 EXPECT_FALSE(SSL_in_early_data(client_.get()));
5709 EXPECT_FALSE(SSL_in_early_data(server_.get()));
5710 EXPECT_TRUE(SSL_early_data_accepted(client_.get()));
5711 EXPECT_TRUE(SSL_early_data_accepted(server_.get()));
5712 EXPECT_EQ(SSL_get_early_data_reason(client_.get()), ssl_early_data_accepted);
5713 EXPECT_EQ(SSL_get_early_data_reason(server_.get()), ssl_early_data_accepted);
David Benjamind6343572019-08-15 17:29:02 -04005714}
5715
Nick Harper7c522992020-04-30 14:15:49 -07005716TEST_F(QUICMethodTest, ZeroRTTRejectMismatchedParameters) {
5717 const SSL_QUIC_METHOD quic_method = DefaultQUICMethod();
5718
5719 SSL_CTX_set_session_cache_mode(client_ctx_.get(), SSL_SESS_CACHE_BOTH);
5720 SSL_CTX_set_early_data_enabled(client_ctx_.get(), 1);
5721 SSL_CTX_set_early_data_enabled(server_ctx_.get(), 1);
5722 ASSERT_TRUE(SSL_CTX_set_quic_method(client_ctx_.get(), &quic_method));
5723 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), &quic_method));
5724
5725
5726 bssl::UniquePtr<SSL_SESSION> session = CreateClientSessionForQUIC();
5727 ASSERT_TRUE(session);
5728
Nick Harper85194322020-05-20 16:59:29 -07005729 ASSERT_TRUE(CreateClientAndServer());
5730 static const uint8_t new_context[] = {4};
5731 ASSERT_TRUE(SSL_set_quic_early_data_context(server_.get(), new_context,
5732 sizeof(new_context)));
5733 SSL_set_session(client_.get(), session.get());
Nick Harper7c522992020-04-30 14:15:49 -07005734
Nick Harper85194322020-05-20 16:59:29 -07005735 // The client handshake should return immediately into the early data
5736 // state.
5737 ASSERT_EQ(SSL_do_handshake(client_.get()), 1);
5738 EXPECT_TRUE(SSL_in_early_data(client_.get()));
5739 // The transport should have keys for sending 0-RTT data.
5740 EXPECT_TRUE(transport_->client()->HasWriteSecret(ssl_encryption_early_data));
Nick Harper7c522992020-04-30 14:15:49 -07005741
Nick Harper85194322020-05-20 16:59:29 -07005742 // The server will consume the ClientHello, but it will not accept 0-RTT.
5743 ASSERT_TRUE(ProvideHandshakeData(server_.get()));
5744 ASSERT_EQ(SSL_do_handshake(server_.get()), -1);
5745 EXPECT_EQ(SSL_ERROR_WANT_READ, SSL_get_error(server_.get(), -1));
5746 EXPECT_FALSE(SSL_in_early_data(server_.get()));
5747 EXPECT_FALSE(transport_->server()->HasReadSecret(ssl_encryption_early_data));
Nick Harper7c522992020-04-30 14:15:49 -07005748
Nick Harper85194322020-05-20 16:59:29 -07005749 // The client consumes the server response and signals 0-RTT rejection.
5750 for (;;) {
5751 ASSERT_TRUE(ProvideHandshakeData(client_.get()));
5752 ASSERT_EQ(-1, SSL_do_handshake(client_.get()));
5753 int err = SSL_get_error(client_.get(), -1);
5754 if (err == SSL_ERROR_EARLY_DATA_REJECTED) {
5755 break;
Nick Harper7c522992020-04-30 14:15:49 -07005756 }
Nick Harper85194322020-05-20 16:59:29 -07005757 ASSERT_EQ(SSL_ERROR_WANT_READ, err);
Nick Harper7c522992020-04-30 14:15:49 -07005758 }
Nick Harper85194322020-05-20 16:59:29 -07005759
5760 // As in TLS over TCP, 0-RTT rejection is sticky.
5761 ASSERT_EQ(-1, SSL_do_handshake(client_.get()));
5762 ASSERT_EQ(SSL_ERROR_EARLY_DATA_REJECTED, SSL_get_error(client_.get(), -1));
5763
5764 // Finish up the client and server handshakes.
5765 SSL_reset_early_data_reject(client_.get());
5766 ASSERT_TRUE(CompleteHandshakesForQUIC());
5767
5768 // Both sides can now exchange 1-RTT data.
5769 ExpectHandshakeSuccess();
5770 EXPECT_TRUE(SSL_session_reused(client_.get()));
5771 EXPECT_TRUE(SSL_session_reused(server_.get()));
5772 EXPECT_FALSE(SSL_in_early_data(client_.get()));
5773 EXPECT_FALSE(SSL_in_early_data(server_.get()));
5774 EXPECT_FALSE(SSL_early_data_accepted(client_.get()));
5775 EXPECT_FALSE(SSL_early_data_accepted(server_.get()));
5776}
5777
5778TEST_F(QUICMethodTest, NoZeroRTTTicketWithoutEarlyDataContext) {
5779 server_quic_early_data_context_ = {};
5780 const SSL_QUIC_METHOD quic_method = DefaultQUICMethod();
5781
5782 SSL_CTX_set_session_cache_mode(client_ctx_.get(), SSL_SESS_CACHE_BOTH);
5783 SSL_CTX_set_early_data_enabled(client_ctx_.get(), 1);
5784 SSL_CTX_set_early_data_enabled(server_ctx_.get(), 1);
5785 ASSERT_TRUE(SSL_CTX_set_quic_method(client_ctx_.get(), &quic_method));
5786 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), &quic_method));
5787
5788 bssl::UniquePtr<SSL_SESSION> session = CreateClientSessionForQUIC();
5789 ASSERT_TRUE(session);
5790 EXPECT_FALSE(SSL_SESSION_early_data_capable(session.get()));
Nick Harper7c522992020-04-30 14:15:49 -07005791}
5792
David Benjamind6343572019-08-15 17:29:02 -04005793TEST_F(QUICMethodTest, ZeroRTTReject) {
David Benjamin1e859052020-02-09 16:04:58 -05005794 const SSL_QUIC_METHOD quic_method = DefaultQUICMethod();
David Benjamind6343572019-08-15 17:29:02 -04005795
5796 SSL_CTX_set_session_cache_mode(client_ctx_.get(), SSL_SESS_CACHE_BOTH);
5797 SSL_CTX_set_early_data_enabled(client_ctx_.get(), 1);
5798 SSL_CTX_set_early_data_enabled(server_ctx_.get(), 1);
5799 ASSERT_TRUE(SSL_CTX_set_quic_method(client_ctx_.get(), &quic_method));
5800 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), &quic_method));
5801
5802 bssl::UniquePtr<SSL_SESSION> session = CreateClientSessionForQUIC();
5803 ASSERT_TRUE(session);
5804
5805 for (bool reject_hrr : {false, true}) {
5806 SCOPED_TRACE(reject_hrr);
5807
5808 ASSERT_TRUE(CreateClientAndServer());
5809 if (reject_hrr) {
5810 // Configure the server to prefer P-256, which will reject 0-RTT via
5811 // HelloRetryRequest.
5812 int p256 = NID_X9_62_prime256v1;
5813 ASSERT_TRUE(SSL_set1_curves(server_.get(), &p256, 1));
5814 } else {
5815 // Disable 0-RTT on the server, so it will reject it.
5816 SSL_set_early_data_enabled(server_.get(), 0);
David Benjaminfd863b62019-07-25 13:51:32 -04005817 }
David Benjamind6343572019-08-15 17:29:02 -04005818 SSL_set_session(client_.get(), session.get());
David Benjaminfd863b62019-07-25 13:51:32 -04005819
David Benjamind6343572019-08-15 17:29:02 -04005820 // The client handshake should return immediately into the early data state.
5821 ASSERT_EQ(SSL_do_handshake(client_.get()), 1);
5822 EXPECT_TRUE(SSL_in_early_data(client_.get()));
5823 // The transport should have keys for sending 0-RTT data.
David Benjamin1e859052020-02-09 16:04:58 -05005824 EXPECT_TRUE(
5825 transport_->client()->HasWriteSecret(ssl_encryption_early_data));
David Benjamind6343572019-08-15 17:29:02 -04005826
5827 // The server will consume the ClientHello, but it will not accept 0-RTT.
David Benjaminfd863b62019-07-25 13:51:32 -04005828 ASSERT_TRUE(ProvideHandshakeData(server_.get()));
David Benjamind6343572019-08-15 17:29:02 -04005829 ASSERT_EQ(SSL_do_handshake(server_.get()), -1);
5830 EXPECT_EQ(SSL_ERROR_WANT_READ, SSL_get_error(server_.get(), -1));
5831 EXPECT_FALSE(SSL_in_early_data(server_.get()));
David Benjamin1e859052020-02-09 16:04:58 -05005832 EXPECT_FALSE(
5833 transport_->server()->HasReadSecret(ssl_encryption_early_data));
David Benjamind6343572019-08-15 17:29:02 -04005834
5835 // The client consumes the server response and signals 0-RTT rejection.
5836 for (;;) {
5837 ASSERT_TRUE(ProvideHandshakeData(client_.get()));
5838 ASSERT_EQ(-1, SSL_do_handshake(client_.get()));
5839 int err = SSL_get_error(client_.get(), -1);
5840 if (err == SSL_ERROR_EARLY_DATA_REJECTED) {
5841 break;
5842 }
5843 ASSERT_EQ(SSL_ERROR_WANT_READ, err);
David Benjaminfd863b62019-07-25 13:51:32 -04005844 }
5845
David Benjamind6343572019-08-15 17:29:02 -04005846 // As in TLS over TCP, 0-RTT rejection is sticky.
5847 ASSERT_EQ(-1, SSL_do_handshake(client_.get()));
5848 ASSERT_EQ(SSL_ERROR_EARLY_DATA_REJECTED, SSL_get_error(client_.get(), -1));
5849
5850 // Finish up the client and server handshakes.
5851 SSL_reset_early_data_reject(client_.get());
5852 ASSERT_TRUE(CompleteHandshakesForQUIC());
5853
5854 // Both sides can now exchange 1-RTT data.
5855 ExpectHandshakeSuccess();
5856 EXPECT_TRUE(SSL_session_reused(client_.get()));
5857 EXPECT_TRUE(SSL_session_reused(server_.get()));
5858 EXPECT_FALSE(SSL_in_early_data(client_.get()));
5859 EXPECT_FALSE(SSL_in_early_data(server_.get()));
5860 EXPECT_FALSE(SSL_early_data_accepted(client_.get()));
5861 EXPECT_FALSE(SSL_early_data_accepted(server_.get()));
David Benjaminfd863b62019-07-25 13:51:32 -04005862 }
David Benjaminfd863b62019-07-25 13:51:32 -04005863}
5864
David Benjaminee0716f2019-11-19 14:16:28 +08005865TEST_F(QUICMethodTest, NoZeroRTTKeysBeforeReverify) {
David Benjamin1e859052020-02-09 16:04:58 -05005866 const SSL_QUIC_METHOD quic_method = DefaultQUICMethod();
David Benjaminee0716f2019-11-19 14:16:28 +08005867
5868 SSL_CTX_set_session_cache_mode(client_ctx_.get(), SSL_SESS_CACHE_BOTH);
5869 SSL_CTX_set_early_data_enabled(client_ctx_.get(), 1);
5870 SSL_CTX_set_reverify_on_resume(client_ctx_.get(), 1);
5871 SSL_CTX_set_early_data_enabled(server_ctx_.get(), 1);
5872 ASSERT_TRUE(SSL_CTX_set_quic_method(client_ctx_.get(), &quic_method));
5873 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), &quic_method));
5874
5875 bssl::UniquePtr<SSL_SESSION> session = CreateClientSessionForQUIC();
5876 ASSERT_TRUE(session);
5877
5878 ASSERT_TRUE(CreateClientAndServer());
5879 SSL_set_session(client_.get(), session.get());
5880
5881 // Configure the certificate (re)verification to never complete. The client
5882 // handshake should pause.
5883 SSL_set_custom_verify(
5884 client_.get(), SSL_VERIFY_PEER,
5885 [](SSL *ssl, uint8_t *out_alert) -> ssl_verify_result_t {
5886 return ssl_verify_retry;
5887 });
5888 ASSERT_EQ(SSL_do_handshake(client_.get()), -1);
5889 ASSERT_EQ(SSL_get_error(client_.get(), -1),
5890 SSL_ERROR_WANT_CERTIFICATE_VERIFY);
5891
5892 // The early data keys have not yet been released.
David Benjamin1e859052020-02-09 16:04:58 -05005893 EXPECT_FALSE(transport_->client()->HasWriteSecret(ssl_encryption_early_data));
David Benjaminee0716f2019-11-19 14:16:28 +08005894
5895 // After the verification completes, the handshake progresses to the 0-RTT
5896 // point and releases keys.
5897 SSL_set_custom_verify(
5898 client_.get(), SSL_VERIFY_PEER,
5899 [](SSL *ssl, uint8_t *out_alert) -> ssl_verify_result_t {
5900 return ssl_verify_ok;
5901 });
5902 ASSERT_EQ(SSL_do_handshake(client_.get()), 1);
5903 EXPECT_TRUE(SSL_in_early_data(client_.get()));
David Benjamin1e859052020-02-09 16:04:58 -05005904 EXPECT_TRUE(transport_->client()->HasWriteSecret(ssl_encryption_early_data));
David Benjaminee0716f2019-11-19 14:16:28 +08005905}
5906
Steven Valdezc8e0f902018-07-14 11:23:01 -04005907// Test only releasing data to QUIC one byte at a time on request, to maximize
5908// state machine pauses. Additionally, test that existing asynchronous callbacks
5909// still work.
5910TEST_F(QUICMethodTest, Async) {
David Benjamin1e859052020-02-09 16:04:58 -05005911 const SSL_QUIC_METHOD quic_method = DefaultQUICMethod();
Steven Valdezc8e0f902018-07-14 11:23:01 -04005912
5913 ASSERT_TRUE(SSL_CTX_set_quic_method(client_ctx_.get(), &quic_method));
5914 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), &quic_method));
5915 ASSERT_TRUE(CreateClientAndServer());
5916
5917 // Install an asynchronous certificate callback.
5918 bool cert_cb_ok = false;
5919 SSL_set_cert_cb(server_.get(),
5920 [](SSL *, void *arg) -> int {
5921 return *static_cast<bool *>(arg) ? 1 : -1;
5922 },
5923 &cert_cb_ok);
5924
5925 for (;;) {
5926 int client_ret = SSL_do_handshake(client_.get());
5927 if (client_ret != 1) {
5928 ASSERT_EQ(client_ret, -1);
5929 ASSERT_EQ(SSL_get_error(client_.get(), client_ret), SSL_ERROR_WANT_READ);
5930 ASSERT_TRUE(ProvideHandshakeData(client_.get(), 1));
5931 }
5932
5933 int server_ret = SSL_do_handshake(server_.get());
5934 if (server_ret != 1) {
5935 ASSERT_EQ(server_ret, -1);
5936 int ssl_err = SSL_get_error(server_.get(), server_ret);
5937 switch (ssl_err) {
5938 case SSL_ERROR_WANT_READ:
5939 ASSERT_TRUE(ProvideHandshakeData(server_.get(), 1));
5940 break;
5941 case SSL_ERROR_WANT_X509_LOOKUP:
5942 ASSERT_FALSE(cert_cb_ok);
5943 cert_cb_ok = true;
5944 break;
5945 default:
5946 FAIL() << "Unexpected SSL_get_error result: " << ssl_err;
5947 }
5948 }
5949
5950 if (client_ret == 1 && server_ret == 1) {
5951 break;
5952 }
5953 }
5954
David Benjamind6343572019-08-15 17:29:02 -04005955 ExpectHandshakeSuccess();
Steven Valdezc8e0f902018-07-14 11:23:01 -04005956}
5957
5958// Test buffering write data until explicit flushes.
5959TEST_F(QUICMethodTest, Buffered) {
David Benjamin5298ef92020-03-13 12:17:30 -04005960 AllowOutOfOrderWrites();
5961
Steven Valdezc8e0f902018-07-14 11:23:01 -04005962 struct BufferedFlight {
5963 std::vector<uint8_t> data[kNumQUICLevels];
5964 };
5965 static UnownedSSLExData<BufferedFlight> buffered_flights;
5966
David Benjamincc9d9352018-10-30 19:45:22 -05005967 auto add_handshake_data = [](SSL *ssl, enum ssl_encryption_level_t level,
5968 const uint8_t *data, size_t len) -> int {
Steven Valdezc8e0f902018-07-14 11:23:01 -04005969 BufferedFlight *flight = buffered_flights.Get(ssl);
5970 flight->data[level].insert(flight->data[level].end(), data, data + len);
5971 return 1;
5972 };
5973
5974 auto flush_flight = [](SSL *ssl) -> int {
5975 BufferedFlight *flight = buffered_flights.Get(ssl);
5976 for (size_t level = 0; level < kNumQUICLevels; level++) {
5977 if (!flight->data[level].empty()) {
5978 if (!TransportFromSSL(ssl)->WriteHandshakeData(
5979 static_cast<ssl_encryption_level_t>(level),
5980 flight->data[level])) {
5981 return 0;
5982 }
5983 flight->data[level].clear();
5984 }
5985 }
5986 return 1;
5987 };
5988
David Benjamin1e859052020-02-09 16:04:58 -05005989 SSL_QUIC_METHOD quic_method = DefaultQUICMethod();
5990 quic_method.add_handshake_data = add_handshake_data;
5991 quic_method.flush_flight = flush_flight;
Steven Valdezc8e0f902018-07-14 11:23:01 -04005992
5993 ASSERT_TRUE(SSL_CTX_set_quic_method(client_ctx_.get(), &quic_method));
5994 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), &quic_method));
5995 ASSERT_TRUE(CreateClientAndServer());
5996
5997 BufferedFlight client_flight, server_flight;
5998 buffered_flights.Set(client_.get(), &client_flight);
5999 buffered_flights.Set(server_.get(), &server_flight);
6000
David Benjamind6343572019-08-15 17:29:02 -04006001 ASSERT_TRUE(CompleteHandshakesForQUIC());
Steven Valdezc8e0f902018-07-14 11:23:01 -04006002
David Benjamind6343572019-08-15 17:29:02 -04006003 ExpectHandshakeSuccess();
Steven Valdezc8e0f902018-07-14 11:23:01 -04006004}
6005
6006// Test that excess data at one level is rejected. That is, if a single
6007// |SSL_provide_quic_data| call included both ServerHello and
6008// EncryptedExtensions in a single chunk, BoringSSL notices and rejects this on
6009// key change.
6010TEST_F(QUICMethodTest, ExcessProvidedData) {
David Benjamin5298ef92020-03-13 12:17:30 -04006011 AllowOutOfOrderWrites();
6012
David Benjamincc9d9352018-10-30 19:45:22 -05006013 auto add_handshake_data = [](SSL *ssl, enum ssl_encryption_level_t level,
6014 const uint8_t *data, size_t len) -> int {
Steven Valdezc8e0f902018-07-14 11:23:01 -04006015 // Switch everything to the initial level.
6016 return TransportFromSSL(ssl)->WriteHandshakeData(ssl_encryption_initial,
6017 MakeConstSpan(data, len));
6018 };
6019
David Benjamin1e859052020-02-09 16:04:58 -05006020 SSL_QUIC_METHOD quic_method = DefaultQUICMethod();
6021 quic_method.add_handshake_data = add_handshake_data;
Steven Valdezc8e0f902018-07-14 11:23:01 -04006022
6023 ASSERT_TRUE(SSL_CTX_set_quic_method(client_ctx_.get(), &quic_method));
6024 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), &quic_method));
6025 ASSERT_TRUE(CreateClientAndServer());
6026
6027 // Send the ClientHello and ServerHello through Finished.
6028 ASSERT_EQ(SSL_do_handshake(client_.get()), -1);
6029 ASSERT_EQ(SSL_get_error(client_.get(), -1), SSL_ERROR_WANT_READ);
6030 ASSERT_TRUE(ProvideHandshakeData(server_.get()));
6031 ASSERT_EQ(SSL_do_handshake(server_.get()), -1);
6032 ASSERT_EQ(SSL_get_error(server_.get(), -1), SSL_ERROR_WANT_READ);
6033
6034 // The client is still waiting for the ServerHello at initial
6035 // encryption.
6036 ASSERT_EQ(ssl_encryption_initial, SSL_quic_read_level(client_.get()));
6037
David Benjamincc9d9352018-10-30 19:45:22 -05006038 // |add_handshake_data| incorrectly wrote everything at the initial level, so
6039 // this queues up ServerHello through Finished in one chunk.
Steven Valdezc8e0f902018-07-14 11:23:01 -04006040 ASSERT_TRUE(ProvideHandshakeData(client_.get()));
6041
6042 // The client reads ServerHello successfully, but then rejects the buffered
6043 // EncryptedExtensions on key change.
6044 ASSERT_EQ(SSL_do_handshake(client_.get()), -1);
6045 ASSERT_EQ(SSL_get_error(client_.get(), -1), SSL_ERROR_SSL);
6046 uint32_t err = ERR_get_error();
6047 EXPECT_EQ(ERR_GET_LIB(err), ERR_LIB_SSL);
David Benjaminf9cc26f2020-02-09 16:49:31 -05006048 EXPECT_EQ(ERR_GET_REASON(err), SSL_R_EXCESS_HANDSHAKE_DATA);
Steven Valdezc8e0f902018-07-14 11:23:01 -04006049
David Benjamin1e859052020-02-09 16:04:58 -05006050 // The client sends an alert in response to this. The alert is sent at
6051 // handshake level because we install write secrets before read secrets and
6052 // the error is discovered when installing the read secret. (How to send
6053 // alerts on protocol syntax errors near key changes is ambiguous in general.)
David Benjamind6343572019-08-15 17:29:02 -04006054 ASSERT_TRUE(transport_->client()->has_alert());
David Benjamin1e859052020-02-09 16:04:58 -05006055 EXPECT_EQ(transport_->client()->alert_level(), ssl_encryption_handshake);
David Benjamind6343572019-08-15 17:29:02 -04006056 EXPECT_EQ(transport_->client()->alert(), SSL_AD_UNEXPECTED_MESSAGE);
Steven Valdezc8e0f902018-07-14 11:23:01 -04006057
David Benjamin5298ef92020-03-13 12:17:30 -04006058 // Sanity-check handshake secrets. The error is discovered while setting the
6059 // read secret, so only the write secret has been installed.
David Benjamin1e859052020-02-09 16:04:58 -05006060 EXPECT_TRUE(transport_->client()->HasWriteSecret(ssl_encryption_handshake));
David Benjamin5298ef92020-03-13 12:17:30 -04006061 EXPECT_FALSE(transport_->client()->HasReadSecret(ssl_encryption_handshake));
Steven Valdezc8e0f902018-07-14 11:23:01 -04006062}
6063
6064// Test that |SSL_provide_quic_data| will reject data at the wrong level.
6065TEST_F(QUICMethodTest, ProvideWrongLevel) {
David Benjamin1e859052020-02-09 16:04:58 -05006066 const SSL_QUIC_METHOD quic_method = DefaultQUICMethod();
Steven Valdezc8e0f902018-07-14 11:23:01 -04006067
6068 ASSERT_TRUE(SSL_CTX_set_quic_method(client_ctx_.get(), &quic_method));
6069 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), &quic_method));
6070 ASSERT_TRUE(CreateClientAndServer());
6071
6072 // Send the ClientHello and ServerHello through Finished.
6073 ASSERT_EQ(SSL_do_handshake(client_.get()), -1);
6074 ASSERT_EQ(SSL_get_error(client_.get(), -1), SSL_ERROR_WANT_READ);
6075 ASSERT_TRUE(ProvideHandshakeData(server_.get()));
6076 ASSERT_EQ(SSL_do_handshake(server_.get()), -1);
6077 ASSERT_EQ(SSL_get_error(server_.get(), -1), SSL_ERROR_WANT_READ);
6078
6079 // The client is still waiting for the ServerHello at initial
6080 // encryption.
6081 ASSERT_EQ(ssl_encryption_initial, SSL_quic_read_level(client_.get()));
6082
6083 // Data cannot be provided at the next level.
6084 std::vector<uint8_t> data;
6085 ASSERT_TRUE(
David Benjamind6343572019-08-15 17:29:02 -04006086 transport_->client()->ReadHandshakeData(&data, ssl_encryption_initial));
Steven Valdezc8e0f902018-07-14 11:23:01 -04006087 ASSERT_FALSE(SSL_provide_quic_data(client_.get(), ssl_encryption_handshake,
6088 data.data(), data.size()));
6089 ERR_clear_error();
6090
6091 // Progress to EncryptedExtensions.
6092 ASSERT_TRUE(SSL_provide_quic_data(client_.get(), ssl_encryption_initial,
6093 data.data(), data.size()));
6094 ASSERT_EQ(SSL_do_handshake(client_.get()), -1);
6095 ASSERT_EQ(SSL_get_error(client_.get(), -1), SSL_ERROR_WANT_READ);
6096 ASSERT_EQ(ssl_encryption_handshake, SSL_quic_read_level(client_.get()));
6097
6098 // Data cannot be provided at the previous level.
6099 ASSERT_TRUE(
David Benjamind6343572019-08-15 17:29:02 -04006100 transport_->client()->ReadHandshakeData(&data, ssl_encryption_handshake));
Steven Valdezc8e0f902018-07-14 11:23:01 -04006101 ASSERT_FALSE(SSL_provide_quic_data(client_.get(), ssl_encryption_initial,
6102 data.data(), data.size()));
6103}
6104
6105TEST_F(QUICMethodTest, TooMuchData) {
David Benjamin1e859052020-02-09 16:04:58 -05006106 const SSL_QUIC_METHOD quic_method = DefaultQUICMethod();
Steven Valdezc8e0f902018-07-14 11:23:01 -04006107
6108 ASSERT_TRUE(SSL_CTX_set_quic_method(client_ctx_.get(), &quic_method));
6109 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), &quic_method));
6110 ASSERT_TRUE(CreateClientAndServer());
6111
6112 size_t limit =
6113 SSL_quic_max_handshake_flight_len(client_.get(), ssl_encryption_initial);
6114 uint8_t b = 0;
6115 for (size_t i = 0; i < limit; i++) {
6116 ASSERT_TRUE(
6117 SSL_provide_quic_data(client_.get(), ssl_encryption_initial, &b, 1));
6118 }
6119
6120 EXPECT_FALSE(
6121 SSL_provide_quic_data(client_.get(), ssl_encryption_initial, &b, 1));
6122}
6123
Steven Valdeze6eef1c2018-11-09 13:32:34 -05006124// Provide invalid post-handshake data.
6125TEST_F(QUICMethodTest, BadPostHandshake) {
David Benjamin1e859052020-02-09 16:04:58 -05006126 const SSL_QUIC_METHOD quic_method = DefaultQUICMethod();
Steven Valdeze6eef1c2018-11-09 13:32:34 -05006127
6128 g_last_session = nullptr;
6129
6130 SSL_CTX_set_session_cache_mode(client_ctx_.get(), SSL_SESS_CACHE_BOTH);
6131 SSL_CTX_sess_set_new_cb(client_ctx_.get(), SaveLastSession);
6132 ASSERT_TRUE(SSL_CTX_set_quic_method(client_ctx_.get(), &quic_method));
6133 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), &quic_method));
6134 ASSERT_TRUE(CreateClientAndServer());
David Benjamind6343572019-08-15 17:29:02 -04006135 ASSERT_TRUE(CompleteHandshakesForQUIC());
Steven Valdeze6eef1c2018-11-09 13:32:34 -05006136
6137 EXPECT_EQ(SSL_do_handshake(client_.get()), 1);
6138 EXPECT_EQ(SSL_do_handshake(server_.get()), 1);
David Benjamind6343572019-08-15 17:29:02 -04006139 EXPECT_TRUE(transport_->SecretsMatch(ssl_encryption_application));
6140 EXPECT_FALSE(transport_->client()->has_alert());
6141 EXPECT_FALSE(transport_->server()->has_alert());
Steven Valdeze6eef1c2018-11-09 13:32:34 -05006142
6143 // Junk sent as part of post-handshake data should cause an error.
6144 uint8_t kJunk[] = {0x17, 0x0, 0x0, 0x4, 0xB, 0xE, 0xE, 0xF};
6145 ASSERT_TRUE(SSL_provide_quic_data(client_.get(), ssl_encryption_application,
6146 kJunk, sizeof(kJunk)));
6147 EXPECT_EQ(SSL_process_quic_post_handshake(client_.get()), 0);
6148}
6149
Nick Harper80ddfc72020-03-11 18:26:31 -07006150static void ExpectReceivedTransportParamsEqual(const SSL *ssl,
6151 Span<const uint8_t> expected) {
6152 const uint8_t *received;
6153 size_t received_len;
6154 SSL_get_peer_quic_transport_params(ssl, &received, &received_len);
6155 ASSERT_EQ(received_len, expected.size());
6156 EXPECT_EQ(Bytes(received, received_len), Bytes(expected));
6157}
6158
6159TEST_F(QUICMethodTest, SetTransportParameters) {
6160 const SSL_QUIC_METHOD quic_method = DefaultQUICMethod();
6161 ASSERT_TRUE(SSL_CTX_set_quic_method(client_ctx_.get(), &quic_method));
6162 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), &quic_method));
6163
6164 ASSERT_TRUE(CreateClientAndServer());
6165 uint8_t kClientParams[] = {1, 2, 3, 4};
6166 uint8_t kServerParams[] = {5, 6, 7};
6167 ASSERT_TRUE(SSL_set_quic_transport_params(client_.get(), kClientParams,
6168 sizeof(kClientParams)));
6169 ASSERT_TRUE(SSL_set_quic_transport_params(server_.get(), kServerParams,
6170 sizeof(kServerParams)));
6171
6172 ASSERT_TRUE(CompleteHandshakesForQUIC());
6173 ExpectReceivedTransportParamsEqual(client_.get(), kServerParams);
6174 ExpectReceivedTransportParamsEqual(server_.get(), kClientParams);
6175}
6176
6177TEST_F(QUICMethodTest, SetTransportParamsInCallback) {
6178 const SSL_QUIC_METHOD quic_method = DefaultQUICMethod();
6179 ASSERT_TRUE(SSL_CTX_set_quic_method(client_ctx_.get(), &quic_method));
6180 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), &quic_method));
6181
6182 ASSERT_TRUE(CreateClientAndServer());
6183 uint8_t kClientParams[] = {1, 2, 3, 4};
6184 static uint8_t kServerParams[] = {5, 6, 7};
6185 ASSERT_TRUE(SSL_set_quic_transport_params(client_.get(), kClientParams,
6186 sizeof(kClientParams)));
6187 SSL_CTX_set_tlsext_servername_callback(
6188 server_ctx_.get(), [](SSL *ssl, int *out_alert, void *arg) -> int {
6189 EXPECT_TRUE(SSL_set_quic_transport_params(ssl, kServerParams,
6190 sizeof(kServerParams)));
6191 return SSL_TLSEXT_ERR_OK;
6192 });
6193
6194 ASSERT_TRUE(CompleteHandshakesForQUIC());
6195 ExpectReceivedTransportParamsEqual(client_.get(), kServerParams);
6196 ExpectReceivedTransportParamsEqual(server_.get(), kClientParams);
6197}
6198
Nick Harper6bfd25c2020-03-30 17:15:19 -07006199TEST_F(QUICMethodTest, ForbidCrossProtocolResumptionClient) {
6200 const SSL_QUIC_METHOD quic_method = DefaultQUICMethod();
6201
6202 g_last_session = nullptr;
6203
6204 SSL_CTX_set_session_cache_mode(client_ctx_.get(), SSL_SESS_CACHE_BOTH);
6205 SSL_CTX_sess_set_new_cb(client_ctx_.get(), SaveLastSession);
6206 ASSERT_TRUE(SSL_CTX_set_quic_method(client_ctx_.get(), &quic_method));
6207 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), &quic_method));
6208
6209 ASSERT_TRUE(CreateClientAndServer());
6210 ASSERT_TRUE(CompleteHandshakesForQUIC());
6211
6212 ExpectHandshakeSuccess();
6213 EXPECT_FALSE(SSL_session_reused(client_.get()));
6214 EXPECT_FALSE(SSL_session_reused(server_.get()));
6215
6216 // The server sent NewSessionTicket messages in the handshake.
6217 EXPECT_FALSE(g_last_session);
6218 ASSERT_TRUE(ProvideHandshakeData(client_.get()));
6219 EXPECT_EQ(SSL_process_quic_post_handshake(client_.get()), 1);
6220 EXPECT_TRUE(g_last_session);
6221
6222 // Pretend that g_last_session came from a TLS-over-TCP connection.
6223 g_last_session.get()->is_quic = false;
6224
6225 // Create a second connection and verify that resumption does not occur with
6226 // a session from a non-QUIC connection. This tests that the client does not
6227 // offer over QUIC a session believed to be received over TCP. The server
6228 // believes this is a QUIC session, so if the client offered the session, the
6229 // server would have resumed it.
6230 ASSERT_TRUE(CreateClientAndServer());
6231 bssl::UniquePtr<SSL_SESSION> session = std::move(g_last_session);
6232 SSL_set_session(client_.get(), session.get());
6233
6234 ASSERT_TRUE(CompleteHandshakesForQUIC());
6235 ExpectHandshakeSuccess();
6236 EXPECT_FALSE(SSL_session_reused(client_.get()));
6237 EXPECT_FALSE(SSL_session_reused(server_.get()));
6238}
6239
6240TEST_F(QUICMethodTest, ForbidCrossProtocolResumptionServer) {
6241 const SSL_QUIC_METHOD quic_method = DefaultQUICMethod();
6242
6243 g_last_session = nullptr;
6244
6245 SSL_CTX_set_session_cache_mode(client_ctx_.get(), SSL_SESS_CACHE_BOTH);
6246 SSL_CTX_sess_set_new_cb(client_ctx_.get(), SaveLastSession);
6247 ASSERT_TRUE(SSL_CTX_set_quic_method(client_ctx_.get(), &quic_method));
6248 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), &quic_method));
6249
6250 ASSERT_TRUE(CreateClientAndServer());
6251 ASSERT_TRUE(CompleteHandshakesForQUIC());
6252
6253 ExpectHandshakeSuccess();
6254 EXPECT_FALSE(SSL_session_reused(client_.get()));
6255 EXPECT_FALSE(SSL_session_reused(server_.get()));
6256
6257 // The server sent NewSessionTicket messages in the handshake.
6258 EXPECT_FALSE(g_last_session);
6259 ASSERT_TRUE(ProvideHandshakeData(client_.get()));
6260 EXPECT_EQ(SSL_process_quic_post_handshake(client_.get()), 1);
6261 EXPECT_TRUE(g_last_session);
6262
6263 // Attempt a resumption with g_last_session using TLS_method.
6264 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLS_method()));
6265 ASSERT_TRUE(client_ctx);
6266
6267 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), nullptr));
6268
6269 bssl::UniquePtr<SSL> client(SSL_new(client_ctx.get())),
6270 server(SSL_new(server_ctx_.get()));
6271 ASSERT_TRUE(client);
6272 ASSERT_TRUE(server);
6273 SSL_set_connect_state(client.get());
6274 SSL_set_accept_state(server.get());
6275
6276 // The TLS-over-TCP client will refuse to resume with a quic session, so
6277 // mark is_quic = false to bypass the client check to test the server check.
6278 g_last_session.get()->is_quic = false;
6279 SSL_set_session(client.get(), g_last_session.get());
6280
6281 BIO *bio1, *bio2;
6282 ASSERT_TRUE(BIO_new_bio_pair(&bio1, 0, &bio2, 0));
6283
6284 // SSL_set_bio takes ownership.
6285 SSL_set_bio(client.get(), bio1, bio1);
6286 SSL_set_bio(server.get(), bio2, bio2);
6287 ASSERT_TRUE(CompleteHandshakes(client.get(), server.get()));
6288
6289 EXPECT_FALSE(SSL_session_reused(client.get()));
6290 EXPECT_FALSE(SSL_session_reused(server.get()));
6291}
6292
Nick Harper72cff812020-03-26 18:06:16 -07006293TEST_F(QUICMethodTest, ClientRejectsMissingTransportParams) {
6294 const SSL_QUIC_METHOD quic_method = DefaultQUICMethod();
6295 ASSERT_TRUE(SSL_CTX_set_quic_method(client_ctx_.get(), &quic_method));
6296 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), &quic_method));
6297
6298 ASSERT_TRUE(CreateClientAndServer());
6299 ASSERT_TRUE(SSL_set_quic_transport_params(server_.get(), nullptr, 0));
6300 ASSERT_TRUE(RunQUICHandshakesAndExpectError(ExpectedError::kServerError));
6301}
6302
6303TEST_F(QUICMethodTest, ServerRejectsMissingTransportParams) {
6304 const SSL_QUIC_METHOD quic_method = DefaultQUICMethod();
6305 ASSERT_TRUE(SSL_CTX_set_quic_method(client_ctx_.get(), &quic_method));
6306 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), &quic_method));
6307
6308 ASSERT_TRUE(CreateClientAndServer());
6309 ASSERT_TRUE(SSL_set_quic_transport_params(client_.get(), nullptr, 0));
6310 ASSERT_TRUE(RunQUICHandshakesAndExpectError(ExpectedError::kClientError));
6311}
6312
David Schinazi3d8b8c32021-01-14 11:25:49 -08006313TEST_F(QUICMethodTest, QuicLegacyCodepointEnabled) {
6314 const SSL_QUIC_METHOD quic_method = DefaultQUICMethod();
6315 ASSERT_TRUE(SSL_CTX_set_quic_method(client_ctx_.get(), &quic_method));
6316 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), &quic_method));
6317
6318 ASSERT_TRUE(CreateClientAndServer());
6319 uint8_t kClientParams[] = {1, 2, 3, 4};
6320 uint8_t kServerParams[] = {5, 6, 7};
6321 SSL_set_quic_use_legacy_codepoint(client_.get(), 1);
6322 SSL_set_quic_use_legacy_codepoint(server_.get(), 1);
6323 ASSERT_TRUE(SSL_set_quic_transport_params(client_.get(), kClientParams,
6324 sizeof(kClientParams)));
6325 ASSERT_TRUE(SSL_set_quic_transport_params(server_.get(), kServerParams,
6326 sizeof(kServerParams)));
6327
6328 ASSERT_TRUE(CompleteHandshakesForQUIC());
6329 ExpectReceivedTransportParamsEqual(client_.get(), kServerParams);
6330 ExpectReceivedTransportParamsEqual(server_.get(), kClientParams);
6331}
6332
6333TEST_F(QUICMethodTest, QuicLegacyCodepointDisabled) {
6334 const SSL_QUIC_METHOD quic_method = DefaultQUICMethod();
6335 ASSERT_TRUE(SSL_CTX_set_quic_method(client_ctx_.get(), &quic_method));
6336 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), &quic_method));
6337
6338 ASSERT_TRUE(CreateClientAndServer());
6339 uint8_t kClientParams[] = {1, 2, 3, 4};
6340 uint8_t kServerParams[] = {5, 6, 7};
6341 SSL_set_quic_use_legacy_codepoint(client_.get(), 0);
6342 SSL_set_quic_use_legacy_codepoint(server_.get(), 0);
6343 ASSERT_TRUE(SSL_set_quic_transport_params(client_.get(), kClientParams,
6344 sizeof(kClientParams)));
6345 ASSERT_TRUE(SSL_set_quic_transport_params(server_.get(), kServerParams,
6346 sizeof(kServerParams)));
6347
6348 ASSERT_TRUE(CompleteHandshakesForQUIC());
6349 ExpectReceivedTransportParamsEqual(client_.get(), kServerParams);
6350 ExpectReceivedTransportParamsEqual(server_.get(), kClientParams);
6351}
6352
6353TEST_F(QUICMethodTest, QuicLegacyCodepointClientOnly) {
6354 const SSL_QUIC_METHOD quic_method = DefaultQUICMethod();
6355 ASSERT_TRUE(SSL_CTX_set_quic_method(client_ctx_.get(), &quic_method));
6356 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), &quic_method));
6357
6358 ASSERT_TRUE(CreateClientAndServer());
6359 uint8_t kClientParams[] = {1, 2, 3, 4};
6360 uint8_t kServerParams[] = {5, 6, 7};
6361 SSL_set_quic_use_legacy_codepoint(client_.get(), 1);
6362 SSL_set_quic_use_legacy_codepoint(server_.get(), 0);
6363 ASSERT_TRUE(SSL_set_quic_transport_params(client_.get(), kClientParams,
6364 sizeof(kClientParams)));
6365 ASSERT_TRUE(SSL_set_quic_transport_params(server_.get(), kServerParams,
6366 sizeof(kServerParams)));
6367
6368 ASSERT_TRUE(RunQUICHandshakesAndExpectError(ExpectedError::kServerError));
6369}
6370
6371TEST_F(QUICMethodTest, QuicLegacyCodepointServerOnly) {
6372 const SSL_QUIC_METHOD quic_method = DefaultQUICMethod();
6373 ASSERT_TRUE(SSL_CTX_set_quic_method(client_ctx_.get(), &quic_method));
6374 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), &quic_method));
6375
6376 ASSERT_TRUE(CreateClientAndServer());
6377 uint8_t kClientParams[] = {1, 2, 3, 4};
6378 uint8_t kServerParams[] = {5, 6, 7};
6379 SSL_set_quic_use_legacy_codepoint(client_.get(), 0);
6380 SSL_set_quic_use_legacy_codepoint(server_.get(), 1);
6381 ASSERT_TRUE(SSL_set_quic_transport_params(client_.get(), kClientParams,
6382 sizeof(kClientParams)));
6383 ASSERT_TRUE(SSL_set_quic_transport_params(server_.get(), kServerParams,
6384 sizeof(kServerParams)));
6385
6386 ASSERT_TRUE(RunQUICHandshakesAndExpectError(ExpectedError::kServerError));
6387}
6388
David Benjaminc47bfce2021-01-20 17:10:32 -05006389// Test that the default QUIC code point is consistent with
6390// |TLSEXT_TYPE_quic_transport_parameters|. This test ensures we remember to
6391// update the two values together.
6392TEST_F(QUICMethodTest, QuicCodePointDefault) {
6393 const SSL_QUIC_METHOD quic_method = DefaultQUICMethod();
6394 ASSERT_TRUE(SSL_CTX_set_quic_method(client_ctx_.get(), &quic_method));
6395 ASSERT_TRUE(SSL_CTX_set_quic_method(server_ctx_.get(), &quic_method));
6396 SSL_CTX_set_select_certificate_cb(
6397 server_ctx_.get(),
6398 [](const SSL_CLIENT_HELLO *client_hello) -> ssl_select_cert_result_t {
6399 const uint8_t *data;
6400 size_t len;
6401 if (!SSL_early_callback_ctx_extension_get(
6402 client_hello, TLSEXT_TYPE_quic_transport_parameters, &data,
6403 &len)) {
6404 ADD_FAILURE() << "Could not find quic_transport_parameters extension";
6405 return ssl_select_cert_error;
6406 }
6407 return ssl_select_cert_success;
6408 });
6409
6410 ASSERT_TRUE(CreateClientAndServer());
6411 ASSERT_TRUE(CompleteHandshakesForQUIC());
6412}
6413
Adam Langley7540cc22019-04-18 09:56:13 -07006414extern "C" {
6415int BORINGSSL_enum_c_type_test(void);
6416}
6417
6418TEST(SSLTest, EnumTypes) {
6419 EXPECT_EQ(sizeof(int), sizeof(ssl_private_key_result_t));
6420 EXPECT_EQ(1, BORINGSSL_enum_c_type_test());
6421}
6422
David Benjaminb29e1e12019-05-06 14:44:46 -05006423TEST_P(SSLVersionTest, DoubleSSLError) {
6424 // Connect the inner SSL connections.
6425 ASSERT_TRUE(Connect());
6426
6427 // Make a pair of |BIO|s which wrap |client_| and |server_|.
6428 UniquePtr<BIO_METHOD> bio_method(BIO_meth_new(0, nullptr));
6429 ASSERT_TRUE(bio_method);
6430 ASSERT_TRUE(BIO_meth_set_read(
6431 bio_method.get(), [](BIO *bio, char *out, int len) -> int {
6432 SSL *ssl = static_cast<SSL *>(BIO_get_data(bio));
6433 int ret = SSL_read(ssl, out, len);
6434 int ssl_ret = SSL_get_error(ssl, ret);
6435 if (ssl_ret == SSL_ERROR_WANT_READ) {
6436 BIO_set_retry_read(bio);
6437 }
6438 return ret;
6439 }));
6440 ASSERT_TRUE(BIO_meth_set_write(
6441 bio_method.get(), [](BIO *bio, const char *in, int len) -> int {
6442 SSL *ssl = static_cast<SSL *>(BIO_get_data(bio));
6443 int ret = SSL_write(ssl, in, len);
6444 int ssl_ret = SSL_get_error(ssl, ret);
6445 if (ssl_ret == SSL_ERROR_WANT_WRITE) {
6446 BIO_set_retry_write(bio);
6447 }
6448 return ret;
6449 }));
6450 ASSERT_TRUE(BIO_meth_set_ctrl(
6451 bio_method.get(), [](BIO *bio, int cmd, long larg, void *parg) -> long {
6452 // |SSL| objects require |BIO_flush| support.
6453 if (cmd == BIO_CTRL_FLUSH) {
6454 return 1;
6455 }
6456 return 0;
6457 }));
6458
6459 UniquePtr<BIO> client_bio(BIO_new(bio_method.get()));
6460 ASSERT_TRUE(client_bio);
6461 BIO_set_data(client_bio.get(), client_.get());
6462 BIO_set_init(client_bio.get(), 1);
6463
6464 UniquePtr<BIO> server_bio(BIO_new(bio_method.get()));
6465 ASSERT_TRUE(server_bio);
6466 BIO_set_data(server_bio.get(), server_.get());
6467 BIO_set_init(server_bio.get(), 1);
6468
6469 // Wrap the inner connections in another layer of SSL.
6470 UniquePtr<SSL> client_outer(SSL_new(client_ctx_.get()));
6471 ASSERT_TRUE(client_outer);
6472 SSL_set_connect_state(client_outer.get());
6473 SSL_set_bio(client_outer.get(), client_bio.get(), client_bio.get());
6474 client_bio.release(); // |SSL_set_bio| takes ownership.
6475
6476 UniquePtr<SSL> server_outer(SSL_new(server_ctx_.get()));
6477 ASSERT_TRUE(server_outer);
6478 SSL_set_accept_state(server_outer.get());
6479 SSL_set_bio(server_outer.get(), server_bio.get(), server_bio.get());
6480 server_bio.release(); // |SSL_set_bio| takes ownership.
6481
6482 // Configure |client_outer| to reject the server certificate.
6483 SSL_set_custom_verify(
6484 client_outer.get(), SSL_VERIFY_PEER,
6485 [](SSL *ssl, uint8_t *out_alert) -> ssl_verify_result_t {
6486 return ssl_verify_invalid;
6487 });
6488
6489 for (;;) {
6490 int client_ret = SSL_do_handshake(client_outer.get());
6491 int client_err = SSL_get_error(client_outer.get(), client_ret);
6492 if (client_err != SSL_ERROR_WANT_READ &&
6493 client_err != SSL_ERROR_WANT_WRITE) {
6494 // The client handshake should terminate on a certificate verification
6495 // error.
6496 EXPECT_EQ(SSL_ERROR_SSL, client_err);
6497 uint32_t err = ERR_peek_error();
6498 EXPECT_EQ(ERR_LIB_SSL, ERR_GET_LIB(err));
6499 EXPECT_EQ(SSL_R_CERTIFICATE_VERIFY_FAILED, ERR_GET_REASON(err));
6500 break;
6501 }
6502
6503 // Run the server handshake and continue.
6504 int server_ret = SSL_do_handshake(server_outer.get());
6505 int server_err = SSL_get_error(server_outer.get(), server_ret);
6506 ASSERT_TRUE(server_err == SSL_ERROR_NONE ||
6507 server_err == SSL_ERROR_WANT_READ ||
6508 server_err == SSL_ERROR_WANT_WRITE);
6509 }
6510}
6511
David Benjamin1b819472020-06-09 14:01:02 -04006512TEST_P(SSLVersionTest, SameKeyResume) {
6513 uint8_t key[48];
6514 RAND_bytes(key, sizeof(key));
6515
6516 bssl::UniquePtr<SSL_CTX> server_ctx2 = CreateContext();
6517 ASSERT_TRUE(server_ctx2);
6518 ASSERT_TRUE(UseCertAndKey(server_ctx2.get()));
6519 ASSERT_TRUE(
6520 SSL_CTX_set_tlsext_ticket_keys(server_ctx_.get(), key, sizeof(key)));
6521 ASSERT_TRUE(
6522 SSL_CTX_set_tlsext_ticket_keys(server_ctx2.get(), key, sizeof(key)));
6523
6524 SSL_CTX_set_session_cache_mode(client_ctx_.get(), SSL_SESS_CACHE_BOTH);
6525 SSL_CTX_set_session_cache_mode(server_ctx_.get(), SSL_SESS_CACHE_BOTH);
6526 SSL_CTX_set_session_cache_mode(server_ctx2.get(), SSL_SESS_CACHE_BOTH);
6527
6528 // Establish a session for |server_ctx_|.
6529 bssl::UniquePtr<SSL_SESSION> session =
6530 CreateClientSession(client_ctx_.get(), server_ctx_.get());
6531 ASSERT_TRUE(session);
6532 ClientConfig config;
6533 config.session = session.get();
6534
6535 // Resuming with |server_ctx_| again works.
6536 bssl::UniquePtr<SSL> client, server;
6537 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx_.get(),
6538 server_ctx_.get(), config));
6539 EXPECT_TRUE(SSL_session_reused(client.get()));
6540 EXPECT_TRUE(SSL_session_reused(server.get()));
6541
6542 // Resuming with |server_ctx2| also works.
6543 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx_.get(),
6544 server_ctx2.get(), config));
6545 EXPECT_TRUE(SSL_session_reused(client.get()));
6546 EXPECT_TRUE(SSL_session_reused(server.get()));
6547}
6548
6549TEST_P(SSLVersionTest, DifferentKeyNoResume) {
6550 uint8_t key1[48], key2[48];
6551 RAND_bytes(key1, sizeof(key1));
6552 RAND_bytes(key2, sizeof(key2));
6553
6554 bssl::UniquePtr<SSL_CTX> server_ctx2 = CreateContext();
6555 ASSERT_TRUE(server_ctx2);
6556 ASSERT_TRUE(UseCertAndKey(server_ctx2.get()));
6557 ASSERT_TRUE(
6558 SSL_CTX_set_tlsext_ticket_keys(server_ctx_.get(), key1, sizeof(key1)));
6559 ASSERT_TRUE(
6560 SSL_CTX_set_tlsext_ticket_keys(server_ctx2.get(), key2, sizeof(key2)));
6561
6562 SSL_CTX_set_session_cache_mode(client_ctx_.get(), SSL_SESS_CACHE_BOTH);
6563 SSL_CTX_set_session_cache_mode(server_ctx_.get(), SSL_SESS_CACHE_BOTH);
6564 SSL_CTX_set_session_cache_mode(server_ctx2.get(), SSL_SESS_CACHE_BOTH);
6565
6566 // Establish a session for |server_ctx_|.
6567 bssl::UniquePtr<SSL_SESSION> session =
6568 CreateClientSession(client_ctx_.get(), server_ctx_.get());
6569 ASSERT_TRUE(session);
6570 ClientConfig config;
6571 config.session = session.get();
6572
6573 // Resuming with |server_ctx_| again works.
6574 bssl::UniquePtr<SSL> client, server;
6575 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx_.get(),
6576 server_ctx_.get(), config));
6577 EXPECT_TRUE(SSL_session_reused(client.get()));
6578 EXPECT_TRUE(SSL_session_reused(server.get()));
6579
6580 // Resuming with |server_ctx2| does not work.
6581 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx_.get(),
6582 server_ctx2.get(), config));
6583 EXPECT_FALSE(SSL_session_reused(client.get()));
6584 EXPECT_FALSE(SSL_session_reused(server.get()));
6585}
6586
6587TEST_P(SSLVersionTest, UnrelatedServerNoResume) {
6588 bssl::UniquePtr<SSL_CTX> server_ctx2 = CreateContext();
6589 ASSERT_TRUE(server_ctx2);
6590 ASSERT_TRUE(UseCertAndKey(server_ctx2.get()));
6591
6592 SSL_CTX_set_session_cache_mode(client_ctx_.get(), SSL_SESS_CACHE_BOTH);
6593 SSL_CTX_set_session_cache_mode(server_ctx_.get(), SSL_SESS_CACHE_BOTH);
6594 SSL_CTX_set_session_cache_mode(server_ctx2.get(), SSL_SESS_CACHE_BOTH);
6595
6596 // Establish a session for |server_ctx_|.
6597 bssl::UniquePtr<SSL_SESSION> session =
6598 CreateClientSession(client_ctx_.get(), server_ctx_.get());
6599 ASSERT_TRUE(session);
6600 ClientConfig config;
6601 config.session = session.get();
6602
6603 // Resuming with |server_ctx_| again works.
6604 bssl::UniquePtr<SSL> client, server;
6605 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx_.get(),
6606 server_ctx_.get(), config));
6607 EXPECT_TRUE(SSL_session_reused(client.get()));
6608 EXPECT_TRUE(SSL_session_reused(server.get()));
6609
6610 // Resuming with |server_ctx2| does not work.
6611 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx_.get(),
6612 server_ctx2.get(), config));
6613 EXPECT_FALSE(SSL_session_reused(client.get()));
6614 EXPECT_FALSE(SSL_session_reused(server.get()));
6615}
6616
David Benjamin0e7dbd52019-05-15 16:01:18 -04006617TEST(SSLTest, WriteWhileExplicitRenegotiate) {
6618 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
6619 ASSERT_TRUE(ctx);
6620
6621 bssl::UniquePtr<X509> cert = GetTestCertificate();
6622 bssl::UniquePtr<EVP_PKEY> pkey = GetTestKey();
6623 ASSERT_TRUE(cert);
6624 ASSERT_TRUE(pkey);
6625 ASSERT_TRUE(SSL_CTX_use_certificate(ctx.get(), cert.get()));
6626 ASSERT_TRUE(SSL_CTX_use_PrivateKey(ctx.get(), pkey.get()));
6627 ASSERT_TRUE(SSL_CTX_set_min_proto_version(ctx.get(), TLS1_2_VERSION));
6628 ASSERT_TRUE(SSL_CTX_set_max_proto_version(ctx.get(), TLS1_2_VERSION));
6629 ASSERT_TRUE(SSL_CTX_set_strict_cipher_list(
6630 ctx.get(), "TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256"));
6631
6632 bssl::UniquePtr<SSL> client, server;
6633 ASSERT_TRUE(ConnectClientAndServer(&client, &server, ctx.get(), ctx.get(),
6634 ClientConfig(), true /* do_handshake */,
6635 false /* don't shed handshake config */));
6636 SSL_set_renegotiate_mode(client.get(), ssl_renegotiate_explicit);
6637
6638 static const uint8_t kInput[] = {'h', 'e', 'l', 'l', 'o'};
6639
6640 // Write "hello" until the buffer is full, so |client| has a pending write.
6641 size_t num_writes = 0;
6642 for (;;) {
6643 int ret = SSL_write(client.get(), kInput, sizeof(kInput));
6644 if (ret != int(sizeof(kInput))) {
6645 ASSERT_EQ(-1, ret);
6646 ASSERT_EQ(SSL_ERROR_WANT_WRITE, SSL_get_error(client.get(), ret));
6647 break;
6648 }
6649 num_writes++;
6650 }
6651
6652 // Encrypt a HelloRequest.
6653 uint8_t in[] = {SSL3_MT_HELLO_REQUEST, 0, 0, 0};
6654#if defined(BORINGSSL_UNSAFE_FUZZER_MODE)
6655 // Fuzzer-mode records are unencrypted.
6656 uint8_t record[5 + sizeof(in)];
6657 record[0] = SSL3_RT_HANDSHAKE;
6658 record[1] = 3;
6659 record[2] = 3; // TLS 1.2
6660 record[3] = 0;
6661 record[4] = sizeof(record) - 5;
6662 memcpy(record + 5, in, sizeof(in));
6663#else
6664 // Extract key material from |server|.
6665 static const size_t kKeyLen = 32;
6666 static const size_t kNonceLen = 12;
6667 ASSERT_EQ(2u * (kKeyLen + kNonceLen), SSL_get_key_block_len(server.get()));
6668 uint8_t key_block[2u * (kKeyLen + kNonceLen)];
6669 ASSERT_TRUE(
6670 SSL_generate_key_block(server.get(), key_block, sizeof(key_block)));
6671 Span<uint8_t> key = MakeSpan(key_block + kKeyLen, kKeyLen);
6672 Span<uint8_t> nonce =
6673 MakeSpan(key_block + kKeyLen + kKeyLen + kNonceLen, kNonceLen);
6674
6675 uint8_t ad[13];
6676 uint64_t seq = SSL_get_write_sequence(server.get());
6677 for (size_t i = 0; i < 8; i++) {
6678 // The nonce is XORed with the sequence number.
6679 nonce[11 - i] ^= uint8_t(seq);
6680 ad[7 - i] = uint8_t(seq);
6681 seq >>= 8;
6682 }
6683
6684 ad[8] = SSL3_RT_HANDSHAKE;
6685 ad[9] = 3;
6686 ad[10] = 3; // TLS 1.2
6687 ad[11] = 0;
6688 ad[12] = sizeof(in);
6689
6690 uint8_t record[5 + sizeof(in) + 16];
6691 record[0] = SSL3_RT_HANDSHAKE;
6692 record[1] = 3;
6693 record[2] = 3; // TLS 1.2
6694 record[3] = 0;
6695 record[4] = sizeof(record) - 5;
6696
6697 ScopedEVP_AEAD_CTX aead;
6698 ASSERT_TRUE(EVP_AEAD_CTX_init(aead.get(), EVP_aead_chacha20_poly1305(),
6699 key.data(), key.size(),
6700 EVP_AEAD_DEFAULT_TAG_LENGTH, nullptr));
6701 size_t len;
6702 ASSERT_TRUE(EVP_AEAD_CTX_seal(aead.get(), record + 5, &len,
6703 sizeof(record) - 5, nonce.data(), nonce.size(),
6704 in, sizeof(in), ad, sizeof(ad)));
6705 ASSERT_EQ(sizeof(record) - 5, len);
6706#endif // BORINGSSL_UNSAFE_FUZZER_MODE
6707
6708 ASSERT_EQ(int(sizeof(record)),
6709 BIO_write(SSL_get_wbio(server.get()), record, sizeof(record)));
6710
6711 // |SSL_read| should pick up the HelloRequest.
6712 uint8_t byte;
6713 ASSERT_EQ(-1, SSL_read(client.get(), &byte, 1));
6714 ASSERT_EQ(SSL_ERROR_WANT_RENEGOTIATE, SSL_get_error(client.get(), -1));
6715
6716 // Drain the data from the |client|.
6717 uint8_t buf[sizeof(kInput)];
6718 for (size_t i = 0; i < num_writes; i++) {
6719 ASSERT_EQ(int(sizeof(buf)), SSL_read(server.get(), buf, sizeof(buf)));
6720 EXPECT_EQ(Bytes(buf), Bytes(kInput));
6721 }
6722
6723 // |client| should be able to finish the pending write and continue to write,
6724 // despite the paused HelloRequest.
6725 ASSERT_EQ(int(sizeof(kInput)),
6726 SSL_write(client.get(), kInput, sizeof(kInput)));
6727 ASSERT_EQ(int(sizeof(buf)), SSL_read(server.get(), buf, sizeof(buf)));
6728 EXPECT_EQ(Bytes(buf), Bytes(kInput));
6729
6730 ASSERT_EQ(int(sizeof(kInput)),
6731 SSL_write(client.get(), kInput, sizeof(kInput)));
6732 ASSERT_EQ(int(sizeof(buf)), SSL_read(server.get(), buf, sizeof(buf)));
6733 EXPECT_EQ(Bytes(buf), Bytes(kInput));
6734
6735 // |SSL_read| is stuck until we acknowledge the HelloRequest.
6736 ASSERT_EQ(-1, SSL_read(client.get(), &byte, 1));
6737 ASSERT_EQ(SSL_ERROR_WANT_RENEGOTIATE, SSL_get_error(client.get(), -1));
6738
6739 ASSERT_TRUE(SSL_renegotiate(client.get()));
6740 ASSERT_EQ(-1, SSL_read(client.get(), &byte, 1));
6741 ASSERT_EQ(SSL_ERROR_WANT_READ, SSL_get_error(client.get(), -1));
6742
6743 // We never renegotiate as a server.
6744 ASSERT_EQ(-1, SSL_read(server.get(), buf, sizeof(buf)));
6745 ASSERT_EQ(SSL_ERROR_SSL, SSL_get_error(server.get(), -1));
6746 uint32_t err = ERR_get_error();
6747 EXPECT_EQ(ERR_LIB_SSL, ERR_GET_LIB(err));
6748 EXPECT_EQ(SSL_R_NO_RENEGOTIATION, ERR_GET_REASON(err));
6749}
6750
David Benjaminf9e0cda2020-03-23 18:29:09 -04006751
6752TEST(SSLTest, CopyWithoutEarlyData) {
6753 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLS_method()));
6754 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(TLS_method()));
6755 ASSERT_TRUE(client_ctx);
6756 ASSERT_TRUE(server_ctx);
6757
6758 bssl::UniquePtr<X509> cert = GetTestCertificate();
6759 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
6760 ASSERT_TRUE(cert);
6761 ASSERT_TRUE(key);
6762 ASSERT_TRUE(SSL_CTX_use_certificate(server_ctx.get(), cert.get()));
6763 ASSERT_TRUE(SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()));
6764
6765 SSL_CTX_set_session_cache_mode(client_ctx.get(), SSL_SESS_CACHE_BOTH);
6766 SSL_CTX_set_session_cache_mode(server_ctx.get(), SSL_SESS_CACHE_BOTH);
6767 SSL_CTX_set_early_data_enabled(client_ctx.get(), 1);
6768 SSL_CTX_set_early_data_enabled(server_ctx.get(), 1);
6769
6770 bssl::UniquePtr<SSL_SESSION> session =
6771 CreateClientSession(client_ctx.get(), server_ctx.get());
6772 ASSERT_TRUE(session);
6773
6774 // The client should attempt early data with |session|.
6775 auto config = ClientConfig();
6776 config.early_data = true;
6777 config.session = session.get();
6778 bssl::UniquePtr<SSL> client, server;
6779 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx.get(),
6780 server_ctx.get(), config,
6781 /*do_handshake=*/false));
6782 ASSERT_EQ(1, SSL_do_handshake(client.get()));
6783 EXPECT_TRUE(SSL_in_early_data(client.get()));
6784
6785 // |SSL_SESSION_copy_without_early_data| should disable early data but
6786 // still resume the session.
6787 bssl::UniquePtr<SSL_SESSION> session2(
6788 SSL_SESSION_copy_without_early_data(session.get()));
6789 ASSERT_TRUE(session2);
6790 EXPECT_NE(session.get(), session2.get());
6791 config.session = session2.get();
6792 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx.get(),
6793 server_ctx.get(), config));
6794 EXPECT_TRUE(SSL_session_reused(client.get()));
6795 EXPECT_EQ(ssl_early_data_unsupported_for_session,
6796 SSL_get_early_data_reason(client.get()));
6797
6798 // |SSL_SESSION_copy_without_early_data| should be a reference count increase
6799 // when passed an early-data-incapable session.
6800 bssl::UniquePtr<SSL_SESSION> session3(
6801 SSL_SESSION_copy_without_early_data(session2.get()));
6802 EXPECT_EQ(session2.get(), session3.get());
6803}
6804
Adam Langley53a17f52020-05-26 14:44:07 -07006805TEST(SSLTest, ProcessTLS13NewSessionTicket) {
6806 // Configure client and server to negotiate TLS 1.3 only.
6807 bssl::UniquePtr<X509> cert = GetTestCertificate();
6808 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
6809 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLS_method()));
6810 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(TLS_method()));
6811 ASSERT_TRUE(client_ctx);
6812 ASSERT_TRUE(server_ctx);
6813 ASSERT_TRUE(SSL_CTX_set_min_proto_version(client_ctx.get(), TLS1_3_VERSION));
6814 ASSERT_TRUE(SSL_CTX_set_min_proto_version(server_ctx.get(), TLS1_3_VERSION));
6815 ASSERT_TRUE(SSL_CTX_set_max_proto_version(client_ctx.get(), TLS1_3_VERSION));
6816 ASSERT_TRUE(SSL_CTX_set_max_proto_version(server_ctx.get(), TLS1_3_VERSION));
6817 ASSERT_TRUE(SSL_CTX_use_certificate(server_ctx.get(), cert.get()));
6818 ASSERT_TRUE(SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()));
6819
6820 bssl::UniquePtr<SSL> client, server;
6821 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx.get(),
6822 server_ctx.get()));
6823 EXPECT_EQ(TLS1_3_VERSION, SSL_version(client.get()));
6824
6825 // Process a TLS 1.3 NewSessionTicket.
6826 static const uint8_t kTicket[] = {
6827 0x04, 0x00, 0x00, 0xb2, 0x00, 0x02, 0xa3, 0x00, 0x04, 0x03, 0x02, 0x01,
6828 0x01, 0x00, 0x00, 0xa0, 0x01, 0x06, 0x09, 0x11, 0x16, 0x19, 0x21, 0x26,
6829 0x29, 0x31, 0x36, 0x39, 0x41, 0x46, 0x49, 0x51, 0x03, 0x06, 0x09, 0x13,
6830 0x16, 0x19, 0x23, 0x26, 0x29, 0x33, 0x36, 0x39, 0x43, 0x46, 0x49, 0x53,
6831 0xf7, 0x00, 0x29, 0xec, 0xf2, 0xc4, 0xa4, 0x41, 0xfc, 0x30, 0x17, 0x2e,
6832 0x9f, 0x7c, 0xa8, 0xaf, 0x75, 0x70, 0xf0, 0x1f, 0xc7, 0x98, 0xf7, 0xcf,
6833 0x5a, 0x5a, 0x6b, 0x5b, 0xfe, 0xf1, 0xe7, 0x3a, 0xe8, 0xf7, 0x6c, 0xd2,
6834 0xa8, 0xa6, 0x92, 0x5b, 0x96, 0x8d, 0xde, 0xdb, 0xd3, 0x20, 0x6a, 0xcb,
6835 0x69, 0x06, 0xf4, 0x91, 0x85, 0x2e, 0xe6, 0x5e, 0x0c, 0x59, 0xf2, 0x9e,
6836 0x9b, 0x79, 0x91, 0x24, 0x7e, 0x4a, 0x32, 0x3d, 0xbe, 0x4b, 0x80, 0x70,
6837 0xaf, 0xd0, 0x1d, 0xe2, 0xca, 0x05, 0x35, 0x09, 0x09, 0x05, 0x0f, 0xbb,
6838 0xc4, 0xae, 0xd7, 0xc4, 0xed, 0xd7, 0xae, 0x35, 0xc8, 0x73, 0x63, 0x78,
6839 0x64, 0xc9, 0x7a, 0x1f, 0xed, 0x7a, 0x9a, 0x47, 0x44, 0xfd, 0x50, 0xf7,
6840 0xb7, 0xe0, 0x64, 0xa9, 0x02, 0xc1, 0x5c, 0x23, 0x18, 0x3f, 0xc4, 0xcf,
6841 0x72, 0x02, 0x59, 0x2d, 0xe1, 0xaa, 0x61, 0x72, 0x00, 0x04, 0x5a, 0x5a,
6842 0x00, 0x00,
6843 };
6844 bssl::UniquePtr<SSL_SESSION> session(SSL_process_tls13_new_session_ticket(
6845 client.get(), kTicket, sizeof(kTicket)));
6846 ASSERT_TRUE(session);
6847 ASSERT_TRUE(SSL_SESSION_has_ticket(session.get()));
6848
6849 uint8_t *session_buf = nullptr;
6850 size_t session_length = 0;
6851 ASSERT_TRUE(
6852 SSL_SESSION_to_bytes(session.get(), &session_buf, &session_length));
6853 bssl::UniquePtr<uint8_t> session_buf_free(session_buf);
6854 ASSERT_TRUE(session_buf);
6855 ASSERT_GT(session_length, 0u);
6856
6857 // Servers cannot call |SSL_process_tls13_new_session_ticket|.
6858 ASSERT_FALSE(SSL_process_tls13_new_session_ticket(server.get(), kTicket,
6859 sizeof(kTicket)));
6860
6861 // Clients cannot call |SSL_process_tls13_new_session_ticket| before the
6862 // handshake completes.
6863 bssl::UniquePtr<SSL> client2(SSL_new(client_ctx.get()));
6864 ASSERT_TRUE(client2);
6865 SSL_set_connect_state(client2.get());
6866 ASSERT_FALSE(SSL_process_tls13_new_session_ticket(client2.get(), kTicket,
6867 sizeof(kTicket)));
6868}
6869
David Benjamin3989c992020-10-09 14:12:06 -04006870TEST(SSLTest, BIO) {
6871 bssl::UniquePtr<SSL_CTX> client_ctx(SSL_CTX_new(TLS_method()));
6872 bssl::UniquePtr<SSL_CTX> server_ctx(SSL_CTX_new(TLS_method()));
6873 ASSERT_TRUE(client_ctx);
6874 ASSERT_TRUE(server_ctx);
6875
6876 bssl::UniquePtr<X509> cert = GetTestCertificate();
6877 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
6878 ASSERT_TRUE(cert);
6879 ASSERT_TRUE(key);
6880 ASSERT_TRUE(SSL_CTX_use_certificate(server_ctx.get(), cert.get()));
6881 ASSERT_TRUE(SSL_CTX_use_PrivateKey(server_ctx.get(), key.get()));
6882
6883 for (bool take_ownership : {true, false}) {
6884 // For simplicity, get the handshake out of the way first.
6885 bssl::UniquePtr<SSL> client, server;
6886 ASSERT_TRUE(ConnectClientAndServer(&client, &server, client_ctx.get(),
6887 server_ctx.get()));
6888
6889 // Wrap |client| in an SSL BIO.
6890 bssl::UniquePtr<BIO> client_bio(BIO_new(BIO_f_ssl()));
6891 ASSERT_TRUE(client_bio);
6892 ASSERT_EQ(1, BIO_set_ssl(client_bio.get(), client.get(), take_ownership));
6893 if (take_ownership) {
6894 client.release();
6895 }
6896
6897 // Flushing the BIO should not crash.
6898 EXPECT_EQ(1, BIO_flush(client_bio.get()));
6899
6900 // Exchange some data.
6901 EXPECT_EQ(5, BIO_write(client_bio.get(), "hello", 5));
6902 uint8_t buf[5];
6903 ASSERT_EQ(5, SSL_read(server.get(), buf, sizeof(buf)));
6904 EXPECT_EQ(Bytes("hello"), Bytes(buf));
6905
6906 EXPECT_EQ(5, SSL_write(server.get(), "world", 5));
6907 ASSERT_EQ(5, BIO_read(client_bio.get(), buf, sizeof(buf)));
6908 EXPECT_EQ(Bytes("world"), Bytes(buf));
6909
6910 // |BIO_should_read| should work.
6911 EXPECT_EQ(-1, BIO_read(client_bio.get(), buf, sizeof(buf)));
6912 EXPECT_TRUE(BIO_should_read(client_bio.get()));
6913
6914 // Writing data should eventually exceed the buffer size and fail, reporting
6915 // |BIO_should_write|.
6916 int ret;
6917 for (int i = 0; i < 1024; i++) {
6918 std::vector<uint8_t> buffer(1024);
6919 ret = BIO_write(client_bio.get(), buffer.data(), buffer.size());
6920 if (ret <= 0) {
6921 break;
6922 }
6923 }
6924 EXPECT_EQ(-1, ret);
6925 EXPECT_TRUE(BIO_should_write(client_bio.get()));
6926 }
6927}
6928
David Benjamin12a3e7e2021-04-13 11:47:36 -04006929TEST(SSLTest, ALPNConfig) {
6930 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
6931 ASSERT_TRUE(ctx);
6932 bssl::UniquePtr<X509> cert = GetTestCertificate();
6933 bssl::UniquePtr<EVP_PKEY> key = GetTestKey();
6934 ASSERT_TRUE(cert);
6935 ASSERT_TRUE(key);
6936 ASSERT_TRUE(SSL_CTX_use_certificate(ctx.get(), cert.get()));
6937 ASSERT_TRUE(SSL_CTX_use_PrivateKey(ctx.get(), key.get()));
6938
6939 // Set up some machinery to check the configured ALPN against what is actually
6940 // sent over the wire. Note that the ALPN callback is only called when the
6941 // client offers ALPN.
6942 std::vector<uint8_t> observed_alpn;
6943 SSL_CTX_set_alpn_select_cb(
6944 ctx.get(),
6945 [](SSL *ssl, const uint8_t **out, uint8_t *out_len, const uint8_t *in,
6946 unsigned in_len, void *arg) -> int {
6947 std::vector<uint8_t> *observed_alpn_ptr =
6948 static_cast<std::vector<uint8_t> *>(arg);
6949 observed_alpn_ptr->assign(in, in + in_len);
6950 return SSL_TLSEXT_ERR_NOACK;
6951 },
6952 &observed_alpn);
6953 auto check_alpn_proto = [&](Span<const uint8_t> expected) {
6954 observed_alpn.clear();
6955 bssl::UniquePtr<SSL> client, server;
6956 EXPECT_TRUE(ConnectClientAndServer(&client, &server, ctx.get(), ctx.get()));
6957 EXPECT_EQ(Bytes(expected), Bytes(observed_alpn));
6958 };
6959
6960 // Note that |SSL_CTX_set_alpn_protos|'s return value is reversed.
6961 static const uint8_t kValidList[] = {0x03, 'f', 'o', 'o',
6962 0x03, 'b', 'a', 'r'};
6963 EXPECT_EQ(0,
6964 SSL_CTX_set_alpn_protos(ctx.get(), kValidList, sizeof(kValidList)));
6965 check_alpn_proto(kValidList);
6966
6967 // Invalid lists are rejected.
6968 static const uint8_t kInvalidList[] = {0x04, 'f', 'o', 'o'};
6969 EXPECT_EQ(1, SSL_CTX_set_alpn_protos(ctx.get(), kInvalidList,
6970 sizeof(kInvalidList)));
6971
6972 // Empty lists are valid and are interpreted as disabling ALPN.
6973 EXPECT_EQ(0, SSL_CTX_set_alpn_protos(ctx.get(), nullptr, 0));
6974 check_alpn_proto({});
6975}
6976
David Benjamin2f3958a2021-04-16 11:55:23 -04006977// Test that the key usage checker can correctly handle issuerUID and
6978// subjectUID. See https://crbug.com/1199744.
6979TEST(SSLTest, KeyUsageWithUIDs) {
6980 static const char kGoodKeyUsage[] = R"(
6981-----BEGIN CERTIFICATE-----
6982MIIB7DCCAZOgAwIBAgIJANlMBNpJfb/rMAoGCCqGSM49BAMCMEUxCzAJBgNVBAYT
6983AkFVMRMwEQYDVQQIDApTb21lLVN0YXRlMSEwHwYDVQQKDBhJbnRlcm5ldCBXaWRn
6984aXRzIFB0eSBMdGQwHhcNMTQwNDIzMjMyMTU3WhcNMTQwNTIzMjMyMTU3WjBFMQsw
6985CQYDVQQGEwJBVTETMBEGA1UECAwKU29tZS1TdGF0ZTEhMB8GA1UECgwYSW50ZXJu
6986ZXQgV2lkZ2l0cyBQdHkgTHRkMFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAE5itp
69874r9ln5e+Lx4NlIpM1Zdrt6keDUb73ampHp3culoB59aXqAoY+cPEox5W4nyDSNsW
6988Ghz1HX7xlC1Lz3IiwYEEABI0VoIEABI0VqNgMF4wHQYDVR0OBBYEFKuE0qyrlfCC
6989ThZ4B1VXX+QmjYLRMB8GA1UdIwQYMBaAFKuE0qyrlfCCThZ4B1VXX+QmjYLRMA4G
6990A1UdDwEB/wQEAwIHgDAMBgNVHRMEBTADAQH/MAoGCCqGSM49BAMCA0cAMEQCIEWJ
699134EcqW5MHwLIA1hZ2Tj/jV2QjN02KLxis9mFsqDKAiAMlMTkzsM51vVs9Ohqa+Rc
69924Z7qDhjIhiF4dM0uEDYRVA==
6993-----END CERTIFICATE-----
6994)";
6995 static const char kBadKeyUsage[] = R"(
6996-----BEGIN CERTIFICATE-----
6997MIIB7jCCAZOgAwIBAgIJANlMBNpJfb/rMAoGCCqGSM49BAMCMEUxCzAJBgNVBAYT
6998AkFVMRMwEQYDVQQIDApTb21lLVN0YXRlMSEwHwYDVQQKDBhJbnRlcm5ldCBXaWRn
6999aXRzIFB0eSBMdGQwHhcNMTQwNDIzMjMyMTU3WhcNMTQwNTIzMjMyMTU3WjBFMQsw
7000CQYDVQQGEwJBVTETMBEGA1UECAwKU29tZS1TdGF0ZTEhMB8GA1UECgwYSW50ZXJu
7001ZXQgV2lkZ2l0cyBQdHkgTHRkMFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAE5itp
70024r9ln5e+Lx4NlIpM1Zdrt6keDUb73ampHp3culoB59aXqAoY+cPEox5W4nyDSNsW
7003Ghz1HX7xlC1Lz3IiwYEEABI0VoIEABI0VqNgMF4wHQYDVR0OBBYEFKuE0qyrlfCC
7004ThZ4B1VXX+QmjYLRMB8GA1UdIwQYMBaAFKuE0qyrlfCCThZ4B1VXX+QmjYLRMA4G
7005A1UdDwEB/wQEAwIDCDAMBgNVHRMEBTADAQH/MAoGCCqGSM49BAMCA0kAMEYCIQC6
7006taYBUDu2gcZC6EMk79FBHArYI0ucF+kzvETegZCbBAIhANtObFec5gtso/47moPD
7007RHrQbWsFUakETXL9QMlegh5t
7008-----END CERTIFICATE-----
7009)";
7010
7011 bssl::UniquePtr<X509> good = CertFromPEM(kGoodKeyUsage);
7012 ASSERT_TRUE(good);
7013 bssl::UniquePtr<X509> bad = CertFromPEM(kBadKeyUsage);
7014 ASSERT_TRUE(bad);
7015
7016 // We check key usage when configuring EC certificates to distinguish ECDSA
7017 // and ECDH.
7018 bssl::UniquePtr<SSL_CTX> ctx(SSL_CTX_new(TLS_method()));
7019 ASSERT_TRUE(ctx);
7020 EXPECT_TRUE(SSL_CTX_use_certificate(ctx.get(), good.get()));
7021 EXPECT_FALSE(SSL_CTX_use_certificate(ctx.get(), bad.get()));
7022}
7023
Martin Kreichgauer72912d22017-08-04 12:06:43 -07007024} // namespace
Joshua Liebow-Feeser8c7c6352018-08-26 18:53:36 -07007025BSSL_NAMESPACE_END