1 /*-
2  * SSLsplit - transparent SSL/TLS interception
3  * https://www.roe.ch/SSLsplit
4  *
5  * Copyright (c) 2009-2019, Daniel Roethlisberger <daniel@roe.ch>.
6  * Copyright (c) 2017-2021, Soner Tari <sonertari@gmail.com>.
7  * All rights reserved.
8  *
9  * Redistribution and use in source and binary forms, with or without
10  * modification, are permitted provided that the following conditions are met:
11  * 1. Redistributions of source code must retain the above copyright notice,
12  *    this list of conditions and the following disclaimer.
13  * 2. Redistributions in binary form must reproduce the above copyright notice,
14  *    this list of conditions and the following disclaimer in the documentation
15  *    and/or other materials provided with the distribution.
16  *
17  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDER AND CONTRIBUTORS ``AS IS''
18  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
19  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
20  * ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
21  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
22  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
23  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
24  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
25  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
26  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
27  * POSSIBILITY OF SUCH DAMAGE.
28  */
29 
30 #include "protossl.h"
31 #include "prototcp.h"
32 #include "protopassthrough.h"
33 
34 #include "cachemgr.h"
35 
36 #include <string.h>
37 #include <sys/param.h>
38 #include <event2/bufferevent_ssl.h>
39 
40 /*
41  * Context used for all server sessions.
42  */
43 #ifdef USE_SSL_SESSION_ID_CONTEXT
44 static unsigned long ssl_session_context = 0x31415926;
45 #endif /* USE_SSL_SESSION_ID_CONTEXT */
46 
47 void
protossl_log_ssl_error(struct bufferevent * bev,pxy_conn_ctx_t * ctx)48 protossl_log_ssl_error(struct bufferevent *bev, pxy_conn_ctx_t *ctx)
49 {
50 	unsigned long sslerr;
51 
52 	/* Can happen for socket errs, ssl errs;
53 	 * may happen for unclean ssl socket shutdowns. */
54 	sslerr = bufferevent_get_openssl_error(bev);
55 	if (sslerr)
56 		ctx->sslctx->have_sslerr = 1;
57 	if (!errno && !sslerr) {
58 #if LIBEVENT_VERSION_NUMBER >= 0x02010000
59 		/* We have disabled notification for unclean shutdowns
60 		 * so this should not happen; log a warning. */
61 		log_err_level_printf(LOG_WARNING, "Spurious error from bufferevent (errno=0,sslerr=0)\n");
62 #else /* LIBEVENT_VERSION_NUMBER < 0x02010000 */
63 		/* Older versions of libevent will report these. */
64 		if (OPTS_DEBUG(ctx->global)) {
65 			log_dbg_printf("Unclean SSL shutdown, fd=%d\n", ctx->fd);
66 		}
67 #endif /* LIBEVENT_VERSION_NUMBER < 0x02010000 */
68 	} else if (ERR_GET_REASON(sslerr) == SSL_R_SSLV3_ALERT_HANDSHAKE_FAILURE) {
69 		/* these can happen due to client cert auth,
70 		 * only log error if debugging is activated */
71 		log_dbg_printf("Error from bufferevent: %i:%s %lu:%i:%s:%i:%s:%i:%s\n",
72 					   errno, errno ? strerror(errno) : "-", sslerr,
73 					   ERR_GET_REASON(sslerr), STRORDASH(ERR_reason_error_string(sslerr)),
74 					   ERR_GET_LIB(sslerr), STRORDASH(ERR_lib_error_string(sslerr)),
75 					   ERR_GET_FUNC(sslerr), STRORDASH(ERR_func_error_string(sslerr)));
76 		while ((sslerr = bufferevent_get_openssl_error(bev))) {
77 			log_dbg_printf("Additional SSL error: %lu:%i:%s:%i:%s:%i:%s\n",
78 						   sslerr,
79 						   ERR_GET_REASON(sslerr), STRORDASH(ERR_reason_error_string(sslerr)),
80 						   ERR_GET_LIB(sslerr), STRORDASH(ERR_lib_error_string(sslerr)),
81 						   ERR_GET_FUNC(sslerr), STRORDASH(ERR_func_error_string(sslerr)));
82 		}
83 	} else {
84 		/* real errors */
85 		log_err_printf("Error from bufferevent: %i:%s %lu:%i:%s:%i:%s:%i:%s\n",
86 					   errno, errno ? strerror(errno) : "-",
87 					   sslerr,
88 					   ERR_GET_REASON(sslerr), STRORDASH(ERR_reason_error_string(sslerr)),
89 					   ERR_GET_LIB(sslerr), STRORDASH(ERR_lib_error_string(sslerr)),
90 					   ERR_GET_FUNC(sslerr), STRORDASH(ERR_func_error_string(sslerr)));
91 		while ((sslerr = bufferevent_get_openssl_error(bev))) {
92 			log_err_printf("Additional SSL error: %lu:%i:%s:%i:%s:%i:%s\n",
93 						   sslerr,
94 						   ERR_GET_REASON(sslerr), STRORDASH(ERR_reason_error_string(sslerr)),
95 						   ERR_GET_LIB(sslerr), STRORDASH(ERR_lib_error_string(sslerr)),
96 						   ERR_GET_FUNC(sslerr), STRORDASH(ERR_func_error_string(sslerr)));
97 		}
98 	}
99 	if (ctx->spec->opts->filter && !ctx->pass) {
100 		log_err_level_printf(LOG_WARNING, "Closing on ssl error without filter match: %s:%s, %s:%s, "
101 #ifndef WITHOUT_USERAUTH
102 			"%s, %s, "
103 #endif /* !WITHOUT_USERAUTH */
104 			"%s, %s\n",
105 			STRORDASH(ctx->srchost_str), STRORDASH(ctx->srcport_str), STRORDASH(ctx->dsthost_str), STRORDASH(ctx->dstport_str),
106 #ifndef WITHOUT_USERAUTH
107 			STRORDASH(ctx->user), STRORDASH(ctx->desc),
108 #endif /* !WITHOUT_USERAUTH */
109 			STRORDASH(ctx->sslctx->sni), STRORDASH(ctx->sslctx->ssl_names));
110 	}
111 }
112 
113 int
protossl_log_masterkey(pxy_conn_ctx_t * ctx,pxy_conn_desc_t * this)114 protossl_log_masterkey(pxy_conn_ctx_t *ctx, pxy_conn_desc_t *this)
115 {
116 	// XXX: Remove ssl check? But the caller function is called by non-ssl protos.
117 	if (this->ssl) {
118 		/* log master key */
119 		if (ctx->log_master && ctx->global->masterkeylog) {
120 			char *keystr;
121 			keystr = ssl_ssl_masterkey_to_str(this->ssl);
122 			if ((keystr == NULL) ||
123 				(log_masterkey_print_free(keystr) == -1)) {
124 				if (errno == ENOMEM)
125 					ctx->enomem = 1;
126 				pxy_conn_term(ctx, 1);
127 				return -1;
128 			}
129 		}
130 	}
131 	return 0;
132 }
133 
134 /* forward declaration of OpenSSL callbacks */
135 #ifndef OPENSSL_NO_TLSEXT
136 static int protossl_ossl_servername_cb(SSL *ssl, int *al, void *arg);
137 #endif /* !OPENSSL_NO_TLSEXT */
138 static int protossl_ossl_sessnew_cb(SSL *, SSL_SESSION *);
139 static void protossl_ossl_sessremove_cb(SSL_CTX *, SSL_SESSION *);
140 #if (OPENSSL_VERSION_NUMBER < 0x10100000L) || (defined(LIBRESSL_VERSION_NUMBER) && LIBRESSL_VERSION_NUMBER < 0x20800000L)
141 static SSL_SESSION * protossl_ossl_sessget_cb(SSL *, unsigned char *, int, int *);
142 #else /* OPENSSL_VERSION_NUMBER >= 0x10100000L */
143 static SSL_SESSION * protossl_ossl_sessget_cb(SSL *, const unsigned char *, int, int *);
144 #endif /* OPENSSL_VERSION_NUMBER >= 0x10100000L */
145 
146 /*
147  * Dump information on a certificate to the debug log.
148  */
149 static void
protossl_debug_crt(X509 * crt)150 protossl_debug_crt(X509 *crt)
151 {
152 	char *sj = ssl_x509_subject(crt);
153 	if (sj) {
154 		log_dbg_printf("Subject DN: %s\n", sj);
155 		free(sj);
156 	}
157 
158 	char *names = ssl_x509_names_to_str(crt);
159 	if (names) {
160 		log_dbg_printf("Common Names: %s\n", names);
161 		free(names);
162 	}
163 
164 	char *fpr;
165 	if (!(fpr = ssl_x509_fingerprint(crt, 1))) {
166 		log_err_level_printf(LOG_WARNING, "Error generating X509 fingerprint\n");
167 	} else {
168 		log_dbg_printf("Fingerprint: %s\n", fpr);
169 		free(fpr);
170 	}
171 
172 #ifdef DEBUG_CERTIFICATE
173 	/* dump certificate */
174 	log_dbg_print_free(ssl_x509_to_str(crt));
175 	log_dbg_print_free(ssl_x509_to_pem(crt));
176 #endif /* DEBUG_CERTIFICATE */
177 }
178 
179 /*
180  * Called by OpenSSL when a new src SSL session is created.
181  * OpenSSL increments the refcount before calling the callback and will
182  * decrement it again if we return 0.  Returning 1 will make OpenSSL skip
183  * the refcount decrementing.  In other words, return 0 if we did not
184  * keep a pointer to the object (which we never do here).
185  */
186 #ifdef HAVE_SSLV2
187 #define MAYBE_UNUSED
188 #else /* !HAVE_SSLV2 */
189 #define MAYBE_UNUSED UNUSED
190 #endif /* !HAVE_SSLV2 */
191 static int
protossl_ossl_sessnew_cb(MAYBE_UNUSED SSL * ssl,SSL_SESSION * sess)192 protossl_ossl_sessnew_cb(MAYBE_UNUSED SSL *ssl, SSL_SESSION *sess)
193 #undef MAYBE_UNUSED
194 {
195 #ifdef DEBUG_SESSION_CACHE
196 	log_dbg_printf("===> OpenSSL new session callback:\n");
197 	if (sess) {
198 		log_dbg_print_free(ssl_session_to_str(sess));
199 	} else {
200 		log_dbg_printf("(null)\n");
201 	}
202 #endif /* DEBUG_SESSION_CACHE */
203 #ifdef HAVE_SSLV2
204 	/* Session resumption seems to fail for SSLv2 with protocol
205 	 * parsing errors, so we disable caching for SSLv2. */
206 	if (SSL_version(ssl) == SSL2_VERSION) {
207 		log_err_level_printf(LOG_WARNING, "Session resumption denied to SSLv2"
208 		               "client.\n");
209 		return 0;
210 	}
211 #endif /* HAVE_SSLV2 */
212 	if (sess) {
213 		cachemgr_ssess_set(sess);
214 	}
215 	return 0;
216 }
217 
218 /*
219  * Called by OpenSSL when a src SSL session should be removed.
220  * OpenSSL calls SSL_SESSION_free() after calling the callback;
221  * we do not need to free the reference here.
222  */
223 static void
protossl_ossl_sessremove_cb(UNUSED SSL_CTX * sslctx,SSL_SESSION * sess)224 protossl_ossl_sessremove_cb(UNUSED SSL_CTX *sslctx, SSL_SESSION *sess)
225 {
226 #ifdef DEBUG_SESSION_CACHE
227 	log_dbg_printf("===> OpenSSL remove session callback:\n");
228 	if (sess) {
229 		log_dbg_print_free(ssl_session_to_str(sess));
230 	} else {
231 		log_dbg_printf("(null)\n");
232 	}
233 #endif /* DEBUG_SESSION_CACHE */
234 	if (sess) {
235 		cachemgr_ssess_del(sess);
236 	}
237 }
238 
239 /*
240  * Called by OpenSSL when a src SSL session is requested by the client.
241  */
242 static SSL_SESSION *
243 #if (OPENSSL_VERSION_NUMBER < 0x10100000L) || (defined(LIBRESSL_VERSION_NUMBER) && LIBRESSL_VERSION_NUMBER < 0x20800000L)
protossl_ossl_sessget_cb(UNUSED SSL * ssl,unsigned char * id,int idlen,int * copy)244 protossl_ossl_sessget_cb(UNUSED SSL *ssl, unsigned char *id, int idlen, int *copy)
245 #else /* OPENSSL_VERSION_NUMBER >= 0x10100000L */
246 protossl_ossl_sessget_cb(UNUSED SSL *ssl, const unsigned char *id, int idlen, int *copy)
247 #endif /* OPENSSL_VERSION_NUMBER >= 0x10100000L */
248 {
249 	SSL_SESSION *sess;
250 
251 #ifdef DEBUG_SESSION_CACHE
252 	log_dbg_printf("===> OpenSSL get session callback:\n");
253 #endif /* DEBUG_SESSION_CACHE */
254 
255 	*copy = 0; /* SSL should not increment reference count of session */
256 	sess = cachemgr_ssess_get(id, idlen);
257 
258 #ifdef DEBUG_SESSION_CACHE
259 	if (sess) {
260 		log_dbg_print_free(ssl_session_to_str(sess));
261 	}
262 #endif /* DEBUG_SESSION_CACHE */
263 
264 	log_dbg_printf("SSL session cache: %s\n", sess ? "HIT" : "MISS");
265 	return sess;
266 }
267 
268 /*
269  * Set SSL_CTX options that are the same for incoming and outgoing SSL_CTX.
270  */
271 static void
protossl_sslctx_setoptions(SSL_CTX * sslctx,pxy_conn_ctx_t * ctx)272 protossl_sslctx_setoptions(SSL_CTX *sslctx, pxy_conn_ctx_t *ctx)
273 {
274 	SSL_CTX_set_options(sslctx, SSL_OP_ALL);
275 #ifdef SSL_OP_TLS_ROLLBACK_BUG
276 	SSL_CTX_set_options(sslctx, SSL_OP_TLS_ROLLBACK_BUG);
277 #endif /* SSL_OP_TLS_ROLLBACK_BUG */
278 #ifdef SSL_OP_ALLOW_UNSAFE_LEGACY_RENEGOTIATION
279 	SSL_CTX_set_options(sslctx, SSL_OP_ALLOW_UNSAFE_LEGACY_RENEGOTIATION);
280 #endif /* SSL_OP_ALLOW_UNSAFE_LEGACY_RENEGOTIATION */
281 #ifdef SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS
282 	SSL_CTX_set_options(sslctx, SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS);
283 #endif /* SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS */
284 #ifdef SSL_OP_NO_TICKET
285 	SSL_CTX_set_options(sslctx, SSL_OP_NO_TICKET);
286 #endif /* SSL_OP_NO_TICKET */
287 
288 #ifdef SSL_OP_NO_SSLv2
289 #ifdef HAVE_SSLV2
290 	if (ctx->conn_opts->no_ssl2) {
291 #endif /* HAVE_SSLV2 */
292 		SSL_CTX_set_options(sslctx, SSL_OP_NO_SSLv2);
293 #ifdef HAVE_SSLV2
294 	}
295 #endif /* HAVE_SSLV2 */
296 #endif /* !SSL_OP_NO_SSLv2 */
297 #ifdef HAVE_SSLV3
298 	if (ctx->conn_opts->no_ssl3) {
299 		SSL_CTX_set_options(sslctx, SSL_OP_NO_SSLv3);
300 	}
301 #endif /* HAVE_SSLV3 */
302 #ifdef HAVE_TLSV10
303 	if (ctx->conn_opts->no_tls10) {
304 		SSL_CTX_set_options(sslctx, SSL_OP_NO_TLSv1);
305 	}
306 #endif /* HAVE_TLSV10 */
307 #ifdef HAVE_TLSV11
308 	if (ctx->conn_opts->no_tls11) {
309 		SSL_CTX_set_options(sslctx, SSL_OP_NO_TLSv1_1);
310 	}
311 #endif /* HAVE_TLSV11 */
312 #ifdef HAVE_TLSV12
313 	if (ctx->conn_opts->no_tls12) {
314 		SSL_CTX_set_options(sslctx, SSL_OP_NO_TLSv1_2);
315 	}
316 #endif /* HAVE_TLSV12 */
317 #ifdef HAVE_TLSV13
318 	if (ctx->conn_opts->no_tls13) {
319 		SSL_CTX_set_options(sslctx, SSL_OP_NO_TLSv1_3);
320 	}
321 #endif /* HAVE_TLSV13 */
322 
323 #ifdef SSL_OP_NO_COMPRESSION
324 	if (!ctx->conn_opts->sslcomp) {
325 		SSL_CTX_set_options(sslctx, SSL_OP_NO_COMPRESSION);
326 	}
327 #endif /* SSL_OP_NO_COMPRESSION */
328 
329 	SSL_CTX_set_cipher_list(sslctx, ctx->conn_opts->ciphers);
330 #ifdef HAVE_TLSV13
331 	SSL_CTX_set_ciphersuites(sslctx, ctx->conn_opts->ciphersuites);
332 #endif /* HAVE_TLSV13 */
333 
334 #if (OPENSSL_VERSION_NUMBER >= 0x10100000L) && !defined(LIBRESSL_VERSION_NUMBER)
335 	/* If the security level of OpenSSL is set to 2+ in system configuration,
336 	 * our forged certificates with 1024-bit RSA key size will be rejected */
337 	SSL_CTX_set_security_level(sslctx, 1);
338 #endif /* OPENSSL_VERSION_NUMBER >= 0x10100000L */
339 }
340 
341 /*
342  * Create and set up a new SSL_CTX instance for terminating SSL.
343  * Set up all the necessary callbacks, the certificate, the cert chain and key.
344  */
345 static SSL_CTX *
protossl_srcsslctx_create(pxy_conn_ctx_t * ctx,X509 * crt,STACK_OF (X509)* chain,EVP_PKEY * key)346 protossl_srcsslctx_create(pxy_conn_ctx_t *ctx, X509 *crt, STACK_OF(X509) *chain,
347                      EVP_PKEY *key)
348 {
349 	SSL_CTX *sslctx = SSL_CTX_new(ctx->conn_opts->sslmethod());
350 	if (!sslctx) {
351 		ctx->enomem = 1;
352 		return NULL;
353 	}
354 
355 	protossl_sslctx_setoptions(sslctx, ctx);
356 
357 #if (OPENSSL_VERSION_NUMBER >= 0x10100000L && !defined(LIBRESSL_VERSION_NUMBER)) || (defined(LIBRESSL_VERSION_NUMBER) && LIBRESSL_VERSION_NUMBER >= 0x20702000L)
358 	if (ctx->conn_opts->minsslversion) {
359 		if (SSL_CTX_set_min_proto_version(sslctx, ctx->conn_opts->minsslversion) == 0) {
360 			SSL_CTX_free(sslctx);
361 			return NULL;
362 		}
363 	}
364 	if (ctx->conn_opts->maxsslversion) {
365 		if (SSL_CTX_set_max_proto_version(sslctx, ctx->conn_opts->maxsslversion) == 0) {
366 			SSL_CTX_free(sslctx);
367 			return NULL;
368 		}
369 	}
370 	// ForceSSLproto has precedence
371 	if (ctx->conn_opts->sslversion) {
372 		if (SSL_CTX_set_min_proto_version(sslctx, ctx->conn_opts->sslversion) == 0 ||
373 			SSL_CTX_set_max_proto_version(sslctx, ctx->conn_opts->sslversion) == 0) {
374 			SSL_CTX_free(sslctx);
375 			return NULL;
376 		}
377 	}
378 #endif /* OPENSSL_VERSION_NUMBER >= 0x10100000L */
379 
380 	SSL_CTX_sess_set_new_cb(sslctx, protossl_ossl_sessnew_cb);
381 	SSL_CTX_sess_set_remove_cb(sslctx, protossl_ossl_sessremove_cb);
382 	SSL_CTX_sess_set_get_cb(sslctx, protossl_ossl_sessget_cb);
383 	SSL_CTX_set_session_cache_mode(sslctx, SSL_SESS_CACHE_SERVER |
384 	                                       SSL_SESS_CACHE_NO_INTERNAL);
385 #ifdef USE_SSL_SESSION_ID_CONTEXT
386 	SSL_CTX_set_session_id_context(sslctx, (void *)(&ssl_session_context),
387 	                                       sizeof(ssl_session_context));
388 #endif /* USE_SSL_SESSION_ID_CONTEXT */
389 #ifndef OPENSSL_NO_TLSEXT
390 	SSL_CTX_set_tlsext_servername_callback(sslctx, protossl_ossl_servername_cb);
391 	SSL_CTX_set_tlsext_servername_arg(sslctx, ctx);
392 #endif /* !OPENSSL_NO_TLSEXT */
393 #ifndef OPENSSL_NO_DH
394 	if (ctx->conn_opts->dh) {
395 		SSL_CTX_set_tmp_dh(sslctx, ctx->conn_opts->dh);
396 	} else {
397 		SSL_CTX_set_tmp_dh_callback(sslctx, ssl_tmp_dh_callback);
398 	}
399 #endif /* !OPENSSL_NO_DH */
400 #ifndef OPENSSL_NO_ECDH
401 	if (ctx->conn_opts->ecdhcurve) {
402 		EC_KEY *ecdh = ssl_ec_by_name(ctx->conn_opts->ecdhcurve);
403 		SSL_CTX_set_tmp_ecdh(sslctx, ecdh);
404 		EC_KEY_free(ecdh);
405 	} else {
406 		EC_KEY *ecdh = ssl_ec_by_name(NULL);
407 		SSL_CTX_set_tmp_ecdh(sslctx, ecdh);
408 		EC_KEY_free(ecdh);
409 	}
410 #endif /* !OPENSSL_NO_ECDH */
411 	if (SSL_CTX_use_certificate(sslctx, crt) != 1) {
412 		log_dbg_printf("loading src server certificate failed\n");
413 		SSL_CTX_free(sslctx);
414 		return NULL;
415 	}
416 	if (SSL_CTX_use_PrivateKey(sslctx, key) != 1) {
417 		log_dbg_printf("loading src server key failed\n");
418 		SSL_CTX_free(sslctx);
419 		return NULL;
420 	}
421 	for (int i = 0; i < sk_X509_num(chain); i++) {
422 		X509 *c = sk_X509_value(chain, i);
423 		ssl_x509_refcount_inc(c); /* next call consumes a reference */
424 		SSL_CTX_add_extra_chain_cert(sslctx, c);
425 	}
426 
427 #ifdef DEBUG_SESSION_CACHE
428 	if (OPTS_DEBUG(ctx->global)) {
429 		int mode = SSL_CTX_get_session_cache_mode(sslctx);
430 		log_dbg_printf("SSL session cache mode: %08x\n", mode);
431 		if (mode == SSL_SESS_CACHE_OFF)
432 			log_dbg_printf("SSL_SESS_CACHE_OFF\n");
433 		if (mode & SSL_SESS_CACHE_CLIENT)
434 			log_dbg_printf("SSL_SESS_CACHE_CLIENT\n");
435 		if (mode & SSL_SESS_CACHE_SERVER)
436 			log_dbg_printf("SSL_SESS_CACHE_SERVER\n");
437 		if (mode & SSL_SESS_CACHE_NO_AUTO_CLEAR)
438 			log_dbg_printf("SSL_SESS_CACHE_NO_AUTO_CLEAR\n");
439 		if (mode & SSL_SESS_CACHE_NO_INTERNAL_LOOKUP)
440 			log_dbg_printf("SSL_SESS_CACHE_NO_INTERNAL_LOOKUP\n");
441 		if (mode & SSL_SESS_CACHE_NO_INTERNAL_STORE)
442 			log_dbg_printf("SSL_SESS_CACHE_NO_INTERNAL_STORE\n");
443 	}
444 #endif /* DEBUG_SESSION_CACHE */
445 
446 	return sslctx;
447 }
448 
449 static int
protossl_srccert_write_to_gendir(pxy_conn_ctx_t * ctx,X509 * crt,int is_orig)450 protossl_srccert_write_to_gendir(pxy_conn_ctx_t *ctx, X509 *crt, int is_orig)
451 {
452 	char *fn;
453 	int rv;
454 
455 	if (!ctx->sslctx->origcrtfpr)
456 		return -1;
457 	if (is_orig) {
458 		rv = asprintf(&fn, "%s/%s.crt", ctx->global->certgendir,
459 		              ctx->sslctx->origcrtfpr);
460 	} else {
461 		if (!ctx->sslctx->usedcrtfpr)
462 			return -1;
463 		rv = asprintf(&fn, "%s/%s-%s.crt", ctx->global->certgendir,
464 		              ctx->sslctx->origcrtfpr, ctx->sslctx->usedcrtfpr);
465 	}
466 	if (rv == -1) {
467 		ctx->enomem = 1;
468 		return -1;
469 	}
470 	rv = log_cert_submit(fn, crt);
471 	free(fn);
472 	return rv;
473 }
474 
475 void
protossl_srccert_write(pxy_conn_ctx_t * ctx)476 protossl_srccert_write(pxy_conn_ctx_t *ctx)
477 {
478 	if (ctx->global->certgen_writeall || ctx->sslctx->generated_cert) {
479 		if (protossl_srccert_write_to_gendir(ctx,
480 		                SSL_get_certificate(ctx->src.ssl), 0) == -1) {
481 			log_err_level_printf(LOG_CRIT, "Failed to write used certificate\n");
482 		}
483 	}
484 	if (ctx->global->certgen_writeall) {
485 		if (protossl_srccert_write_to_gendir(ctx, ctx->sslctx->origcrt, 1) == -1) {
486 			log_err_level_printf(LOG_CRIT, "Failed to write orig certificate\n");
487 		}
488 	}
489 }
490 
491 static cert_t *
protossl_srccert_create(pxy_conn_ctx_t * ctx)492 protossl_srccert_create(pxy_conn_ctx_t *ctx)
493 {
494 	cert_t *cert = NULL;
495 
496 	if (ctx->global->leafcertdir) {
497 		if (ctx->sslctx->sni) {
498 			cert = cachemgr_tgcrt_get(ctx->sslctx->sni);
499 			if (!cert) {
500 				char *wildcarded;
501 				wildcarded = ssl_wildcardify(ctx->sslctx->sni);
502 				if (!wildcarded) {
503 					ctx->enomem = 1;
504 					return NULL;
505 				}
506 				cert = cachemgr_tgcrt_get(wildcarded);
507 				free(wildcarded);
508 			}
509 			if (cert && OPTS_DEBUG(ctx->global)) {
510 				log_dbg_printf("Target cert by SNI\n");
511 			}
512 		} else if (ctx->sslctx->origcrt) {
513 			char **names = ssl_x509_names(ctx->sslctx->origcrt);
514 			for (char **p = names; *p; p++) {
515 				if (!cert) {
516 					cert = cachemgr_tgcrt_get(*p);
517 				}
518 				if (!cert) {
519 					char *wildcarded;
520 					wildcarded = ssl_wildcardify(*p);
521 					if (!wildcarded) {
522 						ctx->enomem = 1;
523 					} else {
524 						/* increases ref count */
525 						cert = cachemgr_tgcrt_get(
526 						       wildcarded);
527 						free(wildcarded);
528 					}
529 				}
530 				free(*p);
531 			}
532 			free(names);
533 			if (ctx->enomem) {
534 				return NULL;
535 			}
536 			if (cert && OPTS_DEBUG(ctx->global)) {
537 				log_dbg_printf("Target cert by origcrt\n");
538 			}
539 		}
540 
541 		if (cert) {
542 			ctx->sslctx->immutable_cert = 1;
543 		}
544 	}
545 
546 	if (!cert && ctx->global->defaultleafcert) {
547 		cert = ctx->global->defaultleafcert;
548 		cert_refcount_inc(cert);
549 		ctx->sslctx->immutable_cert = 1;
550 		if (OPTS_DEBUG(ctx->global)) {
551 			log_dbg_printf("Using default leaf certificate\n");
552 		}
553 	}
554 
555 	if (!cert && ctx->sslctx->origcrt && ctx->global->leafkey) {
556 		cert = cert_new();
557 
558 		cert->crt = cachemgr_fkcrt_get(ctx->sslctx->origcrt);
559 		if (cert->crt) {
560 			if (OPTS_DEBUG(ctx->global))
561 				log_dbg_printf("Certificate cache: HIT\n");
562 		} else {
563 			if (OPTS_DEBUG(ctx->global))
564 				log_dbg_printf("Certificate cache: MISS\n");
565 			cert->crt = ssl_x509_forge(ctx->conn_opts->cacrt,
566 			                           ctx->conn_opts->cakey,
567 			                           ctx->sslctx->origcrt,
568 			                           ctx->global->leafkey,
569 			                           NULL,
570 			                           ctx->conn_opts->leafcrlurl);
571 			cachemgr_fkcrt_set(ctx->sslctx->origcrt, cert->crt);
572 		}
573 		cert_set_key(cert, ctx->global->leafkey);
574 		cert_set_chain(cert, ctx->conn_opts->chain);
575 		ctx->sslctx->generated_cert = 1;
576 	}
577 
578 	if ((WANT_CONNECT_LOG(ctx) || ctx->global->certgendir) && ctx->sslctx->origcrt) {
579 		ctx->sslctx->origcrtfpr = ssl_x509_fingerprint(ctx->sslctx->origcrt, 0);
580 		if (!ctx->sslctx->origcrtfpr)
581 			ctx->enomem = 1;
582 	}
583 	if ((WANT_CONNECT_LOG(ctx) || ctx->global->certgen_writeall) &&
584 	    cert && cert->crt) {
585 		ctx->sslctx->usedcrtfpr = ssl_x509_fingerprint(cert->crt, 0);
586 		if (!ctx->sslctx->usedcrtfpr)
587 			ctx->enomem = 1;
588 	}
589 
590 	return cert;
591 }
592 
593 static filter_action_t * NONNULL(1,2)
protossl_filter_match_sni(pxy_conn_ctx_t * ctx,filter_list_t * list)594 protossl_filter_match_sni(pxy_conn_ctx_t *ctx, filter_list_t *list)
595 {
596 	filter_site_t *site = filter_site_find(list->sni_btree, list->sni_acm, list->sni_all, ctx->sslctx->sni);
597 	if (!site)
598 		return NULL;
599 
600 #ifndef WITHOUT_USERAUTH
601 	log_fine_va("Found site (line=%d): %s for %s:%s, %s:%s, %s, %s, %s", site->action.line_num, site->site,
602 		STRORDASH(ctx->srchost_str), STRORDASH(ctx->srcport_str), STRORDASH(ctx->dsthost_str), STRORDASH(ctx->dstport_str),
603 		STRORDASH(ctx->user), STRORDASH(ctx->desc), STRORDASH(ctx->sslctx->sni));
604 #else /* WITHOUT_USERAUTH */
605 	log_fine_va("Found site (line=%d): %s for %s:%s, %s:%s, %s", site->action.line_num, site->site,
606 		STRORDASH(ctx->srchost_str), STRORDASH(ctx->srcport_str), STRORDASH(ctx->dsthost_str), STRORDASH(ctx->dstport_str),
607 		STRORDASH(ctx->sslctx->sni));
608 #endif /* WITHOUT_USERAUTH */
609 
610 	if (!site->port_btree && !site->port_acm && (site->action.precedence < ctx->filter_precedence)) {
611 		log_finest_va("Rule precedence lower than conn filter precedence %d < %d (line=%d): %s, %s", site->action.precedence, ctx->filter_precedence, site->action.line_num, site->site, ctx->sslctx->sni);
612 		return NULL;
613 	}
614 
615 #ifdef DEBUG_PROXY
616 	if (site->all_sites)
617 		log_finest_va("Match all sni (line=%d): %s, %s", site->action.line_num, site->site, ctx->sslctx->sni);
618 	else if (site->exact)
619 		log_finest_va("Match exact with sni (line=%d): %s, %s", site->action.line_num, site->site, ctx->sslctx->sni);
620 	else
621 		log_finest_va("Match substring in sni (line=%d): %s, %s", site->action.line_num, site->site, ctx->sslctx->sni);
622 #endif /* DEBUG_PROXY */
623 
624 	filter_action_t *port_action = pxy_conn_filter_port(ctx, site);
625 	if (port_action)
626 		return port_action;
627 
628 	return &site->action;
629 }
630 
631 static filter_action_t * NONNULL(1,2)
protossl_filter_match_cn(pxy_conn_ctx_t * ctx,filter_list_t * list)632 protossl_filter_match_cn(pxy_conn_ctx_t *ctx, filter_list_t *list)
633 {
634 	filter_site_t *site = NULL;
635 
636 // ballpark figures
637 #define MAX_CN_LEN 4096
638 #define MAX_CN_TOKENS 100
639 
640 	int argc = 0;
641 	char *p, *last = NULL;
642 
643 	size_t len = strlen(ctx->sslctx->ssl_names);
644 
645 	if (len > MAX_CN_LEN) {
646 		log_err_level_printf(LOG_WARNING, "Skip too long common names, max len %d: %s\n", MAX_CN_LEN, ctx->sslctx->ssl_names);
647 		return NULL;
648 	}
649 
650 	// Do not tokenize ssl_names if there is no rule to match exact common names
651 	if (list->cn_btree) {
652 		// strtok_r() modifies the string param, so copy ssl_names to a local var and pass it to strtok_r()
653 		char _cn[len + 1];
654 		memcpy(_cn, ctx->sslctx->ssl_names, len);
655 		_cn[len] = '\0';
656 
657 		for ((p = strtok_r(_cn, "/", &last));
658 			 p;
659 			 (p = strtok_r(NULL, "/", &last))) {
660 			if (argc++ < MAX_CN_TOKENS) {
661 				site = filter_site_exact_match(list->cn_btree, p);
662 				if (site) {
663 					log_finest_va("Match exact with common name (%d) (line=%d): %s, %s", argc, site->action.line_num, p, ctx->sslctx->ssl_names);
664 					break;
665 				}
666 			}
667 			else {
668 				log_err_level_printf(LOG_WARNING, "Too many tokens in common names, max tokens %d: %s\n", MAX_CN_TOKENS, ctx->sslctx->ssl_names);
669 				break;
670 			}
671 		}
672 	}
673 
674 	if (!site) {
675 		site = filter_site_substring_match(list->cn_acm, ctx->sslctx->ssl_names);
676 		if (site)
677 			log_finest_va("Match substring in common names (line=%d): %s, %s", site->action.line_num, site->site, ctx->sslctx->ssl_names);
678 	}
679 
680 	if (!site)
681 		return NULL;
682 
683 #ifndef WITHOUT_USERAUTH
684 	log_fine_va("Found site (line=%d): %s for %s:%s, %s:%s, %s, %s, %s", site->action.line_num, site->site,
685 		STRORDASH(ctx->srchost_str), STRORDASH(ctx->srcport_str), STRORDASH(ctx->dsthost_str), STRORDASH(ctx->dstport_str),
686 		STRORDASH(ctx->user), STRORDASH(ctx->desc), STRORDASH(ctx->sslctx->ssl_names));
687 #else /* WITHOUT_USERAUTH */
688 	log_fine_va("Found site (line=%d): %s for %s:%s, %s:%s, %s", site->action.line_num, site->site,
689 		STRORDASH(ctx->srchost_str), STRORDASH(ctx->srcport_str), STRORDASH(ctx->dsthost_str), STRORDASH(ctx->dstport_str),
690 		STRORDASH(ctx->sslctx->ssl_names));
691 #endif /* WITHOUT_USERAUTH */
692 
693 	if (!site->port_btree && !site->port_acm && (site->action.precedence < ctx->filter_precedence)) {
694 		log_finest_va("Rule precedence lower than conn filter precedence %d < %d (line=%d): %s, %s", site->action.precedence, ctx->filter_precedence, site->action.line_num, site->site, ctx->sslctx->ssl_names);
695 		return NULL;
696 	}
697 
698 	if (site->all_sites)
699 		log_finest_va("Match all common names (line=%d): %s, %s", site->action.line_num, site->site, ctx->sslctx->ssl_names);
700 
701 	filter_action_t *port_action = pxy_conn_filter_port(ctx, site);
702 	if (port_action)
703 		return port_action;
704 
705 	return &site->action;
706 }
707 
708 static filter_action_t * NONNULL(1,2)
protossl_filter(pxy_conn_ctx_t * ctx,filter_list_t * list)709 protossl_filter(pxy_conn_ctx_t *ctx, filter_list_t *list)
710 {
711 	filter_action_t *action_sni = NULL;
712 	filter_action_t *action_cn = NULL;
713 
714 	if (ctx->sslctx->sni) {
715 		if (!(action_sni = protossl_filter_match_sni(ctx, list))) {
716 #ifndef WITHOUT_USERAUTH
717 			log_finest_va("No filter match with sni: %s:%s, %s:%s, %s, %s, %s, %s",
718 				STRORDASH(ctx->srchost_str), STRORDASH(ctx->srcport_str), STRORDASH(ctx->dsthost_str), STRORDASH(ctx->dstport_str),
719 				STRORDASH(ctx->user), STRORDASH(ctx->desc), STRORDASH(ctx->sslctx->sni), STRORDASH(ctx->sslctx->ssl_names));
720 #else /* WITHOUT_USERAUTH */
721 			log_finest_va("No filter match with sni: %s:%s, %s:%s, %s, %s",
722 				STRORDASH(ctx->srchost_str), STRORDASH(ctx->srcport_str), STRORDASH(ctx->dsthost_str), STRORDASH(ctx->dstport_str),
723 				STRORDASH(ctx->sslctx->sni), STRORDASH(ctx->sslctx->ssl_names));
724 #endif /* !WITHOUT_USERAUTH */
725 		}
726 	}
727 
728 	if (ctx->sslctx->ssl_names) {
729 		if (!(action_cn = protossl_filter_match_cn(ctx, list))) {
730 #ifndef WITHOUT_USERAUTH
731 			log_finest_va("No filter match with common names: %s:%s, %s:%s, %s, %s, %s, %s",
732 				STRORDASH(ctx->srchost_str), STRORDASH(ctx->srcport_str), STRORDASH(ctx->dsthost_str), STRORDASH(ctx->dstport_str),
733 				STRORDASH(ctx->user), STRORDASH(ctx->desc), STRORDASH(ctx->sslctx->sni), STRORDASH(ctx->sslctx->ssl_names));
734 #else /* WITHOUT_USERAUTH */
735 			log_finest_va("No filter match with common names: %s:%s, %s:%s, %s, %s",
736 				STRORDASH(ctx->srchost_str), STRORDASH(ctx->srcport_str), STRORDASH(ctx->dsthost_str), STRORDASH(ctx->dstport_str),
737 				STRORDASH(ctx->sslctx->sni), STRORDASH(ctx->sslctx->ssl_names));
738 #endif /* !WITHOUT_USERAUTH */
739 		}
740 	}
741 
742 	if (action_sni ||  action_cn)
743 		return pxy_conn_set_filter_action(action_sni, action_cn
744 #ifdef DEBUG_PROXY
745 				, ctx, ctx->sslctx->sni, ctx->sslctx->ssl_names
746 #endif /* DEBUG_PROXY */
747 				);
748 
749 	return NULL;
750 }
751 
752 static void
protossl_reconnect_srvdst(pxy_conn_ctx_t * ctx)753 protossl_reconnect_srvdst(pxy_conn_ctx_t *ctx)
754 {
755 	log_fine("ENTER");
756 
757 	// Reconnect only once
758 	ctx->sslctx->reconnected = 1;
759 
760 	ctx->srvdst.free(ctx->srvdst.bev, ctx);
761 	ctx->srvdst.bev = NULL;
762 	ctx->srvdst.ssl = NULL;
763 	ctx->connected = 0;
764 
765 	if (protossl_conn_connect(ctx) == -1) {
766 		return;
767 	}
768 
769 	if (bufferevent_socket_connect(ctx->srvdst.bev, (struct sockaddr *)&ctx->dstaddr, ctx->dstaddrlen) == -1) {
770 		log_err_level(LOG_CRIT, "bufferevent_socket_connect for srvdst failed");
771 		pxy_conn_term(ctx, 1);
772 	}
773 }
774 
775 static int
protossl_apply_filter(pxy_conn_ctx_t * ctx)776 protossl_apply_filter(pxy_conn_ctx_t *ctx)
777 {
778 	int rv = 0;
779 	filter_action_t *a;
780 	if ((a = pxy_conn_filter(ctx, protossl_filter))) {
781 		unsigned int action = pxy_conn_translate_filter_action(ctx, a);
782 
783 		ctx->filter_precedence = action & FILTER_PRECEDENCE;
784 
785 		if (action & FILTER_ACTION_DIVERT) {
786 			ctx->deferred_action = FILTER_ACTION_NONE;
787 			ctx->divert = 1;
788 		}
789 		else if (action & FILTER_ACTION_SPLIT) {
790 			ctx->deferred_action = FILTER_ACTION_NONE;
791 			ctx->divert = 0;
792 		}
793 		else if (action & FILTER_ACTION_PASS) {
794 			ctx->deferred_action = FILTER_ACTION_NONE;
795 			ctx->pass = 1;
796 			rv = 1;
797 		}
798 		else if (action & FILTER_ACTION_BLOCK) {
799 			// Always defer block action, the only action we can defer from this point on
800 			// This block action should override any deferred pass action,
801 			// because the current rule must have a higher precedence
802 			log_fine("Deferring block action");
803 			ctx->deferred_action = FILTER_ACTION_BLOCK;
804 		}
805 		//else { /* FILTER_ACTION_MATCH */ }
806 
807 		// Filtering rules at higher precedence can enable/disable logging
808 		if (action & FILTER_LOG_CONNECT)
809 			ctx->log_connect = 1;
810 		else if (action & FILTER_LOG_NOCONNECT)
811 			ctx->log_connect = 0;
812 		if (action & FILTER_LOG_MASTER)
813 			ctx->log_master = 1;
814 		else if (action & FILTER_LOG_NOMASTER)
815 			ctx->log_master = 0;
816 		if (action & FILTER_LOG_CERT)
817 			ctx->log_cert = 1;
818 		else if (action & FILTER_LOG_NOCERT)
819 			ctx->log_cert = 0;
820 		if (action & FILTER_LOG_CONTENT)
821 			ctx->log_content = 1;
822 		else if (action & FILTER_LOG_NOCONTENT)
823 			ctx->log_content = 0;
824 		if (action & FILTER_LOG_PCAP)
825 			ctx->log_pcap = 1;
826 		else if (action & FILTER_LOG_NOPCAP)
827 			ctx->log_pcap = 0;
828 #ifndef WITHOUT_MIRROR
829 		if (action & FILTER_LOG_MIRROR)
830 			ctx->log_mirror = 1;
831 		else if (action & FILTER_LOG_NOMIRROR)
832 			ctx->log_mirror = 0;
833 #endif /* !WITHOUT_MIRROR */
834 
835 		if (a->conn_opts) {
836 			ctx->conn_opts = a->conn_opts;
837 
838 			if (ctx->conn_opts->reconnect_ssl) {
839 				// Reconnect srvdst only once, if ReconnectSSL set in the rule
840 				if (!ctx->sslctx->reconnected) {
841 					protossl_reconnect_srvdst(ctx);
842 					// Return immediately to avoid applying deferred pass action
843 					return 1;
844 				} else {
845 					log_finest("Already reconnected once, will not reconnect again");
846 				}
847 			}
848 		}
849 	}
850 
851 	// Cannot defer pass action any longer
852 	// Match action should not override pass action, hence no 'else if'
853 	if (ctx->deferred_action & FILTER_ACTION_PASS) {
854 		log_fine("Applying deferred pass action");
855 		ctx->deferred_action = FILTER_ACTION_NONE;
856 		ctx->pass = 1;
857 		rv = 1;
858 	}
859 
860 	return rv;
861 }
862 
863 /*
864  * Create new SSL context for the incoming connection, based on the original
865  * destination SSL certificate.
866  * Returns NULL if no suitable certificate could be found or the site should
867  * be passed through.
868  */
869 static SSL *
protossl_srcssl_create(pxy_conn_ctx_t * ctx,SSL * origssl)870 protossl_srcssl_create(pxy_conn_ctx_t *ctx, SSL *origssl)
871 {
872 	cert_t *cert;
873 
874 	cachemgr_dsess_set((struct sockaddr*)&ctx->dstaddr,
875 	                   ctx->dstaddrlen, ctx->sslctx->sni,
876 	                   SSL_get0_session(origssl));
877 
878 	ctx->sslctx->origcrt = SSL_get_peer_certificate(origssl);
879 
880 	if (OPTS_DEBUG(ctx->global)) {
881 		if (ctx->sslctx->origcrt) {
882 			log_dbg_printf("===> Original server certificate:\n");
883 			protossl_debug_crt(ctx->sslctx->origcrt);
884 		} else {
885 			log_dbg_printf("===> Original server has no cert!\n");
886 		}
887 	}
888 
889 	cert = protossl_srccert_create(ctx);
890 	if (!cert)
891 		return NULL;
892 
893 	if (OPTS_DEBUG(ctx->global)) {
894 		log_dbg_printf("===> Forged server certificate:\n");
895 		protossl_debug_crt(cert->crt);
896 	}
897 
898 	if (WANT_CONNECT_LOG(ctx) || ctx->spec->opts->filter) {
899 		ctx->sslctx->ssl_names = ssl_x509_names_to_str(ctx->sslctx->origcrt ?
900 		                                       ctx->sslctx->origcrt :
901 		                                       cert->crt);
902 		if (!ctx->sslctx->ssl_names)
903 			ctx->enomem = 1;
904 	}
905 
906 	// Defers any block action until HTTP filter application
907 	// or until the first src readcb of non-http protos
908 	if (protossl_apply_filter(ctx)) {
909 		cert_free(cert);
910 		return NULL;
911 	}
912 
913 	SSL_CTX *sslctx = protossl_srcsslctx_create(ctx, cert->crt, cert->chain,
914 	                                       cert->key);
915 	cert_free(cert);
916 	if (!sslctx)
917 		return NULL;
918 	SSL *ssl = SSL_new(sslctx);
919 	SSL_CTX_free(sslctx); /* SSL_new() increments refcount */
920 	if (!ssl) {
921 		ctx->enomem = 1;
922 		return NULL;
923 	}
924 #ifdef SSL_MODE_RELEASE_BUFFERS
925 	/* lower memory footprint for idle connections */
926 	SSL_set_mode(ssl, SSL_get_mode(ssl) | SSL_MODE_RELEASE_BUFFERS);
927 #endif /* SSL_MODE_RELEASE_BUFFERS */
928 	return ssl;
929 }
930 
931 #ifndef OPENSSL_NO_TLSEXT
932 /*
933  * OpenSSL servername callback, called when OpenSSL receives a servername
934  * TLS extension in the clientHello.  Must switch to a new SSL_CTX with
935  * a different certificate if we want to replace the server cert here.
936  * We generate a new certificate if the current one does not match the
937  * supplied servername.  This should only happen if the original destination
938  * server supplies a certificate which does not match the server name we
939  * indicate to it.
940  */
941 static int
protossl_ossl_servername_cb(SSL * ssl,UNUSED int * al,void * arg)942 protossl_ossl_servername_cb(SSL *ssl, UNUSED int *al, void *arg)
943 {
944 	pxy_conn_ctx_t *ctx = arg;
945 	const char *sn;
946 	X509 *sslcrt;
947 
948 	if (!(sn = SSL_get_servername(ssl, TLSEXT_NAMETYPE_host_name)))
949 		return SSL_TLSEXT_ERR_NOACK;
950 
951 	if (!ctx->sslctx->sni) {
952 		if (OPTS_DEBUG(ctx->global)) {
953 			log_dbg_printf("Warning: SNI parser yielded no "
954 			               "hostname, copying OpenSSL one: "
955 			               "[NULL] != [%s]\n", sn);
956 		}
957 		ctx->sslctx->sni = strdup(sn);
958 		if (!ctx->sslctx->sni) {
959 			ctx->enomem = 1;
960 			return SSL_TLSEXT_ERR_NOACK;
961 		}
962 	}
963 	if (OPTS_DEBUG(ctx->global)) {
964 		if (!!strcmp(sn, ctx->sslctx->sni)) {
965 			/*
966 			 * This may happen if the client resumes a session, but
967 			 * uses a different SNI hostname when resuming than it
968 			 * used when the session was created.  OpenSSL
969 			 * correctly ignores the SNI in the ClientHello in this
970 			 * case, but since we have already sent the SNI onwards
971 			 * to the original destination, there is no way back.
972 			 * We log an error and hope this never happens.
973 			 */
974 			log_dbg_printf("Warning: SNI parser yielded different "
975 			               "hostname than OpenSSL callback for "
976 			               "the same ClientHello message: "
977 			               "[%s] != [%s]\n", ctx->sslctx->sni, sn);
978 		}
979 	}
980 
981 	/* generate a new certificate with sn as additional altSubjectName
982 	 * and replace it both in the current SSL ctx and in the cert cache */
983 	if (ctx->conn_opts->allow_wrong_host && !ctx->sslctx->immutable_cert &&
984 	    !ssl_x509_names_match((sslcrt = SSL_get_certificate(ssl)), sn)) {
985 		X509 *newcrt;
986 		SSL_CTX *newsslctx;
987 
988 		if (OPTS_DEBUG(ctx->global)) {
989 			log_dbg_printf("Certificate cache: UPDATE "
990 			               "(SNI mismatch)\n");
991 		}
992 		newcrt = ssl_x509_forge(ctx->conn_opts->cacrt, ctx->conn_opts->cakey,
993 		                        sslcrt, ctx->global->leafkey,
994 		                        sn, ctx->conn_opts->leafcrlurl);
995 		if (!newcrt) {
996 			ctx->enomem = 1;
997 			return SSL_TLSEXT_ERR_NOACK;
998 		}
999 		cachemgr_fkcrt_set(ctx->sslctx->origcrt, newcrt);
1000 		ctx->sslctx->generated_cert = 1;
1001 		if (OPTS_DEBUG(ctx->global)) {
1002 			log_dbg_printf("===> Updated forged server "
1003 			               "certificate:\n");
1004 			protossl_debug_crt(newcrt);
1005 		}
1006 		if (WANT_CONNECT_LOG(ctx) || ctx->spec->opts->filter) {
1007 			if (ctx->sslctx->ssl_names) {
1008 				free(ctx->sslctx->ssl_names);
1009 			}
1010 			ctx->sslctx->ssl_names = ssl_x509_names_to_str(newcrt);
1011 			if (!ctx->sslctx->ssl_names) {
1012 				ctx->enomem = 1;
1013 			}
1014 		}
1015 		if (WANT_CONNECT_LOG(ctx) || ctx->global->certgendir) {
1016 			if (ctx->sslctx->usedcrtfpr) {
1017 				free(ctx->sslctx->usedcrtfpr);
1018 			}
1019 			ctx->sslctx->usedcrtfpr = ssl_x509_fingerprint(newcrt, 0);
1020 			if (!ctx->sslctx->usedcrtfpr) {
1021 				ctx->enomem = 1;
1022 			}
1023 		}
1024 
1025 		newsslctx = protossl_srcsslctx_create(ctx, newcrt, ctx->conn_opts->chain,
1026 		                                 ctx->global->leafkey);
1027 		if (!newsslctx) {
1028 			X509_free(newcrt);
1029 			return SSL_TLSEXT_ERR_NOACK;
1030 		}
1031 		SSL_set_SSL_CTX(ssl, newsslctx); /* decr's old incr new refc */
1032 		SSL_CTX_free(newsslctx);
1033 		X509_free(newcrt);
1034 	} else if (OPTS_DEBUG(ctx->global)) {
1035 		log_dbg_printf("Certificate cache: KEEP (SNI match or "
1036 		               "target mode)\n");
1037 	}
1038 
1039 	return SSL_TLSEXT_ERR_OK;
1040 }
1041 #endif /* !OPENSSL_NO_TLSEXT */
1042 
1043 /*
1044  * Create new SSL context for outgoing connections to the original destination.
1045  * If hostname sni is provided, use it for Server Name Indication.
1046  */
1047 SSL *
protossl_dstssl_create(pxy_conn_ctx_t * ctx)1048 protossl_dstssl_create(pxy_conn_ctx_t *ctx)
1049 {
1050 	SSL_CTX *sslctx;
1051 	SSL *ssl;
1052 	SSL_SESSION *sess;
1053 
1054 	sslctx = SSL_CTX_new(ctx->conn_opts->sslmethod());
1055 	if (!sslctx) {
1056 		ctx->enomem = 1;
1057 		return NULL;
1058 	}
1059 
1060 	protossl_sslctx_setoptions(sslctx, ctx);
1061 
1062 #if (OPENSSL_VERSION_NUMBER >= 0x10100000L && !defined(LIBRESSL_VERSION_NUMBER)) || (defined(LIBRESSL_VERSION_NUMBER) && LIBRESSL_VERSION_NUMBER >= 0x20702000L)
1063 	if (ctx->conn_opts->minsslversion) {
1064 		if (SSL_CTX_set_min_proto_version(sslctx, ctx->conn_opts->minsslversion) == 0) {
1065 			SSL_CTX_free(sslctx);
1066 			return NULL;
1067 		}
1068 	}
1069 	if (ctx->conn_opts->maxsslversion) {
1070 		if (SSL_CTX_set_max_proto_version(sslctx, ctx->conn_opts->maxsslversion) == 0) {
1071 			SSL_CTX_free(sslctx);
1072 			return NULL;
1073 		}
1074 	}
1075 	// ForceSSLproto has precedence
1076 	if (ctx->conn_opts->sslversion) {
1077 		if (SSL_CTX_set_min_proto_version(sslctx, ctx->conn_opts->sslversion) == 0 ||
1078 			SSL_CTX_set_max_proto_version(sslctx, ctx->conn_opts->sslversion) == 0) {
1079 			SSL_CTX_free(sslctx);
1080 			return NULL;
1081 		}
1082 	}
1083 #endif /* OPENSSL_VERSION_NUMBER >= 0x10100000L */
1084 
1085 	if (ctx->conn_opts->verify_peer) {
1086 		SSL_CTX_set_verify(sslctx, SSL_VERIFY_PEER, NULL);
1087 		SSL_CTX_set_default_verify_paths(sslctx);
1088 	} else {
1089 		SSL_CTX_set_verify(sslctx, SSL_VERIFY_NONE, NULL);
1090 	}
1091 
1092 	if (ctx->conn_opts->clientcrt &&
1093 	    (SSL_CTX_use_certificate(sslctx, ctx->conn_opts->clientcrt) != 1)) {
1094 		log_dbg_printf("loading dst client certificate failed\n");
1095 		SSL_CTX_free(sslctx);
1096 		return NULL;
1097 	}
1098 	if (ctx->conn_opts->clientkey &&
1099 	    (SSL_CTX_use_PrivateKey(sslctx, ctx->conn_opts->clientkey) != 1)) {
1100 		log_dbg_printf("loading dst client key failed\n");
1101 		SSL_CTX_free(sslctx);
1102 		return NULL;
1103 	}
1104 
1105 	ssl = SSL_new(sslctx);
1106 	SSL_CTX_free(sslctx); /* SSL_new() increments refcount */
1107 	if (!ssl) {
1108 		ctx->enomem = 1;
1109 		return NULL;
1110 	}
1111 #ifndef OPENSSL_NO_TLSEXT
1112 	if (ctx->sslctx->sni) {
1113 		SSL_set_tlsext_host_name(ssl, ctx->sslctx->sni);
1114 	}
1115 #endif /* !OPENSSL_NO_TLSEXT */
1116 
1117 #ifdef SSL_MODE_RELEASE_BUFFERS
1118 	/* lower memory footprint for idle connections */
1119 	SSL_set_mode(ssl, SSL_get_mode(ssl) | SSL_MODE_RELEASE_BUFFERS);
1120 #endif /* SSL_MODE_RELEASE_BUFFERS */
1121 
1122 	/* session resuming based on remote endpoint address and port */
1123 	sess = cachemgr_dsess_get((struct sockaddr *)&ctx->dstaddr,
1124 	                          ctx->dstaddrlen, ctx->sslctx->sni); /* new sess inst */
1125 	if (sess) {
1126 		if (OPTS_DEBUG(ctx->global)) {
1127 			log_dbg_printf("Attempt reuse dst SSL session\n");
1128 		}
1129 		SSL_set_session(ssl, sess); /* increments sess refcount */
1130 		SSL_SESSION_free(sess);
1131 	}
1132 
1133 	return ssl;
1134 }
1135 
1136 /*
1137  * Set up a bufferevent structure for either a dst or src connection,
1138  * optionally with or without SSL.  Sets all callbacks, enables read
1139  * and write events, but does not call bufferevent_socket_connect().
1140  *
1141  * For dst connections, pass -1 as fd.  Pass a pointer to an initialized
1142  * SSL struct as ssl if the connection should use SSL.
1143  *
1144  * Returns pointer to initialized bufferevent structure, as returned
1145  * by bufferevent_socket_new() or bufferevent_openssl_socket_new().
1146  */
1147 static struct bufferevent * NONNULL(1,3)
protossl_bufferevent_setup(pxy_conn_ctx_t * ctx,evutil_socket_t fd,SSL * ssl)1148 protossl_bufferevent_setup(pxy_conn_ctx_t *ctx, evutil_socket_t fd, SSL *ssl)
1149 {
1150 	log_finest_va("ENTER, fd=%d", fd);
1151 
1152 	struct bufferevent *bev = bufferevent_openssl_socket_new(ctx->thr->evbase, fd, ssl,
1153 			((fd == -1) ? BUFFEREVENT_SSL_CONNECTING : BUFFEREVENT_SSL_ACCEPTING), BEV_OPT_DEFER_CALLBACKS);
1154 	if (!bev) {
1155 		log_err_level_printf(LOG_CRIT, "Error creating bufferevent socket\n");
1156 		return NULL;
1157 	}
1158 #if LIBEVENT_VERSION_NUMBER >= 0x02010000
1159 	log_finest_va("bufferevent_openssl_set_allow_dirty_shutdown, fd=%d", fd);
1160 
1161 	/* Prevent unclean (dirty) shutdowns to cause error
1162 	 * events on the SSL socket bufferevent. */
1163 	bufferevent_openssl_set_allow_dirty_shutdown(bev, 1);
1164 #endif /* LIBEVENT_VERSION_NUMBER >= 0x02010000 */
1165 
1166 	// @attention Do not set callbacks here, we do not set r cb for tcp/ssl srvdst
1167 	//bufferevent_setcb(bev, pxy_bev_readcb, pxy_bev_writecb, pxy_bev_eventcb, ctx);
1168 	// @attention Do not enable r/w events here, we do not set r cb for tcp/ssl srvdst
1169 	// Also, to avoid r/w cb before connected, we should enable r/w events after the conn is connected
1170 	//bufferevent_enable(bev, EV_READ|EV_WRITE);
1171 	return bev;
1172 }
1173 
1174 static struct bufferevent * NONNULL(1,3)
protossl_bufferevent_setup_child(pxy_conn_child_ctx_t * ctx,evutil_socket_t fd,SSL * ssl)1175 protossl_bufferevent_setup_child(pxy_conn_child_ctx_t *ctx, evutil_socket_t fd, SSL *ssl)
1176 {
1177 	log_finest_va("ENTER, fd=%d", fd);
1178 
1179 	struct bufferevent *bev = bufferevent_openssl_socket_new(ctx->conn->thr->evbase, fd, ssl,
1180 			((fd == -1) ? BUFFEREVENT_SSL_CONNECTING : BUFFEREVENT_SSL_ACCEPTING), BEV_OPT_DEFER_CALLBACKS);
1181 	if (!bev) {
1182 		log_err_level_printf(LOG_CRIT, "Error creating bufferevent socket\n");
1183 		return NULL;
1184 	}
1185 
1186 #if LIBEVENT_VERSION_NUMBER >= 0x02010000
1187 	log_finest_va("bufferevent_openssl_set_allow_dirty_shutdown, fd=%d", fd);
1188 
1189 	/* Prevent unclean (dirty) shutdowns to cause error
1190 	 * events on the SSL socket bufferevent. */
1191 	bufferevent_openssl_set_allow_dirty_shutdown(bev, 1);
1192 #endif /* LIBEVENT_VERSION_NUMBER >= 0x02010000 */
1193 
1194 	bufferevent_setcb(bev, pxy_bev_readcb_child, pxy_bev_writecb_child, pxy_bev_eventcb_child, ctx);
1195 
1196 	// @attention We cannot enable events here, because src events will be deferred until after dst is connected
1197 	// Also, to avoid r/w cb before connected, we should enable r/w events after the conn is connected
1198 	//bufferevent_enable(bev, EV_READ|EV_WRITE);
1199 	return bev;
1200 }
1201 
1202 /*
1203  * Free bufferenvent and close underlying socket properly.
1204  * For OpenSSL bufferevents, this will shutdown the SSL connection.
1205  */
1206 static void
protossl_bufferevent_free_and_close_fd(struct bufferevent * bev,pxy_conn_ctx_t * ctx)1207 protossl_bufferevent_free_and_close_fd(struct bufferevent *bev, pxy_conn_ctx_t *ctx)
1208 {
1209 	SSL *ssl = bufferevent_openssl_get_ssl(bev); /* does not inc refc */
1210 	struct bufferevent *ubev = bufferevent_get_underlying(bev);
1211 	evutil_socket_t fd;
1212 
1213 	if (ubev) {
1214 		fd = bufferevent_getfd(ubev);
1215 	} else {
1216 		fd = bufferevent_getfd(bev);
1217 	}
1218 
1219 	log_finer_va("in=%zu, out=%zu, fd=%d", evbuffer_get_length(bufferevent_get_input(bev)), evbuffer_get_length(bufferevent_get_output(bev)), fd);
1220 
1221 	// @see https://stackoverflow.com/questions/31688709/knowing-all-callbacks-have-run-with-libevent-and-bufferevent-free
1222 	bufferevent_setcb(bev, NULL, NULL, NULL, NULL);
1223 
1224 	/*
1225 	 * From the libevent book:  SSL_RECEIVED_SHUTDOWN tells
1226 	 * SSL_shutdown to act as if we had already received a close
1227 	 * notify from the other end.  SSL_shutdown will then send the
1228 	 * final close notify in reply.  The other end will receive the
1229 	 * close notify and send theirs.  By this time, we will have
1230 	 * already closed the socket and the other end's real close
1231 	 * notify will never be received.  In effect, both sides will
1232 	 * think that they have completed a clean shutdown and keep
1233 	 * their sessions valid.  This strategy will fail if the socket
1234 	 * is not ready for writing, in which case this hack will lead
1235 	 * to an unclean shutdown and lost session on the other end.
1236 	 *
1237 	 * Note that in the case of autossl, the SSL object operates on
1238 	 * a BIO wrapper around the underlying bufferevent.
1239 	 */
1240 	SSL_set_shutdown(ssl, SSL_RECEIVED_SHUTDOWN);
1241 	SSL_shutdown(ssl);
1242 
1243 	bufferevent_disable(bev, EV_READ|EV_WRITE);
1244 	if (ubev) {
1245 		bufferevent_disable(ubev, EV_READ|EV_WRITE);
1246 		bufferevent_setfd(ubev, -1);
1247 		bufferevent_setcb(ubev, NULL, NULL, NULL, NULL);
1248 		bufferevent_free(ubev);
1249 	}
1250 	bufferevent_free(bev);
1251 
1252 	if (OPTS_DEBUG(ctx->global)) {
1253 		char *str = ssl_ssl_state_to_str(ssl, "SSL_free() in state ", 1);
1254 		if (str)
1255 			log_dbg_print_free(str);
1256 	}
1257 #ifdef DEBUG_PROXY
1258 	char *str = ssl_ssl_state_to_str(ssl, "SSL_free() in state ", 0);
1259 	if (str) {
1260 		log_finer_va("fd=%d, %s", fd, str);
1261 		free(str);
1262 	}
1263 #endif /* DEBUG_PROXY */
1264 
1265 	SSL_free(ssl);
1266 	/* bufferevent_getfd() returns -1 if no file descriptor is associated
1267 	 * with the bufferevent */
1268 	if (fd >= 0)
1269 		evutil_closesocket(fd);
1270 }
1271 
1272 void
protossl_free(pxy_conn_ctx_t * ctx)1273 protossl_free(pxy_conn_ctx_t *ctx)
1274 {
1275 	if (ctx->sslctx->ssl_names) {
1276 		free(ctx->sslctx->ssl_names);
1277 	}
1278 	if (ctx->sslctx->origcrtfpr) {
1279 		free(ctx->sslctx->origcrtfpr);
1280 	}
1281 	if (ctx->sslctx->usedcrtfpr) {
1282 		free(ctx->sslctx->usedcrtfpr);
1283 	}
1284 	if (ctx->sslctx->origcrt) {
1285 		X509_free(ctx->sslctx->origcrt);
1286 	}
1287 	if (ctx->sslctx->sni) {
1288 		free(ctx->sslctx->sni);
1289 	}
1290 	if (ctx->sslctx->srvdst_ssl_version) {
1291 		free(ctx->sslctx->srvdst_ssl_version);
1292 	}
1293 	if (ctx->sslctx->srvdst_ssl_cipher) {
1294 		free(ctx->sslctx->srvdst_ssl_cipher);
1295 	}
1296 	free(ctx->sslctx);
1297 	// It is necessary to NULL the sslctx to prevent passthrough mode trying to access it (signal 11 crash)
1298 	ctx->sslctx = NULL;
1299 }
1300 
1301 #ifndef OPENSSL_NO_TLSEXT
1302 /*
1303  * The SNI hostname has been resolved.  Fill the first resolved address into
1304  * the context and continue connecting.
1305  */
1306 static void
protossl_sni_resolve_cb(int errcode,struct evutil_addrinfo * ai,void * arg)1307 protossl_sni_resolve_cb(int errcode, struct evutil_addrinfo *ai, void *arg)
1308 {
1309 	pxy_conn_ctx_t *ctx = arg;
1310 
1311 	log_finest("ENTER");
1312 
1313 	if (errcode) {
1314 		log_err_printf("Cannot resolve SNI hostname '%s': %s\n", ctx->sslctx->sni, evutil_gai_strerror(errcode));
1315 		evutil_closesocket(ctx->fd);
1316 		pxy_conn_ctx_free(ctx, 1);
1317 		return;
1318 	}
1319 
1320 	memcpy(&ctx->dstaddr, ai->ai_addr, ai->ai_addrlen);
1321 	ctx->dstaddrlen = ai->ai_addrlen;
1322 	evutil_freeaddrinfo(ai);
1323 	pxy_conn_connect(ctx);
1324 }
1325 #endif /* !OPENSSL_NO_TLSEXT */
1326 
1327 /*
1328  * The src fd is readable.  This is used to sneak-preview the SNI on SSL
1329  * connections.  If ctx->ev is NULL, it was called manually for a non-SSL
1330  * connection.  If ctx->opts->passthrough is set, it was called a second time
1331  * after the first ssl callout failed because of client cert auth.
1332  */
1333 static void
protossl_fd_readcb(evutil_socket_t fd,UNUSED short what,void * arg)1334 protossl_fd_readcb(evutil_socket_t fd, UNUSED short what, void *arg)
1335 {
1336 	pxy_conn_ctx_t *ctx = arg;
1337 
1338 	log_finest("ENTER");
1339 
1340 	event_free(ctx->ev);
1341 	ctx->ev = NULL;
1342 
1343 	// Child connections will use the sni info obtained by the parent conn
1344 	/* for SSL, peek ClientHello and parse SNI from it */
1345 
1346 	unsigned char buf[1024];
1347 	ssize_t n;
1348 	const unsigned char *chello;
1349 	int rv;
1350 
1351 	n = recv(fd, buf, sizeof(buf), MSG_PEEK);
1352 	if (n == -1) {
1353 		log_err_printf("Error peeking on fd, aborting connection\n");
1354 		log_fine("Error peeking on fd, aborting connection");
1355 		goto out;
1356 	}
1357 	if (n == 0) {
1358 		/* socket got closed while we were waiting */
1359 		log_err_printf("Socket got closed while waiting\n");
1360 		log_fine("Socket got closed while waiting");
1361 		goto out;
1362 	}
1363 
1364 	rv = ssl_tls_clienthello_parse(buf, n, 0, &chello, &ctx->sslctx->sni);
1365 	if ((rv == 1) && !chello) {
1366 		log_err_printf("Peeking did not yield a (truncated) ClientHello message, aborting connection\n");
1367 		log_fine("Peeking did not yield a (truncated) ClientHello message, aborting connection");
1368 		goto out;
1369 	}
1370 	if (OPTS_DEBUG(ctx->global)) {
1371 		log_dbg_printf("SNI peek: [%s] [%s], fd=%d\n", ctx->sslctx->sni ? ctx->sslctx->sni : "n/a",
1372 					   ((rv == 1) && chello) ? "incomplete" : "complete", ctx->fd);
1373 	}
1374 	if ((rv == 1) && chello && (ctx->sslctx->sni_peek_retries++ < 50)) {
1375 		/* ssl_tls_clienthello_parse indicates that we
1376 		 * should retry later when we have more data, and we
1377 		 * haven't reached the maximum retry count yet.
1378 		 * Reschedule this event as timeout-only event in
1379 		 * order to prevent busy looping over the read event.
1380 		 * Because we only peeked at the pending bytes and
1381 		 * never actually read them, fd is still ready for
1382 		 * reading now.  We use 25 * 0.2 s = 5 s timeout. */
1383 		struct timeval retry_delay = {0, 100};
1384 
1385 		ctx->ev = event_new(ctx->thr->evbase, fd, 0, protossl_fd_readcb, ctx);
1386 		if (!ctx->ev) {
1387 			log_err_level(LOG_CRIT, "Error creating retry event, aborting connection");
1388 			goto out;
1389 		}
1390 		if (event_add(ctx->ev, &retry_delay) == -1)
1391 			goto out;
1392 		return;
1393 	}
1394 
1395 	if (ctx->sslctx->sni && !ctx->dstaddrlen && ctx->spec->sni_port) {
1396 		char sniport[6];
1397 		struct evutil_addrinfo hints;
1398 
1399 		memset(&hints, 0, sizeof(hints));
1400 		hints.ai_family = ctx->af;
1401 		hints.ai_flags = EVUTIL_AI_ADDRCONFIG;
1402 		hints.ai_socktype = SOCK_STREAM;
1403 		hints.ai_protocol = IPPROTO_TCP;
1404 
1405 		snprintf(sniport, sizeof(sniport), "%i", ctx->spec->sni_port);
1406 		evdns_getaddrinfo(ctx->thr->dnsbase, ctx->sslctx->sni, sniport, &hints, protossl_sni_resolve_cb, ctx);
1407 		return;
1408 	}
1409 
1410 	pxy_conn_connect(ctx);
1411 	return;
1412 out:
1413 	evutil_closesocket(fd);
1414 	pxy_conn_ctx_free(ctx, 1);
1415 }
1416 
1417 void
protossl_init_conn(evutil_socket_t fd,UNUSED short what,void * arg)1418 protossl_init_conn(evutil_socket_t fd, UNUSED short what, void *arg)
1419 {
1420 	pxy_conn_ctx_t *ctx = arg;
1421 
1422 	log_finest("ENTER");
1423 
1424 	event_free(ctx->ev);
1425 	ctx->ev = NULL;
1426 
1427 	if (pxy_conn_init(ctx) == -1)
1428 		return;
1429 
1430 #ifdef OPENSSL_NO_TLSEXT
1431 	pxy_conn_connect(ctx);
1432 	return;
1433 #endif /* !OPENSSL_NO_TLSEXT */
1434 
1435 	/* for SSL, defer dst connection setup to initial_readcb */
1436 	ctx->ev = event_new(ctx->thr->evbase, ctx->fd, EV_READ, protossl_fd_readcb, ctx);
1437 	if (!ctx->ev)
1438 		goto out;
1439 
1440 	if (event_add(ctx->ev, NULL) == -1) {
1441 		log_finest("event_add failed");
1442 		// Note that the timercb of the connection handling thread may try to access the ctx
1443 		goto out;
1444 	}
1445 	return;
1446 out:
1447 	evutil_closesocket(fd);
1448 	pxy_conn_ctx_free(ctx, 1);
1449 }
1450 
1451 int
protossl_setup_dst_ssl(pxy_conn_ctx_t * ctx)1452 protossl_setup_dst_ssl(pxy_conn_ctx_t *ctx)
1453 {
1454 	ctx->dst.ssl = protossl_dstssl_create(ctx);
1455 	if (!ctx->dst.ssl) {
1456 		log_err_level_printf(LOG_CRIT, "Error creating SSL for dst\n");
1457 		pxy_conn_term(ctx, 1);
1458 		return -1;
1459 	}
1460 	return 0;
1461 }
1462 
1463 static int NONNULL(1)
protossl_setup_srvdst_ssl(pxy_conn_ctx_t * ctx)1464 protossl_setup_srvdst_ssl(pxy_conn_ctx_t *ctx)
1465 {
1466 	ctx->srvdst.ssl = protossl_dstssl_create(ctx);
1467 	if (!ctx->srvdst.ssl) {
1468 		log_err_level_printf(LOG_CRIT, "Error creating SSL for srvdst\n");
1469 		pxy_conn_term(ctx, 1);
1470 		return -1;
1471 	}
1472 	return 0;
1473 }
1474 
1475 int
protossl_setup_srvdst(pxy_conn_ctx_t * ctx)1476 protossl_setup_srvdst(pxy_conn_ctx_t *ctx)
1477 {
1478 	if (protossl_setup_srvdst_ssl(ctx) == -1) {
1479 		return -1;
1480 	}
1481 
1482 	ctx->srvdst.bev = protossl_bufferevent_setup(ctx, -1, ctx->srvdst.ssl);
1483 	if (!ctx->srvdst.bev) {
1484 		log_err_level_printf(LOG_CRIT, "Error creating srvdst\n");
1485 		SSL_free(ctx->srvdst.ssl);
1486 		ctx->srvdst.ssl = NULL;
1487 		pxy_conn_term(ctx, 1);
1488 		return -1;
1489 	}
1490 	ctx->srvdst.free = protossl_bufferevent_free_and_close_fd;
1491 	return 0;
1492 }
1493 
1494 int
protossl_conn_connect(pxy_conn_ctx_t * ctx)1495 protossl_conn_connect(pxy_conn_ctx_t *ctx)
1496 {
1497 	log_finest("ENTER");
1498 
1499 	/* create server-side socket and eventbuffer */
1500 	if (protossl_setup_srvdst(ctx) == -1) {
1501 		return -1;
1502 	}
1503 
1504 	// Disable and NULL r/w cbs, we do nothing for srvdst in r/w cbs
1505 	bufferevent_setcb(ctx->srvdst.bev, NULL, NULL, pxy_bev_eventcb, ctx);
1506 	return 0;
1507 }
1508 
1509 int
protossl_setup_dst_ssl_child(pxy_conn_child_ctx_t * ctx)1510 protossl_setup_dst_ssl_child(pxy_conn_child_ctx_t *ctx)
1511 {
1512 	// Children rely on the findings of parent
1513 	ctx->dst.ssl = protossl_dstssl_create(ctx->conn);
1514 	if (!ctx->dst.ssl) {
1515 		log_err_level_printf(LOG_CRIT, "Error creating SSL\n");
1516 		// pxy_conn_free()>pxy_conn_free_child() will close the fd, since we have a non-NULL src.bev now
1517 		pxy_conn_term(ctx->conn, 1);
1518 		return -1;
1519 	}
1520 	return 0;
1521 }
1522 
1523 int
protossl_setup_dst_child(pxy_conn_child_ctx_t * ctx)1524 protossl_setup_dst_child(pxy_conn_child_ctx_t *ctx)
1525 {
1526 	if (!ctx->conn->srvdst_xferred) {
1527 		// Reuse srvdst of parent in the first child conn
1528 		ctx->conn->srvdst_xferred = 1;
1529 		ctx->srvdst_xferred = 1;
1530 		ctx->dst = ctx->conn->srvdst;
1531 		bufferevent_setcb(ctx->dst.bev, pxy_bev_readcb_child, pxy_bev_writecb_child, pxy_bev_eventcb_child, ctx);
1532 		ctx->protoctx->bev_eventcb(ctx->dst.bev, BEV_EVENT_CONNECTED, ctx);
1533 	} else {
1534 		if (protossl_setup_dst_ssl_child(ctx) == -1) {
1535 			return -1;
1536 		}
1537 
1538 		ctx->dst.bev = protossl_bufferevent_setup_child(ctx, -1, ctx->dst.ssl);
1539 		if (!ctx->dst.bev) {
1540 			log_err_level_printf(LOG_CRIT, "Error creating dst bufferevent\n");
1541 			SSL_free(ctx->dst.ssl);
1542 			ctx->dst.ssl = NULL;
1543 			pxy_conn_term(ctx->conn, 1);
1544 			return -1;
1545 		}
1546 		ctx->dst.free = protossl_bufferevent_free_and_close_fd;
1547 	}
1548 	return 0;
1549 }
1550 
1551 void
protossl_connect_child(pxy_conn_child_ctx_t * ctx)1552 protossl_connect_child(pxy_conn_child_ctx_t *ctx)
1553 {
1554 	log_finest("ENTER");
1555 
1556 	/* create server-side socket and eventbuffer */
1557 	protossl_setup_dst_child(ctx);
1558 }
1559 
1560 static int NONNULL(1)
protossl_setup_src_ssl(pxy_conn_ctx_t * ctx)1561 protossl_setup_src_ssl(pxy_conn_ctx_t *ctx)
1562 {
1563 	// @todo Make srvdst.ssl the origssl param
1564 	if (ctx->src.ssl || (ctx->src.ssl = protossl_srcssl_create(ctx, ctx->srvdst.ssl))) {
1565 		return 0;
1566 	}
1567 	else if (ctx->term) {
1568 		return -1;
1569 	}
1570 	else if (!ctx->enomem && (ctx->pass || ctx->conn_opts->passthrough)) {
1571 		log_err_level_printf(LOG_WARNING, "Falling back to passthrough\n");
1572 		protopassthrough_engage(ctx);
1573 		// report protocol change by returning 1
1574 		return 1;
1575 	}
1576 	else if (ctx->sslctx->reconnected) {
1577 		return -1;
1578 	}
1579 	pxy_conn_term(ctx, 1);
1580 	return -1;
1581 }
1582 
1583 int
protossl_setup_src_ssl_from_dst(pxy_conn_ctx_t * ctx)1584 protossl_setup_src_ssl_from_dst(pxy_conn_ctx_t *ctx)
1585 {
1586 	// @attention We cannot engage passthrough mode upon ssl errors on already enabled src
1587 	// This function is used by protoautossl only
1588 	if (ctx->src.ssl || (ctx->src.ssl = protossl_srcssl_create(ctx, ctx->dst.ssl))) {
1589 		return 0;
1590 	}
1591 	else if (ctx->term) {
1592 		return -1;
1593 	}
1594 	pxy_conn_term(ctx, 1);
1595 	return -1;
1596 }
1597 
1598 int
protossl_setup_src_ssl_from_child_dst(pxy_conn_child_ctx_t * ctx)1599 protossl_setup_src_ssl_from_child_dst(pxy_conn_child_ctx_t *ctx)
1600 {
1601 	// @attention We cannot engage passthrough mode upon ssl errors on already enabled src
1602 	// This function is used by protoautossl only
1603 	if (ctx->conn->src.ssl || (ctx->conn->src.ssl = protossl_srcssl_create(ctx->conn, ctx->dst.ssl))) {
1604 		return 0;
1605 	}
1606 	else if (ctx->conn->term) {
1607 		return -1;
1608 	}
1609 	pxy_conn_term(ctx->conn, 1);
1610 	return -1;
1611 }
1612 
1613 static int NONNULL(1)
protossl_setup_src(pxy_conn_ctx_t * ctx)1614 protossl_setup_src(pxy_conn_ctx_t *ctx)
1615 {
1616 	int rv;
1617 	if ((rv = protossl_setup_src_ssl(ctx)) != 0) {
1618 		return rv;
1619 	}
1620 
1621 	ctx->src.bev = protossl_bufferevent_setup(ctx, ctx->fd, ctx->src.ssl);
1622 	if (!ctx->src.bev) {
1623 		log_err_level_printf(LOG_CRIT, "Error creating src bufferevent\n");
1624 		SSL_free(ctx->src.ssl);
1625 		ctx->src.ssl = NULL;
1626 		pxy_conn_term(ctx, 1);
1627 		return -1;
1628 	}
1629 	ctx->src.free = protossl_bufferevent_free_and_close_fd;
1630 	return 0;
1631 }
1632 
1633 int
protossl_setup_src_new_bev_ssl_accepting(pxy_conn_ctx_t * ctx)1634 protossl_setup_src_new_bev_ssl_accepting(pxy_conn_ctx_t *ctx)
1635 {
1636 	ctx->src.bev = bufferevent_openssl_filter_new(ctx->thr->evbase, ctx->src.bev, ctx->src.ssl,
1637 			BUFFEREVENT_SSL_ACCEPTING, BEV_OPT_DEFER_CALLBACKS);
1638 	if (!ctx->src.bev) {
1639 		log_err_level_printf(LOG_CRIT, "Error creating src bufferevent\n");
1640 		SSL_free(ctx->src.ssl);
1641 		ctx->src.ssl = NULL;
1642 		pxy_conn_term(ctx, 1);
1643 		return -1;
1644 	}
1645 	ctx->src.free = protossl_bufferevent_free_and_close_fd;
1646 	return 0;
1647 }
1648 
1649 int
protossl_setup_dst_new_bev_ssl_connecting(pxy_conn_ctx_t * ctx)1650 protossl_setup_dst_new_bev_ssl_connecting(pxy_conn_ctx_t *ctx)
1651 {
1652 	ctx->dst.bev = bufferevent_openssl_filter_new(ctx->thr->evbase, ctx->dst.bev, ctx->dst.ssl,
1653 			BUFFEREVENT_SSL_CONNECTING, BEV_OPT_DEFER_CALLBACKS);
1654 	if (!ctx->dst.bev) {
1655 		log_err_level_printf(LOG_CRIT, "Error creating dst bufferevent\n");
1656 		SSL_free(ctx->dst.ssl);
1657 		ctx->dst.ssl = NULL;
1658 		pxy_conn_term(ctx, 1);
1659 		return -1;
1660 	}
1661 	ctx->dst.free = protossl_bufferevent_free_and_close_fd;
1662 	return 0;
1663 }
1664 
1665 int
protossl_setup_dst_new_bev_ssl_connecting_child(pxy_conn_child_ctx_t * ctx)1666 protossl_setup_dst_new_bev_ssl_connecting_child(pxy_conn_child_ctx_t *ctx)
1667 {
1668 	ctx->dst.bev = bufferevent_openssl_filter_new(ctx->conn->thr->evbase, ctx->dst.bev, ctx->dst.ssl,
1669 			BUFFEREVENT_SSL_CONNECTING, BEV_OPT_DEFER_CALLBACKS);
1670 	if (!ctx->dst.bev) {
1671 		log_err_level_printf(LOG_CRIT, "Error creating dst bufferevent\n");
1672 		SSL_free(ctx->dst.ssl);
1673 		ctx->dst.ssl = NULL;
1674 		pxy_conn_term(ctx->conn, 1);
1675 		return -1;
1676 	}
1677 	ctx->dst.free = protossl_bufferevent_free_and_close_fd;
1678 	return 0;
1679 }
1680 
1681 int
protossl_enable_src(pxy_conn_ctx_t * ctx)1682 protossl_enable_src(pxy_conn_ctx_t *ctx)
1683 {
1684 	// @todo The return value of protossl_enable_src() never used, just return?
1685 	int rv;
1686 	if ((rv = protossl_setup_src(ctx)) != 0) {
1687 		// Might have switched to passthrough mode
1688 		return rv;
1689 	}
1690 	bufferevent_setcb(ctx->src.bev, pxy_bev_readcb, pxy_bev_writecb, pxy_bev_eventcb, ctx);
1691 
1692 	// Save the srvdst ssl info for logging
1693 	ctx->sslctx->srvdst_ssl_version = strdup(SSL_get_version(ctx->srvdst.ssl));
1694 	ctx->sslctx->srvdst_ssl_cipher = strdup(SSL_get_cipher(ctx->srvdst.ssl));
1695 
1696 	if (pxy_setup_child_listener(ctx) == -1) {
1697 		return -1;
1698 	}
1699 
1700 	log_finer("Enabling src");
1701 	// Now open the gates
1702 	bufferevent_enable(ctx->src.bev, EV_READ|EV_WRITE);
1703 	return 0;
1704 }
1705 
1706 static void NONNULL(1,2)
protossl_bev_eventcb_connected_dst(struct bufferevent * bev,pxy_conn_ctx_t * ctx)1707 protossl_bev_eventcb_connected_dst(struct bufferevent *bev, pxy_conn_ctx_t *ctx)
1708 {
1709 	log_finest("ENTER");
1710 
1711 	ctx->connected = 1;
1712 	bufferevent_enable(bev, EV_READ|EV_WRITE);
1713 
1714 	protossl_enable_src(ctx);
1715 }
1716 
1717 static void
protossl_bev_eventcb_connected_srvdst(UNUSED struct bufferevent * bev,pxy_conn_ctx_t * ctx)1718 protossl_bev_eventcb_connected_srvdst(UNUSED struct bufferevent *bev, pxy_conn_ctx_t *ctx)
1719 {
1720 	log_finest("ENTER");
1721 
1722 #ifndef WITHOUT_USERAUTH
1723 	pxy_userauth(ctx);
1724 	if (ctx->term || ctx->enomem) {
1725 		return;
1726 	}
1727 #endif /* !WITHOUT_USERAUTH */
1728 
1729 	// Defer any pass or block action until SSL filter application below
1730 	if (pxy_conn_apply_filter(ctx, FILTER_ACTION_PASS | FILTER_ACTION_BLOCK)) {
1731 		// We never reach here, since we defer pass and block actions
1732 		return;
1733 	}
1734 
1735 	// Set src ssl up early to apply SSL filter,
1736 	// this is the last moment we can take divert or split action
1737 	if (protossl_setup_src_ssl(ctx) != 0) {
1738 		return;
1739 	}
1740 
1741 	if (prototcp_setup_dst(ctx) == -1) {
1742 		return;
1743 	}
1744 
1745 	if (ctx->divert) {
1746 		bufferevent_setcb(ctx->dst.bev, pxy_bev_readcb, pxy_bev_writecb, pxy_bev_eventcb, ctx);
1747 		if (bufferevent_socket_connect(ctx->dst.bev, (struct sockaddr *)&ctx->spec->divert_addr, ctx->spec->divert_addrlen) == -1) {
1748 			log_fine("FAILED bufferevent_socket_connect for divert addr");
1749 			pxy_conn_term(ctx, 1);
1750 			return;
1751 		}
1752 	}
1753 }
1754 
1755 static void NONNULL(1,2)
protossl_bev_eventcb_error_srvdst(UNUSED struct bufferevent * bev,pxy_conn_ctx_t * ctx)1756 protossl_bev_eventcb_error_srvdst(UNUSED struct bufferevent *bev, pxy_conn_ctx_t *ctx)
1757 {
1758 	log_fine("ENTER");
1759 
1760 	if (!ctx->connected) {
1761 		log_fine("!ctx->connected");
1762 
1763 		/* the callout to the original destination failed,
1764 		 * e.g. because it asked for client cert auth, so
1765 		 * close the accepted socket and clean up */
1766 		if (((ctx->conn_opts->passthrough && ctx->sslctx->have_sslerr) || (ctx->pass && !ctx->sslctx->have_sslerr))) {
1767 			/* ssl callout failed, fall back to plain TCP passthrough of SSL connection */
1768 			log_err_level_printf(LOG_WARNING, "SSL srvdst connection failed; falling back to passthrough\n");
1769 			ctx->sslctx->have_sslerr = 0;
1770 			protopassthrough_engage(ctx);
1771 			return;
1772 		}
1773 		pxy_conn_term(ctx, 0);
1774 	}
1775 }
1776 
1777 static void NONNULL(1)
protossl_bev_eventcb_dst(struct bufferevent * bev,short events,pxy_conn_ctx_t * ctx)1778 protossl_bev_eventcb_dst(struct bufferevent *bev, short events, pxy_conn_ctx_t *ctx)
1779 {
1780 	if (events & BEV_EVENT_CONNECTED) {
1781 		protossl_bev_eventcb_connected_dst(bev, ctx);
1782 	} else if (events & BEV_EVENT_EOF) {
1783 		prototcp_bev_eventcb_eof_dst(bev, ctx);
1784 	} else if (events & BEV_EVENT_ERROR) {
1785 		prototcp_bev_eventcb_error_dst(bev, ctx);
1786 	}
1787 }
1788 
1789 void
protossl_bev_eventcb_srvdst(struct bufferevent * bev,short events,pxy_conn_ctx_t * ctx)1790 protossl_bev_eventcb_srvdst(struct bufferevent *bev, short events, pxy_conn_ctx_t *ctx)
1791 {
1792 	if (events & BEV_EVENT_CONNECTED) {
1793 		protossl_bev_eventcb_connected_srvdst(bev, ctx);
1794 	} else if (events & BEV_EVENT_EOF) {
1795 		prototcp_bev_eventcb_eof_srvdst(bev, ctx);
1796 	} else if (events & BEV_EVENT_ERROR) {
1797 		protossl_bev_eventcb_error_srvdst(bev, ctx);
1798 	}
1799 }
1800 
1801 void
protossl_bev_eventcb(struct bufferevent * bev,short events,void * arg)1802 protossl_bev_eventcb(struct bufferevent *bev, short events, void *arg)
1803 {
1804 	pxy_conn_ctx_t *ctx = arg;
1805 
1806 	if (events & BEV_EVENT_ERROR) {
1807 		protossl_log_ssl_error(bev, ctx);
1808 	}
1809 
1810 	if (bev == ctx->src.bev) {
1811 		prototcp_bev_eventcb_src(bev, events, ctx);
1812 	} else if (bev == ctx->dst.bev) {
1813 		protossl_bev_eventcb_dst(bev, events, ctx);
1814 	} else if (bev == ctx->srvdst.bev) {
1815 		protossl_bev_eventcb_srvdst(bev, events, ctx);
1816 	} else {
1817 		log_err_printf("protossl_bev_eventcb: UNKWN conn end\n");
1818 	}
1819 }
1820 
1821 void
protossl_bev_eventcb_child(struct bufferevent * bev,short events,void * arg)1822 protossl_bev_eventcb_child(struct bufferevent *bev, short events, void *arg)
1823 {
1824 	pxy_conn_child_ctx_t *ctx = arg;
1825 
1826 	if (events & BEV_EVENT_ERROR) {
1827 		protossl_log_ssl_error(bev, ctx->conn);
1828 	}
1829 
1830 	if (bev == ctx->src.bev) {
1831 		prototcp_bev_eventcb_src_child(bev, events, ctx);
1832 	} else if (bev == ctx->dst.bev) {
1833 		prototcp_bev_eventcb_dst_child(bev, events, ctx);
1834 	} else {
1835 		log_err_printf("protossl_bev_eventcb_child: UNKWN conn end\n");
1836 	}
1837 }
1838 
1839 // @attention Called by thrmgr thread
1840 protocol_t
protossl_setup(pxy_conn_ctx_t * ctx)1841 protossl_setup(pxy_conn_ctx_t *ctx)
1842 {
1843 	ctx->protoctx->proto = PROTO_SSL;
1844 	ctx->protoctx->connectcb = protossl_conn_connect;
1845 	ctx->protoctx->init_conn = protossl_init_conn;
1846 
1847 	ctx->protoctx->bev_eventcb = protossl_bev_eventcb;
1848 
1849 	ctx->protoctx->proto_free = protossl_free;
1850 
1851 	ctx->sslctx = malloc(sizeof(ssl_ctx_t));
1852 	if (!ctx->sslctx) {
1853 		return PROTO_ERROR;
1854 	}
1855 	memset(ctx->sslctx, 0, sizeof(ssl_ctx_t));
1856 
1857 	return PROTO_SSL;
1858 }
1859 
1860 protocol_t
protossl_setup_child(pxy_conn_child_ctx_t * ctx)1861 protossl_setup_child(pxy_conn_child_ctx_t *ctx)
1862 {
1863 	ctx->protoctx->proto = PROTO_SSL;
1864 	ctx->protoctx->connectcb = protossl_connect_child;
1865 
1866 	ctx->protoctx->bev_eventcb = protossl_bev_eventcb_child;
1867 
1868 	return PROTO_SSL;
1869 }
1870 
1871 /* vim: set noet ft=c: */
1872