xref: /netbsd-src/external/mpl/bind/dist/lib/isc/netmgr/tlsstream.c (revision 32d1c65c71fbdb65a012e8392a62a757dd6853e9)
1 /*	$NetBSD: tlsstream.c,v 1.3 2024/09/22 00:14:09 christos Exp $	*/
2 
3 /*
4  * Copyright (C) Internet Systems Consortium, Inc. ("ISC")
5  *
6  * SPDX-License-Identifier: MPL-2.0
7  *
8  * This Source Code Form is subject to the terms of the Mozilla Public
9  * License, v. 2.0. If a copy of the MPL was not distributed with this
10  * file, you can obtain one at https://mozilla.org/MPL/2.0/.
11  *
12  * See the COPYRIGHT file distributed with this work for additional
13  * information regarding copyright ownership.
14  */
15 
16 #include <errno.h>
17 #include <libgen.h>
18 #include <unistd.h>
19 #include <uv.h>
20 
21 #include <openssl/err.h>
22 #include <openssl/ssl.h>
23 
24 #include <isc/atomic.h>
25 #include <isc/buffer.h>
26 #include <isc/condition.h>
27 #include <isc/log.h>
28 #include <isc/magic.h>
29 #include <isc/mem.h>
30 #include <isc/netmgr.h>
31 #include <isc/once.h>
32 #include <isc/quota.h>
33 #include <isc/random.h>
34 #include <isc/refcount.h>
35 #include <isc/region.h>
36 #include <isc/result.h>
37 #include <isc/sockaddr.h>
38 #include <isc/stdtime.h>
39 #include <isc/thread.h>
40 #include <isc/util.h>
41 
42 #include "../openssl_shim.h"
43 #include "netmgr-int.h"
44 #include "uv-compat.h"
45 
46 #define TLS_BUF_SIZE (UINT16_MAX)
47 
48 static isc_result_t
49 tls_error_to_result(const int tls_err, const int tls_state, isc_tls_t *tls) {
50 	switch (tls_err) {
51 	case SSL_ERROR_ZERO_RETURN:
52 		return (ISC_R_EOF);
53 	case SSL_ERROR_SSL:
54 		if (tls != NULL && tls_state < TLS_IO &&
55 		    SSL_get_verify_result(tls) != X509_V_OK)
56 		{
57 			return (ISC_R_TLSBADPEERCERT);
58 		}
59 		return (ISC_R_TLSERROR);
60 	default:
61 		return (ISC_R_UNEXPECTED);
62 	}
63 }
64 
65 static void
66 tls_failed_read_cb(isc_nmsocket_t *sock, const isc_result_t result);
67 
68 static void
69 tls_do_bio(isc_nmsocket_t *sock, isc_region_t *received_data,
70 	   isc__nm_uvreq_t *send_data, bool finish);
71 
72 static void
73 tls_readcb(isc_nmhandle_t *handle, isc_result_t result, isc_region_t *region,
74 	   void *cbarg);
75 
76 static void
77 tls_close_direct(isc_nmsocket_t *sock);
78 
79 static void
80 async_tls_do_bio(isc_nmsocket_t *sock);
81 
82 static void
83 tls_init_listener_tlsctx(isc_nmsocket_t *listener, isc_tlsctx_t *ctx);
84 
85 static void
86 tls_cleanup_listener_tlsctx(isc_nmsocket_t *listener);
87 
88 static isc_tlsctx_t *
89 tls_get_listener_tlsctx(isc_nmsocket_t *listener, const int tid);
90 
91 static void
92 tls_keep_client_tls_session(isc_nmsocket_t *sock);
93 
94 static void
95 tls_try_shutdown(isc_tls_t *tls, const bool quite);
96 
97 /*
98  * The socket is closing, outerhandle has been detached, listener is
99  * inactive, or the netmgr is closing: any operation on it should abort
100  * with ISC_R_CANCELED.
101  */
102 static bool
103 inactive(isc_nmsocket_t *sock) {
104 	return (!isc__nmsocket_active(sock) || atomic_load(&sock->closing) ||
105 		sock->outerhandle == NULL ||
106 		!isc__nmsocket_active(sock->outerhandle->sock) ||
107 		atomic_load(&sock->outerhandle->sock->closing) ||
108 		(sock->listener != NULL &&
109 		 !isc__nmsocket_active(sock->listener)) ||
110 		isc__nm_closing(sock));
111 }
112 
113 static void
114 tls_call_connect_cb(isc_nmsocket_t *sock, isc_nmhandle_t *handle,
115 		    const isc_result_t result) {
116 	if (sock->connect_cb == NULL) {
117 		return;
118 	}
119 	sock->connect_cb(handle, result, sock->connect_cbarg);
120 	if (result != ISC_R_SUCCESS) {
121 		isc__nmsocket_clearcb(handle->sock);
122 	}
123 }
124 
125 static void
126 tls_senddone(isc_nmhandle_t *handle, isc_result_t eresult, void *cbarg) {
127 	isc_nmsocket_tls_send_req_t *send_req =
128 		(isc_nmsocket_tls_send_req_t *)cbarg;
129 	isc_nmsocket_t *tlssock = NULL;
130 	bool finish = send_req->finish;
131 
132 	REQUIRE(VALID_NMHANDLE(handle));
133 	REQUIRE(VALID_NMSOCK(handle->sock));
134 	REQUIRE(VALID_NMSOCK(send_req->tlssock));
135 
136 	tlssock = send_req->tlssock;
137 	send_req->tlssock = NULL;
138 
139 	if (finish) {
140 		tls_try_shutdown(tlssock->tlsstream.tls, true);
141 	}
142 
143 	if (send_req->cb != NULL) {
144 		INSIST(VALID_NMHANDLE(tlssock->statichandle));
145 		send_req->cb(send_req->handle, eresult, send_req->cbarg);
146 		isc_nmhandle_detach(&send_req->handle);
147 		/* The last handle has been just detached: close the underlying
148 		 * socket. */
149 		if (tlssock->statichandle == NULL) {
150 			finish = true;
151 		}
152 	}
153 
154 	/* We are tying to avoid a memory allocation for small write
155 	 * requests. See the mirroring code in the tls_send_outgoing()
156 	 * function. */
157 	if (send_req->data.length > sizeof(send_req->smallbuf)) {
158 		isc_mem_put(handle->sock->mgr->mctx, send_req->data.base,
159 			    send_req->data.length);
160 	} else {
161 		INSIST(&send_req->smallbuf[0] == send_req->data.base);
162 	}
163 	isc_mem_put(handle->sock->mgr->mctx, send_req, sizeof(*send_req));
164 	tlssock->tlsstream.nsending--;
165 
166 	if (finish && eresult == ISC_R_SUCCESS) {
167 		tlssock->tlsstream.reading = false;
168 		isc_nm_cancelread(handle);
169 	} else if (eresult == ISC_R_SUCCESS) {
170 		tls_do_bio(tlssock, NULL, NULL, false);
171 	} else if (eresult != ISC_R_SUCCESS &&
172 		   tlssock->tlsstream.state <= TLS_HANDSHAKE &&
173 		   !tlssock->tlsstream.server)
174 	{
175 		/*
176 		 * We are still waiting for the handshake to complete, but
177 		 * it isn't going to happen. Call the connect callback,
178 		 * passing the error code there.
179 		 *
180 		 * (Note: tls_failed_read_cb() calls the connect
181 		 * rather than the read callback in this case.
182 		 * XXX: clarify?)
183 		 */
184 		tls_failed_read_cb(tlssock, eresult);
185 	}
186 
187 	isc__nmsocket_detach(&tlssock);
188 }
189 
190 static void
191 tls_failed_read_cb(isc_nmsocket_t *sock, const isc_result_t result) {
192 	bool destroy = true;
193 
194 	REQUIRE(VALID_NMSOCK(sock));
195 	REQUIRE(result != ISC_R_SUCCESS);
196 
197 	if (!sock->tlsstream.server &&
198 	    (sock->tlsstream.state == TLS_INIT ||
199 	     sock->tlsstream.state == TLS_HANDSHAKE) &&
200 	    sock->connect_cb != NULL)
201 	{
202 		isc_nmhandle_t *handle = NULL;
203 		INSIST(sock->statichandle == NULL);
204 		handle = isc__nmhandle_get(sock, &sock->peer, &sock->iface);
205 		tls_call_connect_cb(sock, handle, result);
206 		isc__nmsocket_clearcb(sock);
207 		isc_nmhandle_detach(&handle);
208 	} else if (sock->recv_cb != NULL && sock->statichandle != NULL &&
209 		   (sock->recv_read || result == ISC_R_TIMEDOUT))
210 	{
211 		isc__nm_uvreq_t *req = NULL;
212 		INSIST(VALID_NMHANDLE(sock->statichandle));
213 		sock->recv_read = false;
214 		req = isc__nm_uvreq_get(sock->mgr, sock);
215 		req->cb.recv = sock->recv_cb;
216 		req->cbarg = sock->recv_cbarg;
217 		isc_nmhandle_attach(sock->statichandle, &req->handle);
218 		if (result != ISC_R_TIMEDOUT) {
219 			isc__nmsocket_clearcb(sock);
220 		}
221 		isc__nm_readcb(sock, req, result);
222 		if (result == ISC_R_TIMEDOUT &&
223 		    (sock->outerhandle == NULL ||
224 		     isc__nmsocket_timer_running(sock->outerhandle->sock)))
225 		{
226 			destroy = false;
227 		}
228 	}
229 
230 	if (destroy) {
231 		isc__nmsocket_prep_destroy(sock);
232 	}
233 }
234 
235 static void
236 async_tls_do_bio(isc_nmsocket_t *sock) {
237 	isc__netievent_tlsdobio_t *ievent =
238 		isc__nm_get_netievent_tlsdobio(sock->mgr, sock);
239 	isc__nm_enqueue_ievent(&sock->mgr->workers[sock->tid],
240 			       (isc__netievent_t *)ievent);
241 }
242 
243 static int
244 tls_send_outgoing(isc_nmsocket_t *sock, bool finish, isc_nmhandle_t *tlshandle,
245 		  isc_nm_cb_t cb, void *cbarg) {
246 	isc_nmsocket_tls_send_req_t *send_req = NULL;
247 	int pending;
248 	int rv;
249 	size_t len = 0;
250 
251 	if (inactive(sock)) {
252 		if (cb != NULL) {
253 			INSIST(VALID_NMHANDLE(tlshandle));
254 			cb(tlshandle, ISC_R_CANCELED, cbarg);
255 		}
256 		return (0);
257 	}
258 
259 	if (finish) {
260 		tls_try_shutdown(sock->tlsstream.tls, false);
261 		tls_keep_client_tls_session(sock);
262 	}
263 
264 	pending = BIO_pending(sock->tlsstream.bio_out);
265 	if (pending <= 0) {
266 		return (pending);
267 	}
268 
269 	/* TODO Should we keep track of these requests in a list? */
270 	if ((unsigned int)pending > TLS_BUF_SIZE) {
271 		pending = TLS_BUF_SIZE;
272 	}
273 
274 	send_req = isc_mem_get(sock->mgr->mctx, sizeof(*send_req));
275 	*send_req = (isc_nmsocket_tls_send_req_t){ .finish = finish,
276 						   .data.length = pending };
277 
278 	/* Let's try to avoid a memory allocation for small write requests */
279 	if ((size_t)pending > sizeof(send_req->smallbuf)) {
280 		send_req->data.base = isc_mem_get(sock->mgr->mctx, pending);
281 	} else {
282 		send_req->data.base = &send_req->smallbuf[0];
283 	}
284 
285 	isc__nmsocket_attach(sock, &send_req->tlssock);
286 	if (cb != NULL) {
287 		send_req->cb = cb;
288 		send_req->cbarg = cbarg;
289 		isc_nmhandle_attach(tlshandle, &send_req->handle);
290 	}
291 
292 	rv = BIO_read_ex(sock->tlsstream.bio_out, send_req->data.base, pending,
293 			 &len);
294 	/* There's something pending, read must succeed */
295 	RUNTIME_CHECK(rv == 1);
296 
297 	INSIST(VALID_NMHANDLE(sock->outerhandle));
298 
299 	sock->tlsstream.nsending++;
300 	isc_nm_send(sock->outerhandle, &send_req->data, tls_senddone, send_req);
301 
302 	return (pending);
303 }
304 
305 static int
306 tls_process_outgoing(isc_nmsocket_t *sock, bool finish,
307 		     isc__nm_uvreq_t *send_data) {
308 	int pending;
309 
310 	bool received_shutdown = ((SSL_get_shutdown(sock->tlsstream.tls) &
311 				   SSL_RECEIVED_SHUTDOWN) != 0);
312 	bool sent_shutdown = ((SSL_get_shutdown(sock->tlsstream.tls) &
313 			       SSL_SENT_SHUTDOWN) != 0);
314 
315 	if (received_shutdown && !sent_shutdown) {
316 		finish = true;
317 	}
318 
319 	/* Data from TLS to network */
320 	if (send_data != NULL) {
321 		pending = tls_send_outgoing(sock, finish, send_data->handle,
322 					    send_data->cb.send,
323 					    send_data->cbarg);
324 	} else {
325 		pending = tls_send_outgoing(sock, finish, NULL, NULL, NULL);
326 	}
327 
328 	return (pending);
329 }
330 
331 static int
332 tls_try_handshake(isc_nmsocket_t *sock, isc_result_t *presult) {
333 	int rv = 0;
334 	isc_nmhandle_t *tlshandle = NULL;
335 
336 	REQUIRE(sock->tlsstream.state == TLS_HANDSHAKE);
337 
338 	if (SSL_is_init_finished(sock->tlsstream.tls) == 1) {
339 		return (0);
340 	}
341 
342 	rv = SSL_do_handshake(sock->tlsstream.tls);
343 	if (rv == 1) {
344 		isc_result_t result = ISC_R_SUCCESS;
345 		INSIST(SSL_is_init_finished(sock->tlsstream.tls) == 1);
346 		INSIST(sock->statichandle == NULL);
347 		isc__nmsocket_log_tls_session_reuse(sock, sock->tlsstream.tls);
348 		tlshandle = isc__nmhandle_get(sock, &sock->peer, &sock->iface);
349 
350 		if (isc__nm_closing(sock)) {
351 			result = ISC_R_SHUTTINGDOWN;
352 		}
353 
354 		if (sock->tlsstream.server) {
355 			if (isc__nmsocket_closing(sock->listener)) {
356 				result = ISC_R_CANCELED;
357 			} else if (result == ISC_R_SUCCESS) {
358 				result = sock->listener->accept_cb(
359 					tlshandle, result,
360 					sock->listener->accept_cbarg);
361 			}
362 		} else {
363 			tls_call_connect_cb(sock, tlshandle, result);
364 		}
365 		isc_nmhandle_detach(&tlshandle);
366 		sock->tlsstream.state = TLS_IO;
367 
368 		if (presult != NULL) {
369 			*presult = result;
370 		}
371 	}
372 
373 	return (rv);
374 }
375 
376 static bool
377 tls_try_to_close_unused_socket(isc_nmsocket_t *sock) {
378 	if (sock->tlsstream.state > TLS_HANDSHAKE &&
379 	    sock->statichandle == NULL && sock->tlsstream.nsending == 0)
380 	{
381 		/*
382 		 * It seems that no action on the socket has been
383 		 * scheduled on some point after the handshake, let's
384 		 * close the connection.
385 		 */
386 		isc__nmsocket_prep_destroy(sock);
387 		return (true);
388 	}
389 
390 	return (false);
391 }
392 
393 static void
394 tls_do_bio(isc_nmsocket_t *sock, isc_region_t *received_data,
395 	   isc__nm_uvreq_t *send_data, bool finish) {
396 	isc_result_t result = ISC_R_SUCCESS;
397 	int pending, tls_status = SSL_ERROR_NONE;
398 	int rv = 0;
399 	size_t len = 0;
400 	int saved_errno = 0;
401 
402 	REQUIRE(VALID_NMSOCK(sock));
403 	REQUIRE(sock->tid == isc_nm_tid());
404 
405 	/* We will resume read if TLS layer wants us to */
406 	if (sock->tlsstream.reading && sock->outerhandle) {
407 		REQUIRE(VALID_NMHANDLE(sock->outerhandle));
408 		isc_nm_pauseread(sock->outerhandle);
409 	}
410 
411 	/*
412 	 * Clear the TLS error queue so that SSL_get_error() and SSL I/O
413 	 * routine calls will not get affected by prior error statuses.
414 	 *
415 	 * See here:
416 	 * https://www.openssl.org/docs/man3.0/man3/SSL_get_error.html
417 	 *
418 	 * In particular, it mentions the following:
419 	 *
420 	 * The current thread's error queue must be empty before the
421 	 * TLS/SSL I/O operation is attempted, or SSL_get_error() will not
422 	 * work reliably.
423 	 *
424 	 * As we use the result of SSL_get_error() to decide on I/O
425 	 * operations, we need to ensure that it works reliably by
426 	 * cleaning the error queue.
427 	 *
428 	 * The sum of details: https://stackoverflow.com/a/37980911
429 	 */
430 	ERR_clear_error();
431 
432 	if (sock->tlsstream.state == TLS_INIT) {
433 		INSIST(received_data == NULL && send_data == NULL);
434 		if (sock->tlsstream.server) {
435 			SSL_set_accept_state(sock->tlsstream.tls);
436 		} else {
437 			SSL_set_connect_state(sock->tlsstream.tls);
438 		}
439 		sock->tlsstream.state = TLS_HANDSHAKE;
440 		rv = tls_try_handshake(sock, NULL);
441 		INSIST(SSL_is_init_finished(sock->tlsstream.tls) == 0);
442 	} else if (sock->tlsstream.state == TLS_CLOSED) {
443 		return;
444 	} else { /* initialised and doing I/O */
445 		if (received_data != NULL) {
446 			INSIST(send_data == NULL);
447 			rv = BIO_write_ex(sock->tlsstream.bio_in,
448 					  received_data->base,
449 					  received_data->length, &len);
450 			if (rv <= 0 || len != received_data->length) {
451 				result = ISC_R_TLSERROR;
452 #if defined(NETMGR_TRACE) && defined(NETMGR_TRACE_VERBOSE)
453 				saved_errno = errno;
454 #endif
455 				goto error;
456 			}
457 
458 			/*
459 			 * Only after doing the IO we can check whether SSL
460 			 * handshake is done.
461 			 */
462 			if (sock->tlsstream.state == TLS_HANDSHAKE) {
463 				isc_result_t hs_result = ISC_R_UNSET;
464 				rv = tls_try_handshake(sock, &hs_result);
465 				if (sock->tlsstream.state == TLS_IO &&
466 				    hs_result != ISC_R_SUCCESS)
467 				{
468 					/*
469 					 * The accept callback has been called
470 					 * unsuccessfully. Let's try to shut
471 					 * down the TLS connection gracefully.
472 					 */
473 					INSIST(SSL_is_init_finished(
474 						       sock->tlsstream.tls) ==
475 					       1);
476 					finish = true;
477 				}
478 			}
479 		} else if (send_data != NULL) {
480 			INSIST(received_data == NULL);
481 			INSIST(sock->tlsstream.state > TLS_HANDSHAKE);
482 			bool received_shutdown =
483 				((SSL_get_shutdown(sock->tlsstream.tls) &
484 				  SSL_RECEIVED_SHUTDOWN) != 0);
485 			bool sent_shutdown =
486 				((SSL_get_shutdown(sock->tlsstream.tls) &
487 				  SSL_SENT_SHUTDOWN) != 0);
488 			rv = SSL_write_ex(sock->tlsstream.tls,
489 					  send_data->uvbuf.base,
490 					  send_data->uvbuf.len, &len);
491 			if (rv != 1 || len != send_data->uvbuf.len) {
492 				result = received_shutdown || sent_shutdown
493 						 ? ISC_R_CANCELED
494 						 : ISC_R_TLSERROR;
495 				send_data->cb.send(send_data->handle, result,
496 						   send_data->cbarg);
497 				send_data = NULL;
498 				return;
499 			}
500 		}
501 
502 		/* Decrypt and pass data from network to client */
503 		if (sock->tlsstream.state >= TLS_IO && sock->recv_cb != NULL &&
504 		    !atomic_load(&sock->readpaused) &&
505 		    sock->statichandle != NULL && !finish)
506 		{
507 			uint8_t recv_buf[TLS_BUF_SIZE];
508 			INSIST(sock->tlsstream.state > TLS_HANDSHAKE);
509 			while ((rv = SSL_read_ex(sock->tlsstream.tls, recv_buf,
510 						 TLS_BUF_SIZE, &len)) == 1)
511 			{
512 				isc_region_t region;
513 				region = (isc_region_t){ .base = &recv_buf[0],
514 							 .length = len };
515 
516 				INSIST(VALID_NMHANDLE(sock->statichandle));
517 				sock->recv_cb(sock->statichandle, ISC_R_SUCCESS,
518 					      &region, sock->recv_cbarg);
519 				/* The handle could have been detached in
520 				 * sock->recv_cb, making the sock->statichandle
521 				 * nullified (it happens in netmgr.c). If it is
522 				 * the case, then it means that we are not
523 				 * interested in keeping the connection alive
524 				 * anymore. Let's shut down the SSL session,
525 				 * send what we have in the SSL buffers,
526 				 * and close the connection.
527 				 */
528 				if (sock->statichandle == NULL) {
529 					finish = true;
530 					break;
531 				} else if (sock->recv_cb == NULL) {
532 					/*
533 					 * The 'sock->recv_cb' might have been
534 					 * nullified during the call to
535 					 * 'sock->recv_cb'. That could happen,
536 					 * indirectly when wrapping up.
537 					 *
538 					 * In this case, let's close the TLS
539 					 * connection.
540 					 */
541 					finish = true;
542 					break;
543 				} else if (atomic_load(&sock->readpaused)) {
544 					/*
545 					 * Reading has been paused from withing
546 					 * the context of read callback - stop
547 					 * processing incoming data.
548 					 */
549 					break;
550 				}
551 			}
552 		}
553 	}
554 	errno = 0;
555 	tls_status = SSL_get_error(sock->tlsstream.tls, rv);
556 	saved_errno = errno;
557 
558 	/* See "BUGS" section at:
559 	 * https://www.openssl.org/docs/man1.1.1/man3/SSL_get_error.html
560 	 *
561 	 * It is mentioned there that when TLS status equals
562 	 * SSL_ERROR_SYSCALL AND errno == 0 it means that underlying
563 	 * transport layer returned EOF prematurely.  However, we are
564 	 * managing the transport ourselves, so we should just resume
565 	 * reading from the TCP socket.
566 	 *
567 	 * It seems that this case has been handled properly on modern
568 	 * versions of OpenSSL. That being said, the situation goes in
569 	 * line with the manual: it is briefly mentioned there that
570 	 * SSL_ERROR_SYSCALL might be returned not only in a case of
571 	 * low-level errors (like system call failures).
572 	 */
573 	if (tls_status == SSL_ERROR_SYSCALL && saved_errno == 0 &&
574 	    received_data == NULL && send_data == NULL && finish == false)
575 	{
576 		tls_status = SSL_ERROR_WANT_READ;
577 	}
578 
579 	pending = tls_process_outgoing(sock, finish, send_data);
580 	if (pending > 0 && tls_status != SSL_ERROR_SSL) {
581 		/* We'll continue in tls_senddone */
582 		return;
583 	}
584 
585 	switch (tls_status) {
586 	case SSL_ERROR_NONE:
587 	case SSL_ERROR_ZERO_RETURN:
588 		(void)tls_try_to_close_unused_socket(sock);
589 		return;
590 	case SSL_ERROR_WANT_WRITE:
591 		if (sock->tlsstream.nsending == 0) {
592 			/*
593 			 * Launch tls_do_bio asynchronously. If we're sending
594 			 * already the send callback will call it.
595 			 */
596 			async_tls_do_bio(sock);
597 		}
598 		return;
599 	case SSL_ERROR_WANT_READ:
600 		if (tls_try_to_close_unused_socket(sock) ||
601 		    sock->outerhandle == NULL || atomic_load(&sock->readpaused))
602 		{
603 			return;
604 		}
605 
606 		INSIST(VALID_NMHANDLE(sock->outerhandle));
607 
608 		if (sock->tlsstream.reading) {
609 			isc_nm_resumeread(sock->outerhandle);
610 		} else if (sock->tlsstream.state == TLS_HANDSHAKE) {
611 			sock->tlsstream.reading = true;
612 			isc_nm_read(sock->outerhandle, tls_readcb, sock);
613 		}
614 		return;
615 	default:
616 		result = tls_error_to_result(tls_status, sock->tlsstream.state,
617 					     sock->tlsstream.tls);
618 		break;
619 	}
620 
621 error:
622 #if defined(NETMGR_TRACE) && defined(NETMGR_TRACE_VERBOSE)
623 	isc_log_write(isc_lctx, ISC_LOGCATEGORY_GENERAL, ISC_LOGMODULE_NETMGR,
624 		      ISC_LOG_NOTICE,
625 		      "SSL error in BIO: %d %s (errno: %d). Arguments: "
626 		      "received_data: %p, "
627 		      "send_data: %p, finish: %s",
628 		      tls_status, isc_result_totext(result), saved_errno,
629 		      received_data, send_data, finish ? "true" : "false");
630 #endif
631 	tls_failed_read_cb(sock, result);
632 }
633 
634 static void
635 tls_readcb(isc_nmhandle_t *handle, isc_result_t result, isc_region_t *region,
636 	   void *cbarg) {
637 	isc_nmsocket_t *tlssock = (isc_nmsocket_t *)cbarg;
638 
639 	REQUIRE(VALID_NMSOCK(tlssock));
640 	REQUIRE(VALID_NMHANDLE(handle));
641 	REQUIRE(tlssock->tid == isc_nm_tid());
642 
643 	if (result != ISC_R_SUCCESS) {
644 		tls_failed_read_cb(tlssock, result);
645 		return;
646 	}
647 
648 	tls_do_bio(tlssock, region, NULL, false);
649 }
650 
651 static isc_result_t
652 initialize_tls(isc_nmsocket_t *sock, bool server) {
653 	REQUIRE(sock->tid == isc_nm_tid());
654 
655 	sock->tlsstream.bio_in = BIO_new(BIO_s_mem());
656 	if (sock->tlsstream.bio_in == NULL) {
657 		isc_tls_free(&sock->tlsstream.tls);
658 		return (ISC_R_TLSERROR);
659 	}
660 	sock->tlsstream.bio_out = BIO_new(BIO_s_mem());
661 	if (sock->tlsstream.bio_out == NULL) {
662 		BIO_free_all(sock->tlsstream.bio_in);
663 		sock->tlsstream.bio_in = NULL;
664 		isc_tls_free(&sock->tlsstream.tls);
665 		return (ISC_R_TLSERROR);
666 	}
667 
668 	if (BIO_set_mem_eof_return(sock->tlsstream.bio_in, EOF) != 1 ||
669 	    BIO_set_mem_eof_return(sock->tlsstream.bio_out, EOF) != 1)
670 	{
671 		goto error;
672 	}
673 
674 	SSL_set_bio(sock->tlsstream.tls, sock->tlsstream.bio_in,
675 		    sock->tlsstream.bio_out);
676 	sock->tlsstream.server = server;
677 	sock->tlsstream.nsending = 0;
678 	sock->tlsstream.state = TLS_INIT;
679 	return (ISC_R_SUCCESS);
680 error:
681 	isc_tls_free(&sock->tlsstream.tls);
682 	sock->tlsstream.bio_out = sock->tlsstream.bio_in = NULL;
683 	return (ISC_R_TLSERROR);
684 }
685 
686 static isc_result_t
687 tlslisten_acceptcb(isc_nmhandle_t *handle, isc_result_t result, void *cbarg) {
688 	isc_nmsocket_t *tlslistensock = (isc_nmsocket_t *)cbarg;
689 	isc_nmsocket_t *tlssock = NULL;
690 	isc_tlsctx_t *tlsctx = NULL;
691 	int tid;
692 
693 	/* If accept() was unsuccessful we can't do anything */
694 	if (result != ISC_R_SUCCESS) {
695 		return (result);
696 	}
697 
698 	REQUIRE(VALID_NMHANDLE(handle));
699 	REQUIRE(VALID_NMSOCK(handle->sock));
700 	REQUIRE(VALID_NMSOCK(tlslistensock));
701 	REQUIRE(tlslistensock->type == isc_nm_tlslistener);
702 
703 	if (isc__nmsocket_closing(handle->sock) ||
704 	    isc__nmsocket_closing(tlslistensock) ||
705 	    !atomic_load(&tlslistensock->listening))
706 	{
707 		return (ISC_R_CANCELED);
708 	}
709 
710 	/*
711 	 * We need to create a 'wrapper' tlssocket for this connection.
712 	 */
713 	tlssock = isc_mem_get(handle->sock->mgr->mctx, sizeof(*tlssock));
714 	isc__nmsocket_init(tlssock, handle->sock->mgr, isc_nm_tlssocket,
715 			   &handle->sock->iface);
716 	isc__nmsocket_attach(tlslistensock, &tlssock->server);
717 
718 	tid = isc_nm_tid();
719 	/* We need to initialize SSL now to reference SSL_CTX properly */
720 	tlsctx = tls_get_listener_tlsctx(tlslistensock, tid);
721 	RUNTIME_CHECK(tlsctx != NULL);
722 	isc_tlsctx_attach(tlsctx, &tlssock->tlsstream.ctx);
723 	tlssock->tlsstream.tls = isc_tls_create(tlssock->tlsstream.ctx);
724 	if (tlssock->tlsstream.tls == NULL) {
725 		atomic_store(&tlssock->closed, true);
726 		isc_tlsctx_free(&tlssock->tlsstream.ctx);
727 		isc__nmsocket_detach(&tlssock);
728 		return (ISC_R_TLSERROR);
729 	}
730 
731 	tlssock->extrahandlesize = tlslistensock->extrahandlesize;
732 	isc__nmsocket_attach(tlslistensock, &tlssock->listener);
733 	isc_nmhandle_attach(handle, &tlssock->outerhandle);
734 	tlssock->peer = handle->sock->peer;
735 	tlssock->read_timeout = atomic_load(&handle->sock->mgr->init);
736 	tlssock->tid = tid;
737 
738 	/*
739 	 * Hold a reference to tlssock in the TCP socket: it will
740 	 * detached in isc__nm_tls_cleanup_data().
741 	 */
742 	handle->sock->tlsstream.tlssocket = tlssock;
743 
744 	result = initialize_tls(tlssock, true);
745 	RUNTIME_CHECK(result == ISC_R_SUCCESS);
746 	/* TODO: catch failure code, detach tlssock, and log the error */
747 
748 	tls_do_bio(tlssock, NULL, NULL, false);
749 	return (result);
750 }
751 
752 isc_result_t
753 isc_nm_listentls(isc_nm_t *mgr, isc_sockaddr_t *iface,
754 		 isc_nm_accept_cb_t accept_cb, void *accept_cbarg,
755 		 size_t extrahandlesize, int backlog, isc_quota_t *quota,
756 		 SSL_CTX *sslctx, isc_nmsocket_t **sockp) {
757 	isc_result_t result;
758 	isc_nmsocket_t *tlssock = NULL;
759 	isc_nmsocket_t *tsock = NULL;
760 
761 	REQUIRE(VALID_NM(mgr));
762 	if (atomic_load(&mgr->closing)) {
763 		return (ISC_R_SHUTTINGDOWN);
764 	}
765 
766 	tlssock = isc_mem_get(mgr->mctx, sizeof(*tlssock));
767 
768 	isc__nmsocket_init(tlssock, mgr, isc_nm_tlslistener, iface);
769 	tlssock->result = ISC_R_UNSET;
770 	tlssock->accept_cb = accept_cb;
771 	tlssock->accept_cbarg = accept_cbarg;
772 	tlssock->extrahandlesize = extrahandlesize;
773 	tls_init_listener_tlsctx(tlssock, sslctx);
774 	tlssock->tlsstream.tls = NULL;
775 
776 	/*
777 	 * tlssock will be a TLS 'wrapper' around an unencrypted stream.
778 	 * We set tlssock->outer to a socket listening for a TCP connection.
779 	 */
780 	result = isc_nm_listentcp(mgr, iface, tlslisten_acceptcb, tlssock,
781 				  extrahandlesize, backlog, quota,
782 				  &tlssock->outer);
783 	if (result != ISC_R_SUCCESS) {
784 		atomic_store(&tlssock->closed, true);
785 		isc__nmsocket_detach(&tlssock);
786 		return (result);
787 	}
788 
789 	/* wait for listen result */
790 	isc__nmsocket_attach(tlssock->outer, &tsock);
791 	tlssock->result = result;
792 	atomic_store(&tlssock->active, true);
793 	INSIST(tlssock->outer->tlsstream.tlslistener == NULL);
794 	isc__nmsocket_attach(tlssock, &tlssock->outer->tlsstream.tlslistener);
795 	isc__nmsocket_detach(&tsock);
796 	INSIST(result != ISC_R_UNSET);
797 	tlssock->nchildren = tlssock->outer->nchildren;
798 
799 	isc__nmsocket_barrier_init(tlssock);
800 	atomic_init(&tlssock->rchildren, tlssock->nchildren);
801 
802 	if (result == ISC_R_SUCCESS) {
803 		atomic_store(&tlssock->listening, true);
804 		*sockp = tlssock;
805 	}
806 
807 	return (result);
808 }
809 
810 void
811 isc__nm_async_tlssend(isc__networker_t *worker, isc__netievent_t *ev0) {
812 	isc__netievent_tlssend_t *ievent = (isc__netievent_tlssend_t *)ev0;
813 	isc_nmsocket_t *sock = ievent->sock;
814 	isc__nm_uvreq_t *req = ievent->req;
815 
816 	REQUIRE(VALID_UVREQ(req));
817 	REQUIRE(sock->tid == isc_nm_tid());
818 
819 	UNUSED(worker);
820 
821 	ievent->req = NULL;
822 
823 	if (inactive(sock)) {
824 		req->cb.send(req->handle, ISC_R_CANCELED, req->cbarg);
825 		goto done;
826 	}
827 
828 	tls_do_bio(sock, NULL, req, false);
829 done:
830 	isc__nm_uvreq_put(&req, sock);
831 	return;
832 }
833 
834 void
835 isc__nm_tls_send(isc_nmhandle_t *handle, const isc_region_t *region,
836 		 isc_nm_cb_t cb, void *cbarg) {
837 	isc__netievent_tlssend_t *ievent = NULL;
838 	isc__nm_uvreq_t *uvreq = NULL;
839 	isc_nmsocket_t *sock = NULL;
840 
841 	REQUIRE(VALID_NMHANDLE(handle));
842 	REQUIRE(VALID_NMSOCK(handle->sock));
843 
844 	sock = handle->sock;
845 
846 	REQUIRE(sock->type == isc_nm_tlssocket);
847 
848 	uvreq = isc__nm_uvreq_get(sock->mgr, sock);
849 	isc_nmhandle_attach(handle, &uvreq->handle);
850 	uvreq->cb.send = cb;
851 	uvreq->cbarg = cbarg;
852 	uvreq->uvbuf.base = (char *)region->base;
853 	uvreq->uvbuf.len = region->length;
854 
855 	/*
856 	 * We need to create an event and pass it using async channel
857 	 */
858 	ievent = isc__nm_get_netievent_tlssend(sock->mgr, sock, uvreq);
859 	isc__nm_enqueue_ievent(&sock->mgr->workers[sock->tid],
860 			       (isc__netievent_t *)ievent);
861 }
862 
863 void
864 isc__nm_async_tlsstartread(isc__networker_t *worker, isc__netievent_t *ev0) {
865 	isc__netievent_tlsstartread_t *ievent =
866 		(isc__netievent_tlsstartread_t *)ev0;
867 	isc_nmsocket_t *sock = ievent->sock;
868 
869 	REQUIRE(sock->tid == isc_nm_tid());
870 
871 	UNUSED(worker);
872 
873 	tls_do_bio(sock, NULL, NULL, false);
874 }
875 
876 void
877 isc__nm_tls_read(isc_nmhandle_t *handle, isc_nm_recv_cb_t cb, void *cbarg) {
878 	isc__netievent_tlsstartread_t *ievent = NULL;
879 	isc_nmsocket_t *sock = NULL;
880 
881 	REQUIRE(VALID_NMHANDLE(handle));
882 
883 	sock = handle->sock;
884 	REQUIRE(VALID_NMSOCK(sock));
885 	REQUIRE(sock->statichandle == handle);
886 	REQUIRE(sock->tid == isc_nm_tid());
887 	REQUIRE(sock->recv_cb == NULL);
888 
889 	if (inactive(sock)) {
890 		cb(handle, ISC_R_CANCELED, NULL, cbarg);
891 		return;
892 	}
893 
894 	sock->recv_cb = cb;
895 	sock->recv_cbarg = cbarg;
896 	sock->recv_read = true;
897 
898 	ievent = isc__nm_get_netievent_tlsstartread(sock->mgr, sock);
899 	isc__nm_enqueue_ievent(&sock->mgr->workers[sock->tid],
900 			       (isc__netievent_t *)ievent);
901 }
902 
903 void
904 isc__nm_tls_pauseread(isc_nmhandle_t *handle) {
905 	REQUIRE(VALID_NMHANDLE(handle));
906 	REQUIRE(VALID_NMSOCK(handle->sock));
907 
908 	if (atomic_compare_exchange_strong(&handle->sock->readpaused,
909 					   &(bool){ false }, true))
910 	{
911 		if (handle->sock->outerhandle != NULL) {
912 			isc_nm_pauseread(handle->sock->outerhandle);
913 		}
914 	}
915 }
916 
917 void
918 isc__nm_tls_resumeread(isc_nmhandle_t *handle) {
919 	REQUIRE(VALID_NMHANDLE(handle));
920 	REQUIRE(VALID_NMSOCK(handle->sock));
921 
922 	if (!atomic_compare_exchange_strong(&handle->sock->readpaused,
923 					    &(bool){ true }, false))
924 	{
925 		if (inactive(handle->sock)) {
926 			return;
927 		}
928 
929 		async_tls_do_bio(handle->sock);
930 	}
931 }
932 
933 static void
934 tls_close_direct(isc_nmsocket_t *sock) {
935 	REQUIRE(VALID_NMSOCK(sock));
936 	REQUIRE(sock->tid == isc_nm_tid());
937 	/*
938 	 * At this point we're certain that there are no
939 	 * external references, we can close everything.
940 	 */
941 	if (sock->outerhandle != NULL) {
942 		isc_nm_pauseread(sock->outerhandle);
943 		isc__nmsocket_clearcb(sock->outerhandle->sock);
944 		isc_nmhandle_detach(&sock->outerhandle);
945 	}
946 
947 	if (sock->listener != NULL) {
948 		isc__nmsocket_detach(&sock->listener);
949 	}
950 
951 	if (sock->server != NULL) {
952 		isc__nmsocket_detach(&sock->server);
953 	}
954 
955 	/* Further cleanup performed in isc__nm_tls_cleanup_data() */
956 	atomic_store(&sock->closed, true);
957 	atomic_store(&sock->active, false);
958 	sock->tlsstream.state = TLS_CLOSED;
959 }
960 
961 void
962 isc__nm_tls_close(isc_nmsocket_t *sock) {
963 	isc__netievent_tlsclose_t *ievent = NULL;
964 
965 	REQUIRE(VALID_NMSOCK(sock));
966 	REQUIRE(sock->type == isc_nm_tlssocket);
967 
968 	if (!atomic_compare_exchange_strong(&sock->closing, &(bool){ false },
969 					    true))
970 	{
971 		return;
972 	}
973 
974 	ievent = isc__nm_get_netievent_tlsclose(sock->mgr, sock);
975 	isc__nm_maybe_enqueue_ievent(&sock->mgr->workers[sock->tid],
976 				     (isc__netievent_t *)ievent);
977 }
978 
979 void
980 isc__nm_async_tlsclose(isc__networker_t *worker, isc__netievent_t *ev0) {
981 	isc__netievent_tlsclose_t *ievent = (isc__netievent_tlsclose_t *)ev0;
982 	isc_nmsocket_t *sock = ievent->sock;
983 
984 	REQUIRE(ievent->sock->tid == isc_nm_tid());
985 
986 	UNUSED(worker);
987 
988 	tls_close_direct(sock);
989 }
990 
991 void
992 isc__nm_tls_stoplistening(isc_nmsocket_t *sock) {
993 	REQUIRE(VALID_NMSOCK(sock));
994 	REQUIRE(sock->type == isc_nm_tlslistener);
995 
996 	isc__nmsocket_stop(sock);
997 }
998 
999 static void
1000 tcp_connected(isc_nmhandle_t *handle, isc_result_t result, void *cbarg);
1001 
1002 void
1003 isc_nm_tlsconnect(isc_nm_t *mgr, isc_sockaddr_t *local, isc_sockaddr_t *peer,
1004 		  isc_nm_cb_t cb, void *cbarg, isc_tlsctx_t *ctx,
1005 		  isc_tlsctx_client_session_cache_t *client_sess_cache,
1006 		  unsigned int timeout, size_t extrahandlesize) {
1007 	isc_nmsocket_t *nsock = NULL;
1008 #if defined(NETMGR_TRACE) && defined(NETMGR_TRACE_VERBOSE)
1009 	fprintf(stderr, "TLS: isc_nm_tlsconnect(): in net thread: %s\n",
1010 		isc__nm_in_netthread() ? "yes" : "no");
1011 #endif /* NETMGR_TRACE */
1012 
1013 	REQUIRE(VALID_NM(mgr));
1014 
1015 	if (atomic_load(&mgr->closing)) {
1016 		cb(NULL, ISC_R_SHUTTINGDOWN, cbarg);
1017 		return;
1018 	}
1019 
1020 	nsock = isc_mem_get(mgr->mctx, sizeof(*nsock));
1021 	isc__nmsocket_init(nsock, mgr, isc_nm_tlssocket, local);
1022 	nsock->extrahandlesize = extrahandlesize;
1023 	nsock->result = ISC_R_UNSET;
1024 	nsock->connect_cb = cb;
1025 	nsock->connect_cbarg = cbarg;
1026 	nsock->connect_timeout = timeout;
1027 	isc_tlsctx_attach(ctx, &nsock->tlsstream.ctx);
1028 	atomic_init(&nsock->client, true);
1029 	if (client_sess_cache != NULL) {
1030 		INSIST(isc_tlsctx_client_session_cache_getctx(
1031 			       client_sess_cache) == ctx);
1032 		isc_tlsctx_client_session_cache_attach(
1033 			client_sess_cache, &nsock->tlsstream.client_sess_cache);
1034 	}
1035 
1036 	isc_nm_tcpconnect(mgr, local, peer, tcp_connected, nsock,
1037 			  nsock->connect_timeout, 0);
1038 }
1039 
1040 static void
1041 tcp_connected(isc_nmhandle_t *handle, isc_result_t result, void *cbarg) {
1042 	isc_nmsocket_t *tlssock = (isc_nmsocket_t *)cbarg;
1043 	isc_nmhandle_t *tlshandle = NULL;
1044 
1045 	REQUIRE(VALID_NMSOCK(tlssock));
1046 
1047 	tlssock->tid = isc_nm_tid();
1048 	if (result != ISC_R_SUCCESS) {
1049 		goto error;
1050 	}
1051 
1052 	INSIST(VALID_NMHANDLE(handle));
1053 
1054 	tlssock->iface = handle->sock->iface;
1055 	tlssock->peer = handle->sock->peer;
1056 	if (isc__nm_closing(tlssock)) {
1057 		result = ISC_R_SHUTTINGDOWN;
1058 		goto error;
1059 	}
1060 
1061 	/*
1062 	 * We need to initialize SSL now to reference SSL_CTX properly.
1063 	 */
1064 	tlssock->tlsstream.tls = isc_tls_create(tlssock->tlsstream.ctx);
1065 	if (tlssock->tlsstream.tls == NULL) {
1066 		result = ISC_R_TLSERROR;
1067 		goto error;
1068 	}
1069 
1070 	result = initialize_tls(tlssock, false);
1071 	if (result != ISC_R_SUCCESS) {
1072 		goto error;
1073 	}
1074 	tlssock->peer = isc_nmhandle_peeraddr(handle);
1075 	isc_nmhandle_attach(handle, &tlssock->outerhandle);
1076 	atomic_store(&tlssock->active, true);
1077 
1078 	if (tlssock->tlsstream.client_sess_cache != NULL) {
1079 		isc_tlsctx_client_session_cache_reuse_sockaddr(
1080 			tlssock->tlsstream.client_sess_cache, &tlssock->peer,
1081 			tlssock->tlsstream.tls);
1082 	}
1083 
1084 	/*
1085 	 * Hold a reference to tlssock in the TCP socket: it will
1086 	 * detached in isc__nm_tls_cleanup_data().
1087 	 */
1088 	handle->sock->tlsstream.tlssocket = tlssock;
1089 
1090 	tls_do_bio(tlssock, NULL, NULL, false);
1091 	return;
1092 error:
1093 	tlshandle = isc__nmhandle_get(tlssock, NULL, NULL);
1094 	atomic_store(&tlssock->closed, true);
1095 	tls_call_connect_cb(tlssock, tlshandle, result);
1096 	isc_nmhandle_detach(&tlshandle);
1097 	isc__nmsocket_detach(&tlssock);
1098 }
1099 
1100 static void
1101 tls_cancelread(isc_nmsocket_t *sock) {
1102 	if (!inactive(sock) && sock->tlsstream.state == TLS_IO) {
1103 		tls_do_bio(sock, NULL, NULL, true);
1104 	} else if (sock->outerhandle != NULL) {
1105 		sock->tlsstream.reading = false;
1106 		isc_nm_cancelread(sock->outerhandle);
1107 	}
1108 }
1109 
1110 void
1111 isc__nm_tls_cancelread(isc_nmhandle_t *handle) {
1112 	isc_nmsocket_t *sock = NULL;
1113 	isc__netievent_tlscancel_t *ievent = NULL;
1114 
1115 	REQUIRE(VALID_NMHANDLE(handle));
1116 
1117 	sock = handle->sock;
1118 
1119 	REQUIRE(sock->type == isc_nm_tlssocket);
1120 
1121 	if (sock->tid == isc_nm_tid()) {
1122 		tls_cancelread(sock);
1123 	} else {
1124 		ievent = isc__nm_get_netievent_tlscancel(sock->mgr, sock,
1125 							 handle);
1126 		isc__nm_enqueue_ievent(&sock->mgr->workers[sock->tid],
1127 				       (isc__netievent_t *)ievent);
1128 	}
1129 }
1130 
1131 void
1132 isc__nm_async_tlscancel(isc__networker_t *worker, isc__netievent_t *ev0) {
1133 	isc__netievent_tlscancel_t *ievent = (isc__netievent_tlscancel_t *)ev0;
1134 	isc_nmsocket_t *sock = ievent->sock;
1135 
1136 	REQUIRE(VALID_NMSOCK(sock));
1137 	REQUIRE(worker->id == sock->tid);
1138 	REQUIRE(sock->tid == isc_nm_tid());
1139 
1140 	UNUSED(worker);
1141 	tls_cancelread(sock);
1142 }
1143 
1144 void
1145 isc__nm_async_tlsdobio(isc__networker_t *worker, isc__netievent_t *ev0) {
1146 	isc__netievent_tlsdobio_t *ievent = (isc__netievent_tlsdobio_t *)ev0;
1147 
1148 	UNUSED(worker);
1149 
1150 	tls_do_bio(ievent->sock, NULL, NULL, false);
1151 }
1152 
1153 void
1154 isc__nm_tls_cleanup_data(isc_nmsocket_t *sock) {
1155 	if (sock->type == isc_nm_tcplistener &&
1156 	    sock->tlsstream.tlslistener != NULL)
1157 	{
1158 		isc__nmsocket_detach(&sock->tlsstream.tlslistener);
1159 	} else if (sock->type == isc_nm_tlslistener) {
1160 		tls_cleanup_listener_tlsctx(sock);
1161 	} else if (sock->type == isc_nm_tlssocket) {
1162 		if (sock->tlsstream.tls != NULL) {
1163 			/*
1164 			 * Let's shut down the TLS session properly so that
1165 			 * the session will remain resumable, if required.
1166 			 */
1167 			tls_try_shutdown(sock->tlsstream.tls, true);
1168 			tls_keep_client_tls_session(sock);
1169 			isc_tls_free(&sock->tlsstream.tls);
1170 			/* These are destroyed when we free SSL */
1171 			sock->tlsstream.bio_out = NULL;
1172 			sock->tlsstream.bio_in = NULL;
1173 		}
1174 		if (sock->tlsstream.ctx != NULL) {
1175 			isc_tlsctx_free(&sock->tlsstream.ctx);
1176 		}
1177 		if (sock->tlsstream.client_sess_cache != NULL) {
1178 			INSIST(atomic_load(&sock->client));
1179 			isc_tlsctx_client_session_cache_detach(
1180 				&sock->tlsstream.client_sess_cache);
1181 		}
1182 	} else if (sock->type == isc_nm_tcpsocket &&
1183 		   sock->tlsstream.tlssocket != NULL)
1184 	{
1185 		/*
1186 		 * The TLS socket can't be destroyed until its underlying TCP
1187 		 * socket is, to avoid possible use-after-free errors.
1188 		 */
1189 		isc__nmsocket_detach(&sock->tlsstream.tlssocket);
1190 	}
1191 }
1192 
1193 void
1194 isc__nm_tls_cleartimeout(isc_nmhandle_t *handle) {
1195 	isc_nmsocket_t *sock = NULL;
1196 
1197 	REQUIRE(VALID_NMHANDLE(handle));
1198 	REQUIRE(VALID_NMSOCK(handle->sock));
1199 	REQUIRE(handle->sock->type == isc_nm_tlssocket);
1200 
1201 	sock = handle->sock;
1202 	if (sock->outerhandle != NULL) {
1203 		INSIST(VALID_NMHANDLE(sock->outerhandle));
1204 		isc_nmhandle_cleartimeout(sock->outerhandle);
1205 	}
1206 }
1207 
1208 void
1209 isc__nm_tls_settimeout(isc_nmhandle_t *handle, uint32_t timeout) {
1210 	isc_nmsocket_t *sock = NULL;
1211 
1212 	REQUIRE(VALID_NMHANDLE(handle));
1213 	REQUIRE(VALID_NMSOCK(handle->sock));
1214 	REQUIRE(handle->sock->type == isc_nm_tlssocket);
1215 
1216 	sock = handle->sock;
1217 	if (sock->outerhandle != NULL) {
1218 		INSIST(VALID_NMHANDLE(sock->outerhandle));
1219 		isc_nmhandle_settimeout(sock->outerhandle, timeout);
1220 	}
1221 }
1222 
1223 void
1224 isc__nmhandle_tls_keepalive(isc_nmhandle_t *handle, bool value) {
1225 	isc_nmsocket_t *sock = NULL;
1226 
1227 	REQUIRE(VALID_NMHANDLE(handle));
1228 	REQUIRE(VALID_NMSOCK(handle->sock));
1229 	REQUIRE(handle->sock->type == isc_nm_tlssocket);
1230 
1231 	sock = handle->sock;
1232 	if (sock->outerhandle != NULL) {
1233 		INSIST(VALID_NMHANDLE(sock->outerhandle));
1234 
1235 		isc_nmhandle_keepalive(sock->outerhandle, value);
1236 	}
1237 }
1238 
1239 void
1240 isc__nmhandle_tls_setwritetimeout(isc_nmhandle_t *handle,
1241 				  uint64_t write_timeout) {
1242 	isc_nmsocket_t *sock = NULL;
1243 
1244 	REQUIRE(VALID_NMHANDLE(handle));
1245 	REQUIRE(VALID_NMSOCK(handle->sock));
1246 	REQUIRE(handle->sock->type == isc_nm_tlssocket);
1247 
1248 	sock = handle->sock;
1249 	if (sock->outerhandle != NULL) {
1250 		INSIST(VALID_NMHANDLE(sock->outerhandle));
1251 
1252 		isc_nmhandle_setwritetimeout(sock->outerhandle, write_timeout);
1253 	}
1254 }
1255 
1256 const char *
1257 isc__nm_tls_verify_tls_peer_result_string(const isc_nmhandle_t *handle) {
1258 	isc_nmsocket_t *sock = NULL;
1259 
1260 	REQUIRE(VALID_NMHANDLE(handle));
1261 	REQUIRE(VALID_NMSOCK(handle->sock));
1262 	REQUIRE(handle->sock->type == isc_nm_tlssocket);
1263 
1264 	sock = handle->sock;
1265 	if (sock->tlsstream.tls == NULL) {
1266 		return (NULL);
1267 	}
1268 
1269 	return (isc_tls_verify_peer_result_string(sock->tlsstream.tls));
1270 }
1271 
1272 static void
1273 tls_init_listener_tlsctx(isc_nmsocket_t *listener, isc_tlsctx_t *ctx) {
1274 	size_t nlisteners;
1275 
1276 	REQUIRE(VALID_NM(listener->mgr));
1277 	REQUIRE(ctx != NULL);
1278 
1279 	nlisteners = (size_t)listener->mgr->nlisteners;
1280 	INSIST(nlisteners > 0);
1281 
1282 	listener->tlsstream.listener_tls_ctx = isc_mem_get(
1283 		listener->mgr->mctx, sizeof(isc_tlsctx_t *) * nlisteners);
1284 	listener->tlsstream.n_listener_tls_ctx = nlisteners;
1285 	for (size_t i = 0; i < nlisteners; i++) {
1286 		listener->tlsstream.listener_tls_ctx[i] = NULL;
1287 		isc_tlsctx_attach(ctx,
1288 				  &listener->tlsstream.listener_tls_ctx[i]);
1289 	}
1290 }
1291 
1292 static void
1293 tls_cleanup_listener_tlsctx(isc_nmsocket_t *listener) {
1294 	REQUIRE(VALID_NM(listener->mgr));
1295 
1296 	if (listener->tlsstream.listener_tls_ctx == NULL) {
1297 		return;
1298 	}
1299 
1300 	for (size_t i = 0; i < listener->tlsstream.n_listener_tls_ctx; i++) {
1301 		isc_tlsctx_free(&listener->tlsstream.listener_tls_ctx[i]);
1302 	}
1303 	isc_mem_put(listener->mgr->mctx, listener->tlsstream.listener_tls_ctx,
1304 		    sizeof(isc_tlsctx_t *) *
1305 			    listener->tlsstream.n_listener_tls_ctx);
1306 	listener->tlsstream.n_listener_tls_ctx = 0;
1307 }
1308 
1309 static isc_tlsctx_t *
1310 tls_get_listener_tlsctx(isc_nmsocket_t *listener, const int tid) {
1311 	REQUIRE(VALID_NM(listener->mgr));
1312 	REQUIRE(tid >= 0);
1313 
1314 	if (listener->tlsstream.listener_tls_ctx == NULL) {
1315 		return (NULL);
1316 	}
1317 
1318 	return (listener->tlsstream.listener_tls_ctx[tid]);
1319 }
1320 
1321 void
1322 isc__nm_async_tls_set_tlsctx(isc_nmsocket_t *listener, isc_tlsctx_t *tlsctx,
1323 			     const int tid) {
1324 	REQUIRE(tid >= 0);
1325 
1326 	isc_tlsctx_free(&listener->tlsstream.listener_tls_ctx[tid]);
1327 	isc_tlsctx_attach(tlsctx, &listener->tlsstream.listener_tls_ctx[tid]);
1328 }
1329 
1330 static void
1331 tls_keep_client_tls_session(isc_nmsocket_t *sock) {
1332 	/*
1333 	 * Ensure that the isc_tls_t is being accessed from
1334 	 * within the worker thread the socket is bound to.
1335 	 */
1336 	REQUIRE(sock->tid == isc_nm_tid());
1337 	if (sock->tlsstream.client_sess_cache != NULL &&
1338 	    sock->tlsstream.client_session_saved == false)
1339 	{
1340 		INSIST(atomic_load(&sock->client));
1341 		isc_tlsctx_client_session_cache_keep_sockaddr(
1342 			sock->tlsstream.client_sess_cache, &sock->peer,
1343 			sock->tlsstream.tls);
1344 		sock->tlsstream.client_session_saved = true;
1345 	}
1346 }
1347 
1348 static void
1349 tls_try_shutdown(isc_tls_t *tls, const bool force) {
1350 	if (force) {
1351 		(void)SSL_set_shutdown(tls, SSL_SENT_SHUTDOWN);
1352 	} else if ((SSL_get_shutdown(tls) & SSL_SENT_SHUTDOWN) == 0) {
1353 		(void)SSL_shutdown(tls);
1354 	}
1355 }
1356