xref: /openbsd-src/lib/libssl/ssl_versions.c (revision de8cc8edbc71bd3e3bc7fbffa27ba0e564c37d8b)
1 /* $OpenBSD: ssl_versions.c,v 1.13 2021/02/25 17:06:05 jsing Exp $ */
2 /*
3  * Copyright (c) 2016, 2017 Joel Sing <jsing@openbsd.org>
4  *
5  * Permission to use, copy, modify, and distribute this software for any
6  * purpose with or without fee is hereby granted, provided that the above
7  * copyright notice and this permission notice appear in all copies.
8  *
9  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
10  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
11  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
12  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
13  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
14  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
15  * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
16  */
17 
18 #include "ssl_locl.h"
19 
20 static int
21 ssl_clamp_tls_version_range(uint16_t *min_ver, uint16_t *max_ver,
22     uint16_t clamp_min, uint16_t clamp_max)
23 {
24 	if (clamp_min > clamp_max || *min_ver > *max_ver)
25 		return 0;
26 	if (clamp_max < *min_ver || clamp_min > *max_ver)
27 		return 0;
28 
29 	if (*min_ver < clamp_min)
30 		*min_ver = clamp_min;
31 	if (*max_ver > clamp_max)
32 		*max_ver = clamp_max;
33 
34 	return 1;
35 }
36 
37 int
38 ssl_version_set_min(const SSL_METHOD *meth, uint16_t proto_ver,
39     uint16_t max_tls_ver, uint16_t *out_tls_ver, uint16_t *out_proto_ver)
40 {
41 	uint16_t min_version, max_version;
42 
43 	if (proto_ver == 0) {
44 		*out_tls_ver = meth->internal->min_tls_version;
45 		*out_proto_ver = 0;
46 		return 1;
47 	}
48 	if (meth->internal->dtls) {
49 		if (proto_ver != DTLS1_VERSION)
50 			return 0;
51 		*out_tls_ver = TLS1_1_VERSION;
52 		*out_proto_ver = proto_ver;
53 		return 1;
54 	}
55 
56 	min_version = proto_ver;
57 	max_version = max_tls_ver;
58 
59 	if (!ssl_clamp_tls_version_range(&min_version, &max_version,
60 	    meth->internal->min_tls_version, meth->internal->max_tls_version))
61 		return 0;
62 
63 	*out_tls_ver = min_version;
64 	*out_proto_ver = min_version;
65 
66 	return 1;
67 }
68 
69 int
70 ssl_version_set_max(const SSL_METHOD *meth, uint16_t proto_ver,
71     uint16_t min_tls_ver, uint16_t *out_tls_ver, uint16_t *out_proto_ver)
72 {
73 	uint16_t min_version, max_version;
74 
75 	if (proto_ver == 0) {
76 		*out_tls_ver = meth->internal->max_tls_version;
77 		*out_proto_ver = 0;
78 		return 1;
79 	}
80 	if (meth->internal->dtls) {
81 		if (proto_ver != DTLS1_VERSION)
82 			return 0;
83 		*out_tls_ver = TLS1_1_VERSION;
84 		*out_proto_ver = proto_ver;
85 		return 1;
86 	}
87 
88 	min_version = min_tls_ver;
89 	max_version = proto_ver;
90 
91 	if (!ssl_clamp_tls_version_range(&min_version, &max_version,
92 	    meth->internal->min_tls_version, meth->internal->max_tls_version))
93 		return 0;
94 
95 	*out_tls_ver = max_version;
96 	*out_proto_ver = max_version;
97 
98 	return 1;
99 }
100 
101 int
102 ssl_enabled_tls_version_range(SSL *s, uint16_t *min_ver, uint16_t *max_ver)
103 {
104 	uint16_t min_version, max_version;
105 
106 	/*
107 	 * The enabled versions have to be a contiguous range, which means we
108 	 * cannot enable and disable single versions at our whim, even though
109 	 * this is what the OpenSSL flags allow. The historical way this has
110 	 * been handled is by making a flag mean that all higher versions
111 	 * are disabled, if any version lower than the flag is enabled.
112 	 */
113 
114 	min_version = 0;
115 	max_version = TLS1_3_VERSION;
116 
117 	if ((s->internal->options & SSL_OP_NO_TLSv1) == 0)
118 		min_version = TLS1_VERSION;
119 	else if ((s->internal->options & SSL_OP_NO_TLSv1_1) == 0)
120 		min_version = TLS1_1_VERSION;
121 	else if ((s->internal->options & SSL_OP_NO_TLSv1_2) == 0)
122 		min_version = TLS1_2_VERSION;
123 	else if ((s->internal->options & SSL_OP_NO_TLSv1_3) == 0)
124 		min_version = TLS1_3_VERSION;
125 
126 	if ((s->internal->options & SSL_OP_NO_TLSv1_3) && min_version < TLS1_3_VERSION)
127 		max_version = TLS1_2_VERSION;
128 	if ((s->internal->options & SSL_OP_NO_TLSv1_2) && min_version < TLS1_2_VERSION)
129 		max_version = TLS1_1_VERSION;
130 	if ((s->internal->options & SSL_OP_NO_TLSv1_1) && min_version < TLS1_1_VERSION)
131 		max_version = TLS1_VERSION;
132 	if ((s->internal->options & SSL_OP_NO_TLSv1) && min_version < TLS1_VERSION)
133 		max_version = 0;
134 
135 	/* Everything has been disabled... */
136 	if (min_version == 0 || max_version == 0)
137 		return 0;
138 
139 	/* Limit to configured version range. */
140 	if (!ssl_clamp_tls_version_range(&min_version, &max_version,
141 	    s->internal->min_tls_version, s->internal->max_tls_version))
142 		return 0;
143 
144 	if (min_ver != NULL)
145 		*min_ver = min_version;
146 	if (max_ver != NULL)
147 		*max_ver = max_version;
148 
149 	return 1;
150 }
151 
152 int
153 ssl_supported_tls_version_range(SSL *s, uint16_t *min_ver, uint16_t *max_ver)
154 {
155 	uint16_t min_version, max_version;
156 
157 	if (!ssl_enabled_tls_version_range(s, &min_version, &max_version))
158 		return 0;
159 
160 	/* Limit to the versions supported by this method. */
161 	if (!ssl_clamp_tls_version_range(&min_version, &max_version,
162 	    s->method->internal->min_tls_version,
163 	    s->method->internal->max_tls_version))
164 		return 0;
165 
166 	if (min_ver != NULL)
167 		*min_ver = min_version;
168 	if (max_ver != NULL)
169 		*max_ver = max_version;
170 
171 	return 1;
172 }
173 
174 int
175 ssl_max_supported_version(SSL *s, uint16_t *max_ver)
176 {
177 	*max_ver = 0;
178 
179 	if (SSL_is_dtls(s)) {
180 		*max_ver = DTLS1_VERSION;
181 		return 1;
182 	}
183 
184 	if (!ssl_supported_tls_version_range(s, NULL, max_ver))
185 		return 0;
186 
187 	return 1;
188 }
189 
190 int
191 ssl_max_shared_version(SSL *s, uint16_t peer_ver, uint16_t *max_ver)
192 {
193 	uint16_t min_version, max_version, shared_version;
194 
195 	*max_ver = 0;
196 
197 	if (SSL_is_dtls(s)) {
198 		if (peer_ver >= DTLS1_VERSION) {
199 			*max_ver = DTLS1_VERSION;
200 			return 1;
201 		}
202 		return 0;
203 	}
204 
205 	if (peer_ver >= TLS1_3_VERSION)
206 		shared_version = TLS1_3_VERSION;
207 	else if (peer_ver >= TLS1_2_VERSION)
208 		shared_version = TLS1_2_VERSION;
209 	else if (peer_ver >= TLS1_1_VERSION)
210 		shared_version = TLS1_1_VERSION;
211 	else if (peer_ver >= TLS1_VERSION)
212 		shared_version = TLS1_VERSION;
213 	else
214 		return 0;
215 
216 	if (!ssl_supported_tls_version_range(s, &min_version, &max_version))
217 		return 0;
218 
219 	if (shared_version < min_version)
220 		return 0;
221 
222 	if (shared_version > max_version)
223 		shared_version = max_version;
224 
225 	*max_ver = shared_version;
226 
227 	return 1;
228 }
229 
230 int
231 ssl_downgrade_max_version(SSL *s, uint16_t *max_ver)
232 {
233 	uint16_t min_version, max_version;
234 
235 	/*
236 	 * The downgrade maximum version is based on the versions that are
237 	 * enabled, however we also have to then limit to the versions
238 	 * supported by the method. The SSL method will be changed during
239 	 * version negotiation and when switching from the new stack to
240 	 * the legacy context, as such we want to use the method from the
241 	 * context.
242 	 */
243 
244 	if (SSL_is_dtls(s)) {
245 		*max_ver = DTLS1_VERSION;
246 		return 1;
247 	}
248 
249 	if (!ssl_enabled_tls_version_range(s, &min_version, &max_version))
250 		return 0;
251 
252 	if (!ssl_clamp_tls_version_range(&min_version, &max_version,
253 	    s->ctx->method->internal->min_tls_version,
254 	    s->ctx->method->internal->max_tls_version))
255 		return 0;
256 
257 	*max_ver = max_version;
258 
259 	return 1;
260 }
261 
262 int
263 ssl_check_version_from_server(SSL *s, uint16_t server_version)
264 {
265 	uint16_t min_version, max_version;
266 
267 	/* Ensure that the version selected by the server is valid. */
268 
269 	if (SSL_is_dtls(s))
270 		return (server_version == DTLS1_VERSION);
271 
272 	if (!ssl_supported_tls_version_range(s, &min_version, &max_version))
273 		return 0;
274 
275 	return (server_version >= min_version && server_version <= max_version);
276 }
277 
278 int
279 ssl_legacy_stack_version(SSL *s, uint16_t version)
280 {
281 	if (SSL_is_dtls(s))
282 		return version == DTLS1_VERSION || version == DTLS1_2_VERSION;
283 
284 	return version == TLS1_VERSION || version == TLS1_1_VERSION ||
285 	    version == TLS1_2_VERSION;
286 }
287