1*521ba2f2Sbeck /* $OpenBSD: ssl_versions.c,v 1.27 2023/07/02 17:21:32 beck Exp $ */
22b939dc4Sjsing /*
32b939dc4Sjsing * Copyright (c) 2016, 2017 Joel Sing <jsing@openbsd.org>
42b939dc4Sjsing *
52b939dc4Sjsing * Permission to use, copy, modify, and distribute this software for any
62b939dc4Sjsing * purpose with or without fee is hereby granted, provided that the above
72b939dc4Sjsing * copyright notice and this permission notice appear in all copies.
82b939dc4Sjsing *
92b939dc4Sjsing * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
102b939dc4Sjsing * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
112b939dc4Sjsing * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
122b939dc4Sjsing * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
132b939dc4Sjsing * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
142b939dc4Sjsing * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
152b939dc4Sjsing * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
162b939dc4Sjsing */
172b939dc4Sjsing
18c9675a23Stb #include "ssl_local.h"
192b939dc4Sjsing
20ad17e628Sjsing static uint16_t
ssl_dtls_to_tls_version(uint16_t dtls_ver)21ad17e628Sjsing ssl_dtls_to_tls_version(uint16_t dtls_ver)
22ad17e628Sjsing {
23ad17e628Sjsing if (dtls_ver == DTLS1_VERSION)
24ad17e628Sjsing return TLS1_1_VERSION;
25ad17e628Sjsing if (dtls_ver == DTLS1_2_VERSION)
26ad17e628Sjsing return TLS1_2_VERSION;
27ad17e628Sjsing return 0;
28ad17e628Sjsing }
29ad17e628Sjsing
30ad17e628Sjsing static uint16_t
ssl_tls_to_dtls_version(uint16_t tls_ver)31ad17e628Sjsing ssl_tls_to_dtls_version(uint16_t tls_ver)
32ad17e628Sjsing {
33ad17e628Sjsing if (tls_ver == TLS1_1_VERSION)
34ad17e628Sjsing return DTLS1_VERSION;
35ad17e628Sjsing if (tls_ver == TLS1_2_VERSION)
36ad17e628Sjsing return DTLS1_2_VERSION;
37ad17e628Sjsing return 0;
38ad17e628Sjsing }
39ad17e628Sjsing
402b939dc4Sjsing static int
ssl_clamp_tls_version_range(uint16_t * min_ver,uint16_t * max_ver,uint16_t clamp_min,uint16_t clamp_max)41970acf87Sjsing ssl_clamp_tls_version_range(uint16_t *min_ver, uint16_t *max_ver,
422b939dc4Sjsing uint16_t clamp_min, uint16_t clamp_max)
432b939dc4Sjsing {
442b939dc4Sjsing if (clamp_min > clamp_max || *min_ver > *max_ver)
452b939dc4Sjsing return 0;
462b939dc4Sjsing if (clamp_max < *min_ver || clamp_min > *max_ver)
472b939dc4Sjsing return 0;
482b939dc4Sjsing
492b939dc4Sjsing if (*min_ver < clamp_min)
502b939dc4Sjsing *min_ver = clamp_min;
512b939dc4Sjsing if (*max_ver > clamp_max)
522b939dc4Sjsing *max_ver = clamp_max;
532b939dc4Sjsing
542b939dc4Sjsing return 1;
552b939dc4Sjsing }
562b939dc4Sjsing
572b939dc4Sjsing int
ssl_version_set_min(const SSL_METHOD * meth,uint16_t proto_ver,uint16_t max_tls_ver,uint16_t * out_tls_ver,uint16_t * out_proto_ver)58970acf87Sjsing ssl_version_set_min(const SSL_METHOD *meth, uint16_t proto_ver,
59970acf87Sjsing uint16_t max_tls_ver, uint16_t *out_tls_ver, uint16_t *out_proto_ver)
6043a30d3dSjsing {
61ad17e628Sjsing uint16_t min_proto, min_version, max_version;
6243a30d3dSjsing
63970acf87Sjsing if (proto_ver == 0) {
646ba40c14Sjsing *out_tls_ver = meth->min_tls_version;
65c7716c22Sjsing *out_proto_ver = 0;
6643a30d3dSjsing return 1;
6743a30d3dSjsing }
6843a30d3dSjsing
69970acf87Sjsing min_version = proto_ver;
70970acf87Sjsing max_version = max_tls_ver;
7143a30d3dSjsing
726ba40c14Sjsing if (meth->dtls) {
73ad17e628Sjsing if ((min_version = ssl_dtls_to_tls_version(proto_ver)) == 0)
74ad17e628Sjsing return 0;
75ad17e628Sjsing }
76ad17e628Sjsing
77970acf87Sjsing if (!ssl_clamp_tls_version_range(&min_version, &max_version,
786ba40c14Sjsing meth->min_tls_version, meth->max_tls_version))
7943a30d3dSjsing return 0;
8043a30d3dSjsing
81ad17e628Sjsing min_proto = min_version;
826ba40c14Sjsing if (meth->dtls) {
83ad17e628Sjsing if ((min_proto = ssl_tls_to_dtls_version(min_version)) == 0)
84ad17e628Sjsing return 0;
85ad17e628Sjsing }
86970acf87Sjsing *out_tls_ver = min_version;
87ad17e628Sjsing *out_proto_ver = min_proto;
8843a30d3dSjsing
8943a30d3dSjsing return 1;
9043a30d3dSjsing }
9143a30d3dSjsing
9243a30d3dSjsing int
ssl_version_set_max(const SSL_METHOD * meth,uint16_t proto_ver,uint16_t min_tls_ver,uint16_t * out_tls_ver,uint16_t * out_proto_ver)93970acf87Sjsing ssl_version_set_max(const SSL_METHOD *meth, uint16_t proto_ver,
94970acf87Sjsing uint16_t min_tls_ver, uint16_t *out_tls_ver, uint16_t *out_proto_ver)
9543a30d3dSjsing {
96ad17e628Sjsing uint16_t max_proto, min_version, max_version;
9743a30d3dSjsing
98970acf87Sjsing if (proto_ver == 0) {
996ba40c14Sjsing *out_tls_ver = meth->max_tls_version;
100c7716c22Sjsing *out_proto_ver = 0;
10143a30d3dSjsing return 1;
10243a30d3dSjsing }
10343a30d3dSjsing
104970acf87Sjsing min_version = min_tls_ver;
105970acf87Sjsing max_version = proto_ver;
10643a30d3dSjsing
1076ba40c14Sjsing if (meth->dtls) {
108ad17e628Sjsing if ((max_version = ssl_dtls_to_tls_version(proto_ver)) == 0)
109ad17e628Sjsing return 0;
110ad17e628Sjsing }
111ad17e628Sjsing
112970acf87Sjsing if (!ssl_clamp_tls_version_range(&min_version, &max_version,
1136ba40c14Sjsing meth->min_tls_version, meth->max_tls_version))
11443a30d3dSjsing return 0;
11543a30d3dSjsing
116ad17e628Sjsing max_proto = max_version;
1176ba40c14Sjsing if (meth->dtls) {
118ad17e628Sjsing if ((max_proto = ssl_tls_to_dtls_version(max_version)) == 0)
119ad17e628Sjsing return 0;
120ad17e628Sjsing }
121970acf87Sjsing *out_tls_ver = max_version;
122ad17e628Sjsing *out_proto_ver = max_proto;
12343a30d3dSjsing
12443a30d3dSjsing return 1;
12543a30d3dSjsing }
12643a30d3dSjsing
12743a30d3dSjsing int
ssl_enabled_tls_version_range(SSL * s,uint16_t * min_ver,uint16_t * max_ver)128970acf87Sjsing ssl_enabled_tls_version_range(SSL *s, uint16_t *min_ver, uint16_t *max_ver)
1292b939dc4Sjsing {
1302b939dc4Sjsing uint16_t min_version, max_version;
131ad17e628Sjsing unsigned long options;
1322b939dc4Sjsing
1332b939dc4Sjsing /*
1342b939dc4Sjsing * The enabled versions have to be a contiguous range, which means we
1352b939dc4Sjsing * cannot enable and disable single versions at our whim, even though
1362b939dc4Sjsing * this is what the OpenSSL flags allow. The historical way this has
1372b939dc4Sjsing * been handled is by making a flag mean that all higher versions
1382b939dc4Sjsing * are disabled, if any version lower than the flag is enabled.
1392b939dc4Sjsing */
1402b939dc4Sjsing
1412b939dc4Sjsing min_version = 0;
142a639fc07Sjsing max_version = TLS1_3_VERSION;
1436f7f653bSjsing options = s->options;
1442b939dc4Sjsing
145ad17e628Sjsing if (SSL_is_dtls(s)) {
146ad17e628Sjsing options = 0;
1476f7f653bSjsing if (s->options & SSL_OP_NO_DTLSv1)
148007a3d8dSjsing options |= SSL_OP_NO_TLSv1 | SSL_OP_NO_TLSv1_1;
1496f7f653bSjsing if (s->options & SSL_OP_NO_DTLSv1_2)
150007a3d8dSjsing options |= SSL_OP_NO_TLSv1 | SSL_OP_NO_TLSv1_2;
151ad17e628Sjsing }
152ad17e628Sjsing
153*521ba2f2Sbeck if ((options & SSL_OP_NO_TLSv1_2) == 0)
1542b939dc4Sjsing min_version = TLS1_2_VERSION;
155ad17e628Sjsing else if ((options & SSL_OP_NO_TLSv1_3) == 0)
156a639fc07Sjsing min_version = TLS1_3_VERSION;
1572b939dc4Sjsing
158ad17e628Sjsing if ((options & SSL_OP_NO_TLSv1_3) && min_version < TLS1_3_VERSION)
159a639fc07Sjsing max_version = TLS1_2_VERSION;
160ad17e628Sjsing if ((options & SSL_OP_NO_TLSv1_2) && min_version < TLS1_2_VERSION)
1612b939dc4Sjsing max_version = 0;
1622b939dc4Sjsing
1632b939dc4Sjsing /* Everything has been disabled... */
1642b939dc4Sjsing if (min_version == 0 || max_version == 0)
1652b939dc4Sjsing return 0;
1662b939dc4Sjsing
1672b939dc4Sjsing /* Limit to configured version range. */
168970acf87Sjsing if (!ssl_clamp_tls_version_range(&min_version, &max_version,
1696f7f653bSjsing s->min_tls_version, s->max_tls_version))
1702b939dc4Sjsing return 0;
1712b939dc4Sjsing
1720093eb61Sjsing /* QUIC requires a minimum of TLSv1.3. */
1730093eb61Sjsing if (SSL_is_quic(s)) {
1740093eb61Sjsing if (max_version < TLS1_3_VERSION)
1750093eb61Sjsing return 0;
1760093eb61Sjsing if (min_version < TLS1_3_VERSION)
1770093eb61Sjsing min_version = TLS1_3_VERSION;
1780093eb61Sjsing }
1790093eb61Sjsing
1802b939dc4Sjsing if (min_ver != NULL)
1812b939dc4Sjsing *min_ver = min_version;
1822b939dc4Sjsing if (max_ver != NULL)
1832b939dc4Sjsing *max_ver = max_version;
1842b939dc4Sjsing
1852b939dc4Sjsing return 1;
1862b939dc4Sjsing }
1872b939dc4Sjsing
1882b939dc4Sjsing int
ssl_supported_tls_version_range(SSL * s,uint16_t * min_ver,uint16_t * max_ver)189970acf87Sjsing ssl_supported_tls_version_range(SSL *s, uint16_t *min_ver, uint16_t *max_ver)
1902b939dc4Sjsing {
1912b939dc4Sjsing uint16_t min_version, max_version;
1922b939dc4Sjsing
193970acf87Sjsing if (!ssl_enabled_tls_version_range(s, &min_version, &max_version))
1942b939dc4Sjsing return 0;
1952b939dc4Sjsing
1962b939dc4Sjsing /* Limit to the versions supported by this method. */
197970acf87Sjsing if (!ssl_clamp_tls_version_range(&min_version, &max_version,
1986ba40c14Sjsing s->method->min_tls_version, s->method->max_tls_version))
1992b939dc4Sjsing return 0;
2002b939dc4Sjsing
2012b939dc4Sjsing if (min_ver != NULL)
2022b939dc4Sjsing *min_ver = min_version;
2032b939dc4Sjsing if (max_ver != NULL)
2042b939dc4Sjsing *max_ver = max_version;
2052b939dc4Sjsing
2062b939dc4Sjsing return 1;
2072b939dc4Sjsing }
2082b939dc4Sjsing
209c5e6469dSjsing uint16_t
ssl_tls_version(uint16_t version)210c5e6469dSjsing ssl_tls_version(uint16_t version)
211c5e6469dSjsing {
212c5e6469dSjsing if (version == TLS1_VERSION || version == TLS1_1_VERSION ||
213c5e6469dSjsing version == TLS1_2_VERSION || version == TLS1_3_VERSION)
214c5e6469dSjsing return version;
215c5e6469dSjsing
216c5e6469dSjsing if (version == DTLS1_VERSION)
217c5e6469dSjsing return TLS1_1_VERSION;
218c5e6469dSjsing if (version == DTLS1_2_VERSION)
219c5e6469dSjsing return TLS1_2_VERSION;
220c5e6469dSjsing
221c5e6469dSjsing return 0;
222c5e6469dSjsing }
223c5e6469dSjsing
224c5e6469dSjsing uint16_t
ssl_effective_tls_version(SSL * s)225c5e6469dSjsing ssl_effective_tls_version(SSL *s)
226c5e6469dSjsing {
22702876cc3Sjsing if (s->s3->hs.negotiated_tls_version > 0)
22802876cc3Sjsing return s->s3->hs.negotiated_tls_version;
229c5e6469dSjsing
23002876cc3Sjsing return s->s3->hs.our_max_tls_version;
231c5e6469dSjsing }
232c5e6469dSjsing
2332b939dc4Sjsing int
ssl_max_supported_version(SSL * s,uint16_t * max_ver)234305a9276Sjsing ssl_max_supported_version(SSL *s, uint16_t *max_ver)
235305a9276Sjsing {
236ad17e628Sjsing uint16_t max_version;
237ad17e628Sjsing
238305a9276Sjsing *max_ver = 0;
239305a9276Sjsing
240ad17e628Sjsing if (!ssl_supported_tls_version_range(s, NULL, &max_version))
241ad17e628Sjsing return 0;
242ad17e628Sjsing
243970acf87Sjsing if (SSL_is_dtls(s)) {
244ad17e628Sjsing if ((max_version = ssl_tls_to_dtls_version(max_version)) == 0)
245ad17e628Sjsing return 0;
246970acf87Sjsing }
247970acf87Sjsing
248ad17e628Sjsing *max_ver = max_version;
249305a9276Sjsing
250305a9276Sjsing return 1;
251305a9276Sjsing }
252305a9276Sjsing
253305a9276Sjsing int
ssl_max_legacy_version(SSL * s,uint16_t * max_ver)25401f29c58Sjsing ssl_max_legacy_version(SSL *s, uint16_t *max_ver)
25501f29c58Sjsing {
25601f29c58Sjsing uint16_t max_version;
25701f29c58Sjsing
25802876cc3Sjsing if ((max_version = s->s3->hs.our_max_tls_version) > TLS1_2_VERSION)
25901f29c58Sjsing max_version = TLS1_2_VERSION;
26001f29c58Sjsing
26101f29c58Sjsing if (SSL_is_dtls(s)) {
26201f29c58Sjsing if ((max_version = ssl_tls_to_dtls_version(max_version)) == 0)
26301f29c58Sjsing return 0;
26401f29c58Sjsing }
26501f29c58Sjsing
26601f29c58Sjsing *max_ver = max_version;
26701f29c58Sjsing
26801f29c58Sjsing return 1;
26901f29c58Sjsing }
27001f29c58Sjsing
27101f29c58Sjsing int
ssl_max_shared_version(SSL * s,uint16_t peer_ver,uint16_t * max_ver)2722b939dc4Sjsing ssl_max_shared_version(SSL *s, uint16_t peer_ver, uint16_t *max_ver)
2732b939dc4Sjsing {
274ad17e628Sjsing uint16_t min_version, max_version, peer_tls_version, shared_version;
2752b939dc4Sjsing
2762b939dc4Sjsing *max_ver = 0;
277ad17e628Sjsing peer_tls_version = peer_ver;
2782b939dc4Sjsing
2799e659261Sjsing if (SSL_is_dtls(s)) {
280ad17e628Sjsing if ((peer_ver >> 8) != DTLS1_VERSION_MAJOR)
2812b939dc4Sjsing return 0;
282ad17e628Sjsing
283ad17e628Sjsing /*
284ad17e628Sjsing * Convert the peer version to a TLS version - DTLS versions are
285ad17e628Sjsing * the 1's complement of TLS version numbers (but not the actual
286ad17e628Sjsing * protocol version numbers, that would be too sensible). Not to
287ad17e628Sjsing * mention that DTLSv1.0 is really equivalent to DTLSv1.1.
288ad17e628Sjsing */
289ad17e628Sjsing peer_tls_version = ssl_dtls_to_tls_version(peer_ver);
290ad17e628Sjsing
291ad17e628Sjsing /*
292ad17e628Sjsing * This may be a version that we do not know about, if it is
293ad17e628Sjsing * newer than DTLS1_2_VERSION (yes, less than is correct due
294ad17e628Sjsing * to the "clever" versioning scheme), use TLS1_2_VERSION.
295ad17e628Sjsing */
296ad17e628Sjsing if (peer_tls_version == 0) {
297ad17e628Sjsing if (peer_ver < DTLS1_2_VERSION)
298ad17e628Sjsing peer_tls_version = TLS1_2_VERSION;
299ad17e628Sjsing }
3002b939dc4Sjsing }
3012b939dc4Sjsing
302ad17e628Sjsing if (peer_tls_version >= TLS1_3_VERSION)
303a639fc07Sjsing shared_version = TLS1_3_VERSION;
304ad17e628Sjsing else if (peer_tls_version >= TLS1_2_VERSION)
3052b939dc4Sjsing shared_version = TLS1_2_VERSION;
306ad17e628Sjsing else if (peer_tls_version >= TLS1_1_VERSION)
3072b939dc4Sjsing shared_version = TLS1_1_VERSION;
308ad17e628Sjsing else if (peer_tls_version >= TLS1_VERSION)
3092b939dc4Sjsing shared_version = TLS1_VERSION;
3102b939dc4Sjsing else
3112b939dc4Sjsing return 0;
3122b939dc4Sjsing
313970acf87Sjsing if (!ssl_supported_tls_version_range(s, &min_version, &max_version))
3142b939dc4Sjsing return 0;
3152b939dc4Sjsing
3162b939dc4Sjsing if (shared_version < min_version)
3172b939dc4Sjsing return 0;
3182b939dc4Sjsing
3192b939dc4Sjsing if (shared_version > max_version)
3202b939dc4Sjsing shared_version = max_version;
3212b939dc4Sjsing
322ad17e628Sjsing if (SSL_is_dtls(s)) {
323ad17e628Sjsing /*
324ad17e628Sjsing * The resulting shared version will by definition be something
325ad17e628Sjsing * that we know about. Switch back from TLS to DTLS.
326ad17e628Sjsing */
327ad17e628Sjsing shared_version = ssl_tls_to_dtls_version(shared_version);
328ad17e628Sjsing if (shared_version == 0)
329ad17e628Sjsing return 0;
330ad17e628Sjsing }
331ad17e628Sjsing
33289b4969bStb if (!ssl_security_version(s, shared_version))
33389b4969bStb return 0;
33489b4969bStb
3352b939dc4Sjsing *max_ver = shared_version;
3362b939dc4Sjsing
3372b939dc4Sjsing return 1;
3382b939dc4Sjsing }
3392b939dc4Sjsing
3403231e218Sjsing int
ssl_check_version_from_server(SSL * s,uint16_t server_version)341305a9276Sjsing ssl_check_version_from_server(SSL *s, uint16_t server_version)
342305a9276Sjsing {
343ad17e628Sjsing uint16_t min_tls_version, max_tls_version, server_tls_version;
344305a9276Sjsing
345305a9276Sjsing /* Ensure that the version selected by the server is valid. */
346305a9276Sjsing
347ad17e628Sjsing server_tls_version = server_version;
348ad17e628Sjsing if (SSL_is_dtls(s)) {
349ad17e628Sjsing server_tls_version = ssl_dtls_to_tls_version(server_version);
350ad17e628Sjsing if (server_tls_version == 0)
351ad17e628Sjsing return 0;
352ad17e628Sjsing }
353305a9276Sjsing
354ad17e628Sjsing if (!ssl_supported_tls_version_range(s, &min_tls_version,
355ad17e628Sjsing &max_tls_version))
356305a9276Sjsing return 0;
357305a9276Sjsing
35889b4969bStb if (server_tls_version < min_tls_version ||
35989b4969bStb server_tls_version > max_tls_version)
36089b4969bStb return 0;
36189b4969bStb
36289b4969bStb return ssl_security_version(s, server_tls_version);
363305a9276Sjsing }
364305a9276Sjsing
365305a9276Sjsing int
ssl_legacy_stack_version(SSL * s,uint16_t version)366b81375ccSjsing ssl_legacy_stack_version(SSL *s, uint16_t version)
367b81375ccSjsing {
368b81375ccSjsing if (SSL_is_dtls(s))
369e9d01b14Sjsing return version == DTLS1_VERSION || version == DTLS1_2_VERSION;
370b81375ccSjsing
371b81375ccSjsing return version == TLS1_VERSION || version == TLS1_1_VERSION ||
372b81375ccSjsing version == TLS1_2_VERSION;
373b81375ccSjsing }
374