diff options
| author | Garrett D'Amore <garrett@damore.org> | 2024-12-12 17:55:48 -0800 |
|---|---|---|
| committer | Garrett D'Amore <garrett@damore.org> | 2024-12-12 17:55:48 -0800 |
| commit | 81f5d3c6268ff91ee9c36c4cb34f6f9bfd54740d (patch) | |
| tree | f9f21aa66bd22cfd95ae0c4b8abe57036c8fce0d /src/platform/posix/posix_tcpconn.c | |
| parent | 371eedeeb6fafe628ae89b9ad2690fa3d6a57e8a (diff) | |
| download | nng-81f5d3c6268ff91ee9c36c4cb34f6f9bfd54740d.tar.gz nng-81f5d3c6268ff91ee9c36c4cb34f6f9bfd54740d.tar.bz2 nng-81f5d3c6268ff91ee9c36c4cb34f6f9bfd54740d.zip | |
streams: add explicit stop functions
This allows us to explicitly stop streams, dialers, and listeners,
before we start tearing down things. This hopefully will be useful
in resolving use-after-free bugs in http, tls, and websockets.
The new functions are not yet documented, but they are
nng_stream_stop, nng_stream_dialer_stop, and nng_stream_listener_stop.
They should be called after close, and before free. The close
functions now close without blocking, but the stop function is
allowed to block.
Diffstat (limited to 'src/platform/posix/posix_tcpconn.c')
| -rw-r--r-- | src/platform/posix/posix_tcpconn.c | 25 |
1 files changed, 21 insertions, 4 deletions
diff --git a/src/platform/posix/posix_tcpconn.c b/src/platform/posix/posix_tcpconn.c index 74b3371b..ce5243b0 100644 --- a/src/platform/posix/posix_tcpconn.c +++ b/src/platform/posix/posix_tcpconn.c @@ -10,6 +10,7 @@ // #include "core/nng_impl.h" +#include "platform/posix/posix_pollq.h" #include <errno.h> #include <fcntl.h> @@ -199,16 +200,30 @@ tcp_close(void *arg) nni_mtx_unlock(&c->mtx); } +static void +tcp_stop(void *arg) +{ + nni_tcp_conn *c = arg; + nni_posix_pfd *pfd; + tcp_close(c); + + nni_mtx_lock(&c->mtx); + pfd = c->pfd; + c->pfd = NULL; + nni_mtx_unlock(&c->mtx); + + if (pfd != NULL) { + nni_posix_pfd_fini(pfd); + } +} + // tcp_fini may block briefly waiting for the pollq thread. // To get that out of our context, we simply reap this. static void tcp_fini(void *arg) { nni_tcp_conn *c = arg; - tcp_close(c); - if (c->pfd != NULL) { - nni_posix_pfd_fini(c->pfd); - } + tcp_stop(c); nni_mtx_fini(&c->mtx); if (c->dialer != NULL) { @@ -221,6 +236,7 @@ static nni_reap_list tcp_reap_list = { .rl_offset = offsetof(nni_tcp_conn, reap), .rl_func = tcp_fini, }; + static void tcp_free(void *arg) { @@ -454,6 +470,7 @@ nni_posix_tcp_alloc(nni_tcp_conn **cp, nni_tcp_dialer *d) nni_aio_list_init(&c->writeq); c->stream.s_free = tcp_free; + c->stream.s_stop = tcp_stop; c->stream.s_close = tcp_close; c->stream.s_recv = tcp_recv; c->stream.s_send = tcp_send; |
