diff options
author | tb <> | 2020-12-01 07:46:02 +0000 |
---|---|---|
committer | tb <> | 2020-12-01 07:46:02 +0000 |
commit | 7e83d137a386213a28873ba8555b80f3902047ea (patch) | |
tree | b8860cebc16a52f900f9938beabf8efa53dbe3c1 /src/lib | |
parent | e184d9b4d57f92ba4003625ca5e4bf386ad6843f (diff) | |
download | openbsd-7e83d137a386213a28873ba8555b80f3902047ea.tar.gz openbsd-7e83d137a386213a28873ba8555b80f3902047ea.tar.bz2 openbsd-7e83d137a386213a28873ba8555b80f3902047ea.zip |
Bring back *_client_method() structs
The method unification broke an API promise of SSL_is_server(). According
to the documentation, calling SSL_is_server() on SSL objects constructed
from generic and server methods would result in 1 even before any call to
SSL_set_accept_state(). This means the information needs to be available
when SSL_new() is called, so must come from the method itself.
Prior to the method unification, s->server would be set to 0 or 1 in
SSL_new() depending on whether the accept method was undefined or not.
Instead, introduce a flag to the internal structs to distinguish client
methods from server and generic methods and copy that flag to s->server in
SSL_new().
This problem was reported to otto due to breakage of DoH in net/dnsdist.
The reason for this is that www/h2o relies on SSL_is_server() to decide
whether to call SSL_accept() or SSL_connect(). Thus, the h2o server would
end up responding to a ClientHello with another ClientHello, which results
in a handshake failure. The bandaid applied to www/h2o can be removed once
this fix has made it into snaps. No other breakage is known.
This commit brings back only about half of the duplication removed in the
method unification, so is preferable to a full revert.
ok jsing
Diffstat (limited to 'src/lib')
-rw-r--r-- | src/lib/libssl/ssl_lib.c | 4 | ||||
-rw-r--r-- | src/lib/libssl/ssl_locl.h | 3 | ||||
-rw-r--r-- | src/lib/libssl/ssl_methods.c | 204 |
3 files changed, 200 insertions, 11 deletions
diff --git a/src/lib/libssl/ssl_lib.c b/src/lib/libssl/ssl_lib.c index 58b9dae910..69628b48df 100644 --- a/src/lib/libssl/ssl_lib.c +++ b/src/lib/libssl/ssl_lib.c | |||
@@ -1,4 +1,4 @@ | |||
1 | /* $OpenBSD: ssl_lib.c,v 1.238 2020/11/16 18:55:15 jsing Exp $ */ | 1 | /* $OpenBSD: ssl_lib.c,v 1.239 2020/12/01 07:46:01 tb Exp $ */ |
2 | /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) | 2 | /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) |
3 | * All rights reserved. | 3 | * All rights reserved. |
4 | * | 4 | * |
@@ -345,7 +345,7 @@ SSL_new(SSL_CTX *ctx) | |||
345 | goto err; | 345 | goto err; |
346 | 346 | ||
347 | s->references = 1; | 347 | s->references = 1; |
348 | s->server = 0; | 348 | s->server = ctx->method->internal->server; |
349 | 349 | ||
350 | SSL_clear(s); | 350 | SSL_clear(s); |
351 | 351 | ||
diff --git a/src/lib/libssl/ssl_locl.h b/src/lib/libssl/ssl_locl.h index 46a1ad4884..19d883e3b0 100644 --- a/src/lib/libssl/ssl_locl.h +++ b/src/lib/libssl/ssl_locl.h | |||
@@ -1,4 +1,4 @@ | |||
1 | /* $OpenBSD: ssl_locl.h,v 1.307 2020/11/11 18:14:12 jsing Exp $ */ | 1 | /* $OpenBSD: ssl_locl.h,v 1.308 2020/12/01 07:46:02 tb Exp $ */ |
2 | /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) | 2 | /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) |
3 | * All rights reserved. | 3 | * All rights reserved. |
4 | * | 4 | * |
@@ -359,6 +359,7 @@ __BEGIN_HIDDEN_DECLS | |||
359 | 359 | ||
360 | typedef struct ssl_method_internal_st { | 360 | typedef struct ssl_method_internal_st { |
361 | int dtls; | 361 | int dtls; |
362 | int server; | ||
362 | int version; | 363 | int version; |
363 | 364 | ||
364 | uint16_t min_version; | 365 | uint16_t min_version; |
diff --git a/src/lib/libssl/ssl_methods.c b/src/lib/libssl/ssl_methods.c index 600aa89095..ea67403d5d 100644 --- a/src/lib/libssl/ssl_methods.c +++ b/src/lib/libssl/ssl_methods.c | |||
@@ -1,4 +1,4 @@ | |||
1 | /* $OpenBSD: ssl_methods.c,v 1.20 2020/10/14 16:44:15 jsing Exp $ */ | 1 | /* $OpenBSD: ssl_methods.c,v 1.21 2020/12/01 07:46:02 tb Exp $ */ |
2 | /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) | 2 | /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) |
3 | * All rights reserved. | 3 | * All rights reserved. |
4 | * | 4 | * |
@@ -61,6 +61,7 @@ | |||
61 | 61 | ||
62 | static const SSL_METHOD_INTERNAL DTLSv1_method_internal_data = { | 62 | static const SSL_METHOD_INTERNAL DTLSv1_method_internal_data = { |
63 | .dtls = 1, | 63 | .dtls = 1, |
64 | .server = 1, | ||
64 | .version = DTLS1_VERSION, | 65 | .version = DTLS1_VERSION, |
65 | .min_version = DTLS1_VERSION, | 66 | .min_version = DTLS1_VERSION, |
66 | .max_version = DTLS1_VERSION, | 67 | .max_version = DTLS1_VERSION, |
@@ -87,10 +88,39 @@ static const SSL_METHOD DTLSv1_method_data = { | |||
87 | .internal = &DTLSv1_method_internal_data, | 88 | .internal = &DTLSv1_method_internal_data, |
88 | }; | 89 | }; |
89 | 90 | ||
91 | static const SSL_METHOD_INTERNAL DTLSv1_client_method_internal_data = { | ||
92 | .dtls = 1, | ||
93 | .server = 0, | ||
94 | .version = DTLS1_VERSION, | ||
95 | .min_version = DTLS1_VERSION, | ||
96 | .max_version = DTLS1_VERSION, | ||
97 | .ssl_new = dtls1_new, | ||
98 | .ssl_clear = dtls1_clear, | ||
99 | .ssl_free = dtls1_free, | ||
100 | .ssl_accept = ssl_undefined_function, | ||
101 | .ssl_connect = ssl3_connect, | ||
102 | .ssl_shutdown = ssl3_shutdown, | ||
103 | .ssl_renegotiate = ssl3_renegotiate, | ||
104 | .ssl_renegotiate_check = ssl3_renegotiate_check, | ||
105 | .ssl_pending = ssl3_pending, | ||
106 | .ssl_read_bytes = dtls1_read_bytes, | ||
107 | .ssl_write_bytes = dtls1_write_app_data_bytes, | ||
108 | .enc_flags = TLSV1_1_ENC_FLAGS, | ||
109 | }; | ||
110 | |||
111 | static const SSL_METHOD DTLSv1_client_method_data = { | ||
112 | .ssl_dispatch_alert = dtls1_dispatch_alert, | ||
113 | .num_ciphers = ssl3_num_ciphers, | ||
114 | .get_cipher = dtls1_get_cipher, | ||
115 | .get_cipher_by_char = ssl3_get_cipher_by_char, | ||
116 | .put_cipher_by_char = ssl3_put_cipher_by_char, | ||
117 | .internal = &DTLSv1_client_method_internal_data, | ||
118 | }; | ||
119 | |||
90 | const SSL_METHOD * | 120 | const SSL_METHOD * |
91 | DTLSv1_client_method(void) | 121 | DTLSv1_client_method(void) |
92 | { | 122 | { |
93 | return &DTLSv1_method_data; | 123 | return &DTLSv1_client_method_data; |
94 | } | 124 | } |
95 | 125 | ||
96 | const SSL_METHOD * | 126 | const SSL_METHOD * |
@@ -108,7 +138,7 @@ DTLSv1_server_method(void) | |||
108 | const SSL_METHOD * | 138 | const SSL_METHOD * |
109 | DTLS_client_method(void) | 139 | DTLS_client_method(void) |
110 | { | 140 | { |
111 | return DTLSv1_method(); | 141 | return DTLSv1_client_method(); |
112 | } | 142 | } |
113 | 143 | ||
114 | const SSL_METHOD * | 144 | const SSL_METHOD * |
@@ -126,6 +156,7 @@ DTLS_server_method(void) | |||
126 | #if defined(LIBRESSL_HAS_TLS1_3_CLIENT) && defined(LIBRESSL_HAS_TLS1_3_SERVER) | 156 | #if defined(LIBRESSL_HAS_TLS1_3_CLIENT) && defined(LIBRESSL_HAS_TLS1_3_SERVER) |
127 | static const SSL_METHOD_INTERNAL TLS_method_internal_data = { | 157 | static const SSL_METHOD_INTERNAL TLS_method_internal_data = { |
128 | .dtls = 0, | 158 | .dtls = 0, |
159 | .server = 1, | ||
129 | .version = TLS1_3_VERSION, | 160 | .version = TLS1_3_VERSION, |
130 | .min_version = TLS1_VERSION, | 161 | .min_version = TLS1_VERSION, |
131 | .max_version = TLS1_3_VERSION, | 162 | .max_version = TLS1_3_VERSION, |
@@ -155,6 +186,7 @@ static const SSL_METHOD TLS_method_data = { | |||
155 | 186 | ||
156 | static const SSL_METHOD_INTERNAL TLS_legacy_method_internal_data = { | 187 | static const SSL_METHOD_INTERNAL TLS_legacy_method_internal_data = { |
157 | .dtls = 0, | 188 | .dtls = 0, |
189 | .server = 1, | ||
158 | .version = TLS1_2_VERSION, | 190 | .version = TLS1_2_VERSION, |
159 | .min_version = TLS1_VERSION, | 191 | .min_version = TLS1_VERSION, |
160 | .max_version = TLS1_2_VERSION, | 192 | .max_version = TLS1_2_VERSION, |
@@ -181,8 +213,71 @@ static const SSL_METHOD TLS_legacy_method_data = { | |||
181 | .internal = &TLS_legacy_method_internal_data, | 213 | .internal = &TLS_legacy_method_internal_data, |
182 | }; | 214 | }; |
183 | 215 | ||
216 | #if defined(LIBRESSL_HAS_TLS1_3_CLIENT) | ||
217 | static const SSL_METHOD_INTERNAL TLS_client_method_internal_data = { | ||
218 | .dtls = 0, | ||
219 | .server = 0, | ||
220 | .version = TLS1_3_VERSION, | ||
221 | .min_version = TLS1_VERSION, | ||
222 | .max_version = TLS1_3_VERSION, | ||
223 | .ssl_new = tls1_new, | ||
224 | .ssl_clear = tls1_clear, | ||
225 | .ssl_free = tls1_free, | ||
226 | .ssl_accept = tls13_legacy_accept, | ||
227 | .ssl_connect = tls13_legacy_connect, | ||
228 | .ssl_shutdown = tls13_legacy_shutdown, | ||
229 | .ssl_renegotiate = ssl_undefined_function, | ||
230 | .ssl_renegotiate_check = ssl_ok, | ||
231 | .ssl_pending = tls13_legacy_pending, | ||
232 | .ssl_read_bytes = tls13_legacy_read_bytes, | ||
233 | .ssl_write_bytes = tls13_legacy_write_bytes, | ||
234 | .enc_flags = TLSV1_3_ENC_FLAGS, | ||
235 | }; | ||
236 | |||
237 | static const SSL_METHOD TLS_client_method_data = { | ||
238 | .ssl_dispatch_alert = ssl3_dispatch_alert, | ||
239 | .num_ciphers = ssl3_num_ciphers, | ||
240 | .get_cipher = ssl3_get_cipher, | ||
241 | .get_cipher_by_char = ssl3_get_cipher_by_char, | ||
242 | .put_cipher_by_char = ssl3_put_cipher_by_char, | ||
243 | .internal = &TLS_client_method_internal_data, | ||
244 | }; | ||
245 | |||
246 | #else | ||
247 | |||
248 | static const SSL_METHOD_INTERNAL TLS_legacy_client_method_internal_data = { | ||
249 | .dtls = 0, | ||
250 | .server = 0, | ||
251 | .version = TLS1_2_VERSION, | ||
252 | .min_version = TLS1_VERSION, | ||
253 | .max_version = TLS1_2_VERSION, | ||
254 | .ssl_new = tls1_new, | ||
255 | .ssl_clear = tls1_clear, | ||
256 | .ssl_free = tls1_free, | ||
257 | .ssl_accept = ssl3_accept, | ||
258 | .ssl_connect = ssl3_connect, | ||
259 | .ssl_shutdown = ssl3_shutdown, | ||
260 | .ssl_renegotiate = ssl_undefined_function, | ||
261 | .ssl_renegotiate_check = ssl_ok, | ||
262 | .ssl_pending = ssl3_pending, | ||
263 | .ssl_read_bytes = ssl3_read_bytes, | ||
264 | .ssl_write_bytes = ssl3_write_bytes, | ||
265 | .enc_flags = TLSV1_2_ENC_FLAGS, | ||
266 | }; | ||
267 | |||
268 | static const SSL_METHOD TLS_legacy_client_method_data = { | ||
269 | .ssl_dispatch_alert = ssl3_dispatch_alert, | ||
270 | .num_ciphers = ssl3_num_ciphers, | ||
271 | .get_cipher = ssl3_get_cipher, | ||
272 | .get_cipher_by_char = ssl3_get_cipher_by_char, | ||
273 | .put_cipher_by_char = ssl3_put_cipher_by_char, | ||
274 | .internal = &TLS_legacy_client_method_internal_data, | ||
275 | }; | ||
276 | #endif | ||
277 | |||
184 | static const SSL_METHOD_INTERNAL TLSv1_method_internal_data = { | 278 | static const SSL_METHOD_INTERNAL TLSv1_method_internal_data = { |
185 | .dtls = 0, | 279 | .dtls = 0, |
280 | .server = 1, | ||
186 | .version = TLS1_VERSION, | 281 | .version = TLS1_VERSION, |
187 | .min_version = TLS1_VERSION, | 282 | .min_version = TLS1_VERSION, |
188 | .max_version = TLS1_VERSION, | 283 | .max_version = TLS1_VERSION, |
@@ -209,8 +304,38 @@ static const SSL_METHOD TLSv1_method_data = { | |||
209 | .internal = &TLSv1_method_internal_data, | 304 | .internal = &TLSv1_method_internal_data, |
210 | }; | 305 | }; |
211 | 306 | ||
307 | static const SSL_METHOD_INTERNAL TLSv1_client_method_internal_data = { | ||
308 | .dtls = 0, | ||
309 | .server = 0, | ||
310 | .version = TLS1_VERSION, | ||
311 | .min_version = TLS1_VERSION, | ||
312 | .max_version = TLS1_VERSION, | ||
313 | .ssl_new = tls1_new, | ||
314 | .ssl_clear = tls1_clear, | ||
315 | .ssl_free = tls1_free, | ||
316 | .ssl_accept = ssl_undefined_function, | ||
317 | .ssl_connect = ssl3_connect, | ||
318 | .ssl_shutdown = ssl3_shutdown, | ||
319 | .ssl_renegotiate = ssl3_renegotiate, | ||
320 | .ssl_renegotiate_check = ssl3_renegotiate_check, | ||
321 | .ssl_pending = ssl3_pending, | ||
322 | .ssl_read_bytes = ssl3_read_bytes, | ||
323 | .ssl_write_bytes = ssl3_write_bytes, | ||
324 | .enc_flags = TLSV1_ENC_FLAGS, | ||
325 | }; | ||
326 | |||
327 | static const SSL_METHOD TLSv1_client_method_data = { | ||
328 | .ssl_dispatch_alert = ssl3_dispatch_alert, | ||
329 | .num_ciphers = ssl3_num_ciphers, | ||
330 | .get_cipher = ssl3_get_cipher, | ||
331 | .get_cipher_by_char = ssl3_get_cipher_by_char, | ||
332 | .put_cipher_by_char = ssl3_put_cipher_by_char, | ||
333 | .internal = &TLSv1_client_method_internal_data, | ||
334 | }; | ||
335 | |||
212 | static const SSL_METHOD_INTERNAL TLSv1_1_method_internal_data = { | 336 | static const SSL_METHOD_INTERNAL TLSv1_1_method_internal_data = { |
213 | .dtls = 0, | 337 | .dtls = 0, |
338 | .server = 1, | ||
214 | .version = TLS1_1_VERSION, | 339 | .version = TLS1_1_VERSION, |
215 | .min_version = TLS1_1_VERSION, | 340 | .min_version = TLS1_1_VERSION, |
216 | .max_version = TLS1_1_VERSION, | 341 | .max_version = TLS1_1_VERSION, |
@@ -237,8 +362,38 @@ static const SSL_METHOD TLSv1_1_method_data = { | |||
237 | .internal = &TLSv1_1_method_internal_data, | 362 | .internal = &TLSv1_1_method_internal_data, |
238 | }; | 363 | }; |
239 | 364 | ||
365 | static const SSL_METHOD_INTERNAL TLSv1_1_client_method_internal_data = { | ||
366 | .dtls = 0, | ||
367 | .server = 0, | ||
368 | .version = TLS1_1_VERSION, | ||
369 | .min_version = TLS1_1_VERSION, | ||
370 | .max_version = TLS1_1_VERSION, | ||
371 | .ssl_new = tls1_new, | ||
372 | .ssl_clear = tls1_clear, | ||
373 | .ssl_free = tls1_free, | ||
374 | .ssl_accept = ssl_undefined_function, | ||
375 | .ssl_connect = ssl3_connect, | ||
376 | .ssl_shutdown = ssl3_shutdown, | ||
377 | .ssl_renegotiate = ssl3_renegotiate, | ||
378 | .ssl_renegotiate_check = ssl3_renegotiate_check, | ||
379 | .ssl_pending = ssl3_pending, | ||
380 | .ssl_read_bytes = ssl3_read_bytes, | ||
381 | .ssl_write_bytes = ssl3_write_bytes, | ||
382 | .enc_flags = TLSV1_1_ENC_FLAGS, | ||
383 | }; | ||
384 | |||
385 | static const SSL_METHOD TLSv1_1_client_method_data = { | ||
386 | .ssl_dispatch_alert = ssl3_dispatch_alert, | ||
387 | .num_ciphers = ssl3_num_ciphers, | ||
388 | .get_cipher = ssl3_get_cipher, | ||
389 | .get_cipher_by_char = ssl3_get_cipher_by_char, | ||
390 | .put_cipher_by_char = ssl3_put_cipher_by_char, | ||
391 | .internal = &TLSv1_1_client_method_internal_data, | ||
392 | }; | ||
393 | |||
240 | static const SSL_METHOD_INTERNAL TLSv1_2_method_internal_data = { | 394 | static const SSL_METHOD_INTERNAL TLSv1_2_method_internal_data = { |
241 | .dtls = 0, | 395 | .dtls = 0, |
396 | .server = 1, | ||
242 | .version = TLS1_2_VERSION, | 397 | .version = TLS1_2_VERSION, |
243 | .min_version = TLS1_2_VERSION, | 398 | .min_version = TLS1_2_VERSION, |
244 | .max_version = TLS1_2_VERSION, | 399 | .max_version = TLS1_2_VERSION, |
@@ -265,10 +420,43 @@ static const SSL_METHOD TLSv1_2_method_data = { | |||
265 | .internal = &TLSv1_2_method_internal_data, | 420 | .internal = &TLSv1_2_method_internal_data, |
266 | }; | 421 | }; |
267 | 422 | ||
423 | static const SSL_METHOD_INTERNAL TLSv1_2_client_method_internal_data = { | ||
424 | .dtls = 0, | ||
425 | .server = 0, | ||
426 | .version = TLS1_2_VERSION, | ||
427 | .min_version = TLS1_2_VERSION, | ||
428 | .max_version = TLS1_2_VERSION, | ||
429 | .ssl_new = tls1_new, | ||
430 | .ssl_clear = tls1_clear, | ||
431 | .ssl_free = tls1_free, | ||
432 | .ssl_accept = ssl_undefined_function, | ||
433 | .ssl_connect = ssl3_connect, | ||
434 | .ssl_shutdown = ssl3_shutdown, | ||
435 | .ssl_renegotiate = ssl3_renegotiate, | ||
436 | .ssl_renegotiate_check = ssl3_renegotiate_check, | ||
437 | .ssl_pending = ssl3_pending, | ||
438 | .ssl_read_bytes = ssl3_read_bytes, | ||
439 | .ssl_write_bytes = ssl3_write_bytes, | ||
440 | .enc_flags = TLSV1_2_ENC_FLAGS, | ||
441 | }; | ||
442 | |||
443 | static const SSL_METHOD TLSv1_2_client_method_data = { | ||
444 | .ssl_dispatch_alert = ssl3_dispatch_alert, | ||
445 | .num_ciphers = ssl3_num_ciphers, | ||
446 | .get_cipher = ssl3_get_cipher, | ||
447 | .get_cipher_by_char = ssl3_get_cipher_by_char, | ||
448 | .put_cipher_by_char = ssl3_put_cipher_by_char, | ||
449 | .internal = &TLSv1_2_client_method_internal_data, | ||
450 | }; | ||
451 | |||
268 | const SSL_METHOD * | 452 | const SSL_METHOD * |
269 | TLS_client_method(void) | 453 | TLS_client_method(void) |
270 | { | 454 | { |
271 | return TLS_method(); | 455 | #if defined(LIBRESSL_HAS_TLS1_3_CLIENT) |
456 | return (&TLS_client_method_data); | ||
457 | #else | ||
458 | return (&TLS_legacy_client_method_data); | ||
459 | #endif | ||
272 | } | 460 | } |
273 | 461 | ||
274 | const SSL_METHOD * | 462 | const SSL_METHOD * |
@@ -296,7 +484,7 @@ tls_legacy_method(void) | |||
296 | const SSL_METHOD * | 484 | const SSL_METHOD * |
297 | SSLv23_client_method(void) | 485 | SSLv23_client_method(void) |
298 | { | 486 | { |
299 | return TLS_method(); | 487 | return TLS_client_method(); |
300 | } | 488 | } |
301 | 489 | ||
302 | const SSL_METHOD * | 490 | const SSL_METHOD * |
@@ -314,7 +502,7 @@ SSLv23_server_method(void) | |||
314 | const SSL_METHOD * | 502 | const SSL_METHOD * |
315 | TLSv1_client_method(void) | 503 | TLSv1_client_method(void) |
316 | { | 504 | { |
317 | return (&TLSv1_method_data); | 505 | return (&TLSv1_client_method_data); |
318 | } | 506 | } |
319 | 507 | ||
320 | const SSL_METHOD * | 508 | const SSL_METHOD * |
@@ -332,7 +520,7 @@ TLSv1_server_method(void) | |||
332 | const SSL_METHOD * | 520 | const SSL_METHOD * |
333 | TLSv1_1_client_method(void) | 521 | TLSv1_1_client_method(void) |
334 | { | 522 | { |
335 | return (&TLSv1_1_method_data); | 523 | return (&TLSv1_1_client_method_data); |
336 | } | 524 | } |
337 | 525 | ||
338 | const SSL_METHOD * | 526 | const SSL_METHOD * |
@@ -350,7 +538,7 @@ TLSv1_1_server_method(void) | |||
350 | const SSL_METHOD * | 538 | const SSL_METHOD * |
351 | TLSv1_2_client_method(void) | 539 | TLSv1_2_client_method(void) |
352 | { | 540 | { |
353 | return (&TLSv1_2_method_data); | 541 | return (&TLSv1_2_client_method_data); |
354 | } | 542 | } |
355 | 543 | ||
356 | const SSL_METHOD * | 544 | const SSL_METHOD * |