diff options
Diffstat (limited to 'src')
24 files changed, 323 insertions, 244 deletions
diff --git a/src/core/pipe.c b/src/core/pipe.c index db2c4d41..baa2d6f9 100644 --- a/src/core/pipe.c +++ b/src/core/pipe.c @@ -421,7 +421,7 @@ nni_pipe_bump_error(nni_pipe *p, int err) } char * -nni_pipe_peer_addr(nni_pipe *p, char buf[NNG_MAXADDRSTRLEN]) +nni_pipe_peer_str_addr(nni_pipe *p, char buf[NNG_MAXADDRSTRLEN]) { nng_sockaddr sa; size_t sz = sizeof(sa); @@ -431,6 +431,17 @@ nni_pipe_peer_addr(nni_pipe *p, char buf[NNG_MAXADDRSTRLEN]) return (buf); } +char * +nni_pipe_self_str_addr(nni_pipe *p, char buf[NNG_MAXADDRSTRLEN]) +{ + nng_sockaddr sa; + size_t sz = sizeof(sa); + sa.s_family = AF_UNSPEC; + nni_pipe_getopt(p, NNG_OPT_LOCADDR, &sa, &sz, NNI_TYPE_SOCKADDR); + nng_str_sockaddr(&sa, buf, NNG_MAXADDRSTRLEN); + return (buf); +} + nng_err nni_pipe_peer_cert(nni_pipe *p, nng_tls_cert **certp) { diff --git a/src/core/pipe.h b/src/core/pipe.h index 4ed61660..6ef3c206 100644 --- a/src/core/pipe.h +++ b/src/core/pipe.h @@ -69,7 +69,8 @@ extern void nni_pipe_bump_rx(nni_pipe *, size_t); extern void nni_pipe_bump_tx(nni_pipe *, size_t); extern void nni_pipe_bump_error(nni_pipe *, int); -extern char *nni_pipe_peer_addr(nni_pipe *p, char buf[NNG_MAXADDRSTRLEN]); +extern char *nni_pipe_peer_str_addr(nni_pipe *p, char buf[NNG_MAXADDRSTRLEN]); +extern char *nni_pipe_self_str_addr(nni_pipe *p, char buf[NNG_MAXADDRSTRLEN]); extern int nni_pipe_alloc_dialer(void **, nni_dialer *); extern int nni_pipe_alloc_listener(void **, nni_listener *); diff --git a/src/core/socket.c b/src/core/socket.c index 7112014e..a7633c9e 100644 --- a/src/core/socket.c +++ b/src/core/socket.c @@ -1301,7 +1301,8 @@ dialer_start_pipe(nni_dialer *d, nni_pipe *p) char addr[NNG_MAXADDRSTRLEN]; nng_log_debug("NNG-PIPEREJECT", "Pipe on socket<%u> from %s rejected by callback", - nni_pipe_sock_id(p), nni_pipe_peer_addr(p, addr)); + nni_pipe_sock_id(p), + nni_pipe_peer_str_addr(p, addr)); } nni_pipe_rele(p); return; @@ -1323,10 +1324,13 @@ dialer_start_pipe(nni_dialer *d, nni_pipe *p) #endif nni_pipe_run_cb(p, NNG_PIPE_EV_ADD_POST); if (nng_log_get_level() >= NNG_LOG_DEBUG) { - char addr[NNG_MAXADDRSTRLEN]; + char peer_addr[NNG_MAXADDRSTRLEN]; + char self_addr[NNG_MAXADDRSTRLEN]; nng_log_debug("NNG-CONNECT", - "Connected pipe<%u> on socket<%u> to %s", nni_pipe_id(p), - nni_sock_id(s), nni_pipe_peer_addr(p, addr)); + "Connected pipe<%u> on socket<%u> at %s to %s", + nni_pipe_id(p), nni_sock_id(s), + nni_pipe_self_str_addr(p, self_addr), + nni_pipe_peer_str_addr(p, peer_addr)); } nni_pipe_rele(p); } @@ -1429,10 +1433,13 @@ listener_start_pipe(nni_listener *l, nni_pipe *p) #endif nni_pipe_run_cb(p, NNG_PIPE_EV_ADD_POST); if (nng_log_get_level() >= NNG_LOG_DEBUG) { - char addr[NNG_MAXADDRSTRLEN]; + char peer_addr[NNG_MAXADDRSTRLEN]; + char self_addr[NNG_MAXADDRSTRLEN]; nng_log_debug("NNG-ACCEPT", - "Accepted pipe<%u> on socket<%u> from %s", nni_pipe_id(p), - nni_sock_id(s), nni_pipe_peer_addr(p, addr)); + "Accepted pipe<%u> on socket<%u> at %s from %s", + nni_pipe_id(p), nni_sock_id(s), + nni_pipe_self_str_addr(p, self_addr), + nni_pipe_peer_str_addr(p, peer_addr)); } // the socket now "owns" the pipe, and a pipe close should immediately diff --git a/src/core/stream.c b/src/core/stream.c index 5a5159df..6c7ad5f0 100644 --- a/src/core/stream.c +++ b/src/core/stream.c @@ -133,6 +133,15 @@ void nng_stream_free(nng_stream *s) { if (s != NULL) { + // These are mandatory - we have checks here for completeness. + NNI_ASSERT(s->s_close != NULL); + NNI_ASSERT(s->s_stop != NULL); + NNI_ASSERT(s->s_send != NULL); + NNI_ASSERT(s->s_recv != NULL); + NNI_ASSERT(s->s_free != NULL); + NNI_ASSERT(s->s_peer_addr != NULL); + NNI_ASSERT(s->s_self_addr != NULL); + s->s_free(s); } } @@ -155,6 +164,15 @@ nng_err nni_stream_get( nng_stream *s, const char *nm, void *data, size_t *szp, nni_type t) { + // TODO: eventually this needs die + if ((strcmp(nm, NNG_OPT_REMADDR) == 0) || + (strcmp(nm, NNG_OPT_LOCADDR) == 0)) { + if (t != NNI_TYPE_SOCKADDR) { + return (NNG_EBADTYPE); + } + return (nng_stream_get_addr(s, nm, (nng_sockaddr *) data)); + } + return (s->s_get(s, nm, data, szp, t)); } @@ -382,7 +400,29 @@ nng_stream_get_ms(nng_stream *s, const char *n, nng_duration *v) nng_err nng_stream_get_addr(nng_stream *s, const char *n, nng_sockaddr *v) { - return (nni_stream_get(s, n, v, NULL, NNI_TYPE_SOCKADDR)); + const nng_sockaddr *sap; + int rv = NNG_ENOTSUP; + if (strcmp(n, NNG_OPT_LOCADDR) == 0) { + rv = nng_stream_self_addr(s, &sap); + } else if (strcmp(n, NNG_OPT_REMADDR) == 0) { + rv = nng_stream_peer_addr(s, &sap); + } + if (rv == NNG_OK) { + *v = *sap; + } + return (rv); +} + +nng_err +nng_stream_self_addr(nng_stream *s, const nng_sockaddr **sa) +{ + return (s->s_self_addr(s, &*sa)); +} + +nng_err +nng_stream_peer_addr(nng_stream *s, const nng_sockaddr **sa) +{ + return (s->s_peer_addr(s, &*sa)); } nng_err diff --git a/src/core/stream.h b/src/core/stream.h index a9a17ec1..3c87e9c5 100644 --- a/src/core/stream.h +++ b/src/core/stream.h @@ -50,6 +50,8 @@ struct nng_stream { void (*s_send)(void *, nng_aio *); nng_err (*s_get)(void *, const char *, void *, size_t *, nni_type); nng_err (*s_set)(void *, const char *, const void *, size_t, nni_type); + nng_err (*s_peer_addr)(void *, const nng_sockaddr **); + nng_err (*s_self_addr)(void *, const nng_sockaddr **); nng_err (*s_peer_cert)(void *, nng_tls_cert **); }; diff --git a/src/platform/posix/posix_ipc.h b/src/platform/posix/posix_ipc.h index f1aa412d..7a48beaf 100644 --- a/src/platform/posix/posix_ipc.h +++ b/src/platform/posix/posix_ipc.h @@ -45,7 +45,7 @@ struct nni_ipc_dialer { #endif }; -extern int nni_posix_ipc_alloc( +extern nng_err nni_posix_ipc_alloc( nni_ipc_conn **, nni_sockaddr *, nni_ipc_dialer *, int); extern void nni_posix_ipc_dialer_rele(nni_ipc_dialer *); extern void nni_posix_ipc_dialer_cb(void *arg, unsigned events); diff --git a/src/platform/posix/posix_ipcconn.c b/src/platform/posix/posix_ipcconn.c index fd3cdbd8..11bd03d8 100644 --- a/src/platform/posix/posix_ipcconn.c +++ b/src/platform/posix/posix_ipcconn.c @@ -300,6 +300,14 @@ ipc_recv(void *arg, nni_aio *aio) } static nng_err +ipc_sock_addr(void *arg, const nng_sockaddr **sap) +{ + ipc_conn *c = arg; + *sap = &c->sa; + return (NNG_OK); +} + +static nng_err ipc_get_peer_uid(void *arg, void *buf, size_t *szp, nni_type t) { ipc_conn *c = arg; @@ -367,13 +375,6 @@ ipc_get_peer_pid(void *arg, void *buf, size_t *szp, nni_type t) return (nni_copyout_int(id, buf, szp, t)); } -static nng_err -ipc_get_addr(void *arg, void *buf, size_t *szp, nni_type t) -{ - ipc_conn *c = arg; - return (nni_copyout_sockaddr(&c->sa, buf, szp, t)); -} - static void ipc_stop(void *arg) { @@ -413,14 +414,6 @@ ipc_free(void *arg) static const nni_option ipc_options[] = { { - .o_name = NNG_OPT_LOCADDR, - .o_get = ipc_get_addr, - }, - { - .o_name = NNG_OPT_REMADDR, - .o_get = ipc_get_addr, - }, - { .o_name = NNG_OPT_IPC_PEER_PID, .o_get = ipc_get_peer_pid, }, @@ -455,7 +448,7 @@ ipc_set(void *arg, const char *name, const void *val, size_t sz, nni_type t) return (nni_setopt(ipc_options, name, c, val, sz, t)); } -int +nng_err nni_posix_ipc_alloc( nni_ipc_conn **cp, nni_sockaddr *sa, nni_ipc_dialer *d, int fd) { @@ -465,16 +458,18 @@ nni_posix_ipc_alloc( return (NNG_ENOMEM); } - c->closed = false; - c->dialer = d; - c->stream.s_free = ipc_free; - c->stream.s_close = ipc_close; - c->stream.s_stop = ipc_stop; - c->stream.s_send = ipc_send; - c->stream.s_recv = ipc_recv; - c->stream.s_get = ipc_get; - c->stream.s_set = ipc_set; - c->sa = *sa; + c->closed = false; + c->dialer = d; + c->stream.s_free = ipc_free; + c->stream.s_close = ipc_close; + c->stream.s_stop = ipc_stop; + c->stream.s_send = ipc_send; + c->stream.s_recv = ipc_recv; + c->stream.s_get = ipc_get; + c->stream.s_set = ipc_set; + c->stream.s_self_addr = ipc_sock_addr, + c->stream.s_peer_addr = ipc_sock_addr; + c->sa = *sa; nni_mtx_init(&c->mtx); nni_aio_list_init(&c->readq); diff --git a/src/platform/posix/posix_sockfd.c b/src/platform/posix/posix_sockfd.c index 6762987b..43225e7e 100644 --- a/src/platform/posix/posix_sockfd.c +++ b/src/platform/posix/posix_sockfd.c @@ -328,15 +328,6 @@ sfd_recv(void *arg, nni_aio *aio) } static nng_err -sfd_get_addr(void *arg, void *buf, size_t *szp, nni_type t) -{ - NNI_ARG_UNUSED(arg); - nng_sockaddr sa; - sa.s_family = NNG_AF_UNSPEC; - return (nni_copyout_sockaddr(&sa, buf, szp, t)); -} - -static nng_err sfd_get_peer_uid(void *arg, void *buf, size_t *szp, nni_type t) { nni_sfd_conn *c = arg; @@ -406,14 +397,6 @@ sfd_get_peer_pid(void *arg, void *buf, size_t *szp, nni_type t) static const nni_option sfd_options[] = { { - .o_name = NNG_OPT_LOCADDR, - .o_get = sfd_get_addr, - }, - { - .o_name = NNG_OPT_REMADDR, - .o_get = sfd_get_addr, - }, - { .o_name = NNG_OPT_PEER_PID, .o_get = sfd_get_peer_pid, }, @@ -448,6 +431,15 @@ sfd_set(void *arg, const char *name, const void *buf, size_t sz, nni_type t) return (nni_setopt(sfd_options, name, c, buf, sz, t)); } +static nng_err +sfd_addr(void *arg, const nng_sockaddr **sap) +{ + static nng_sockaddr sa = { .s_family = NNG_AF_UNSPEC }; + NNI_ARG_UNUSED(arg); + *sap = &sa; + return (NNG_OK); +} + nng_err nni_sfd_conn_alloc(nni_sfd_conn **cp, int fd) { @@ -464,13 +456,15 @@ nni_sfd_conn_alloc(nni_sfd_conn **cp, int fd) nni_aio_list_init(&c->readq); nni_aio_list_init(&c->writeq); - c->stream.s_free = sfd_free; - c->stream.s_close = sfd_close; - c->stream.s_stop = sfd_stop; - c->stream.s_recv = sfd_recv; - c->stream.s_send = sfd_send; - c->stream.s_get = sfd_get; - c->stream.s_set = sfd_set; + c->stream.s_free = sfd_free; + c->stream.s_close = sfd_close; + c->stream.s_stop = sfd_stop; + c->stream.s_recv = sfd_recv; + c->stream.s_send = sfd_send; + c->stream.s_get = sfd_get; + c->stream.s_set = sfd_set; + c->stream.s_peer_addr = sfd_addr; + c->stream.s_self_addr = sfd_addr; *cp = c; return (NNG_OK); diff --git a/src/platform/posix/posix_tcp.h b/src/platform/posix/posix_tcp.h index 3b61d7da..20325841 100644 --- a/src/platform/posix/posix_tcp.h +++ b/src/platform/posix/posix_tcp.h @@ -1,5 +1,5 @@ // -// Copyright 2024 Staysail Systems, Inc. <info@staysail.tech> +// Copyright 2025 Staysail Systems, Inc. <info@staysail.tech> // Copyright 2018 Capitar IT Group BV <info@capitar.com> // Copyright 2018 Devolutions <info@devolutions.net> // @@ -26,6 +26,8 @@ struct nni_tcp_conn { nni_aio *dial_aio; nni_tcp_dialer *dialer; nni_reap_node reap; + nng_sockaddr peer; + nng_sockaddr self; }; extern int nni_posix_tcp_alloc(nni_tcp_conn **, nni_tcp_dialer *, int); diff --git a/src/platform/posix/posix_tcpconn.c b/src/platform/posix/posix_tcpconn.c index 674e3f46..43dfb4e4 100644 --- a/src/platform/posix/posix_tcpconn.c +++ b/src/platform/posix/posix_tcpconn.c @@ -333,41 +333,19 @@ tcp_recv(void *arg, nni_aio *aio) } static nng_err -tcp_get_peername(void *arg, void *buf, size_t *szp, nni_type t) +tcp_get_peer_addr(void *arg, const nng_sockaddr **addr) { - nni_tcp_conn *c = arg; - struct sockaddr_storage ss; - socklen_t len = sizeof(ss); - int fd = nni_posix_pfd_fd(&c->pfd); - nng_err rv; - nng_sockaddr sa; - - if (getpeername(fd, (void *) &ss, &len) != 0) { - return (nni_plat_errno(errno)); - } - if ((rv = nni_posix_sockaddr2nn(&sa, &ss, len)) == NNG_OK) { - rv = nni_copyout_sockaddr(&sa, buf, szp, t); - } - return (rv); + nni_tcp_conn *c = arg; + *addr = &c->peer; + return (NNG_OK); } static nng_err -tcp_get_sockname(void *arg, void *buf, size_t *szp, nni_type t) +tcp_get_self_addr(void *arg, const nng_sockaddr **addr) { - nni_tcp_conn *c = arg; - struct sockaddr_storage ss; - socklen_t len = sizeof(ss); - int fd = nni_posix_pfd_fd(&c->pfd); - int rv; - nng_sockaddr sa; - - if (getsockname(fd, (void *) &ss, &len) != 0) { - return (nni_plat_errno(errno)); - } - if ((rv = nni_posix_sockaddr2nn(&sa, &ss, len)) == NNG_OK) { - rv = nni_copyout_sockaddr(&sa, buf, szp, t); - } - return (rv); + nni_tcp_conn *c = arg; + *addr = &c->self; + return (NNG_OK); } static nng_err @@ -402,14 +380,6 @@ tcp_get_keepalive(void *arg, void *buf, size_t *szp, nni_type t) static const nni_option tcp_options[] = { { - .o_name = NNG_OPT_REMADDR, - .o_get = tcp_get_peername, - }, - { - .o_name = NNG_OPT_LOCADDR, - .o_get = tcp_get_sockname, - }, - { .o_name = NNG_OPT_TCP_NODELAY, .o_get = tcp_get_nodelay, }, @@ -452,13 +422,15 @@ nni_posix_tcp_alloc(nni_tcp_conn **cp, nni_tcp_dialer *d, int fd) nni_aio_list_init(&c->writeq); nni_posix_pfd_init(&c->pfd, fd, tcp_cb, c); - 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; - c->stream.s_get = tcp_get; - c->stream.s_set = tcp_set; + 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; + c->stream.s_get = tcp_get; + c->stream.s_set = tcp_set; + c->stream.s_peer_addr = tcp_get_peer_addr; + c->stream.s_self_addr = tcp_get_self_addr; *cp = c; return (0); @@ -467,9 +439,19 @@ nni_posix_tcp_alloc(nni_tcp_conn **cp, nni_tcp_dialer *d, int fd) void nni_posix_tcp_start(nni_tcp_conn *c, int nodelay, int keepalive) { + int fd = nni_posix_pfd_fd(&c->pfd); // Configure the initial socket options. - (void) setsockopt(nni_posix_pfd_fd(&c->pfd), IPPROTO_TCP, TCP_NODELAY, - &nodelay, sizeof(int)); - (void) setsockopt(nni_posix_pfd_fd(&c->pfd), SOL_SOCKET, SO_KEEPALIVE, - &keepalive, sizeof(int)); + (void) setsockopt(fd, IPPROTO_TCP, TCP_NODELAY, &nodelay, sizeof(int)); + (void) setsockopt( + fd, SOL_SOCKET, SO_KEEPALIVE, &keepalive, sizeof(int)); + + struct sockaddr_storage ss; + socklen_t len = sizeof(ss); + + // Get this info now so we can avoid system calls later. + (void) getpeername(fd, (void *) &ss, &len); + nni_posix_sockaddr2nn(&c->peer, &ss, len); + + (void) getsockname(fd, (void *) &ss, &len); + nni_posix_sockaddr2nn(&c->self, &ss, len); } diff --git a/src/platform/windows/win_ipcconn.c b/src/platform/windows/win_ipcconn.c index 45235387..a5ef16a6 100644 --- a/src/platform/windows/win_ipcconn.c +++ b/src/platform/windows/win_ipcconn.c @@ -9,8 +9,8 @@ // found online at https://opensource.org/licenses/MIT. // -#include "core/aio.h" -#include "core/nng_impl.h" +#include "../../core/nng_impl.h" +#include "win_impl.h" #include "win_ipc.h" @@ -276,7 +276,7 @@ ipc_send_cb(nni_win_io *io, int rv, size_t num) } static void -ipc_send_cancel(nni_aio *aio, void *arg, int rv) +ipc_send_cancel(nni_aio *aio, void *arg, nng_err rv) { ipc_conn *c = arg; nni_mtx_lock(&c->mtx); @@ -388,12 +388,6 @@ ipc_free(void *arg) } static nng_err -ipc_conn_get_addr(void *c, void *buf, size_t *szp, nni_opt_type t) -{ - return (nni_copyout_sockaddr(&(CONN(c))->sa, buf, szp, t)); -} - -static nng_err ipc_conn_get_peer_pid(void *c, void *buf, size_t *szp, nni_opt_type t) { ULONG id; @@ -415,14 +409,6 @@ ipc_conn_get_peer_pid(void *c, void *buf, size_t *szp, nni_opt_type t) static const nni_option ipc_conn_options[] = { { - .o_name = NNG_OPT_LOCADDR, - .o_get = ipc_conn_get_addr, - }, - { - .o_name = NNG_OPT_REMADDR, - .o_get = ipc_conn_get_addr, - }, - { .o_name = NNG_OPT_IPC_PEER_PID, .o_get = ipc_conn_get_peer_pid, }, @@ -445,6 +431,14 @@ ipc_get(void *arg, const char *nm, void *val, size_t *szp, nni_opt_type t) return (nni_getopt(ipc_conn_options, nm, c, val, szp, t)); } +static nng_err +ipc_addr(void *arg, const nng_sockaddr **sap) +{ + ipc_conn *c = arg; + *sap = &c->sa; + return (NNG_OK); +} + int nni_win_ipc_init( nng_stream **connp, HANDLE p, const nng_sockaddr *sa, bool dialer) @@ -459,15 +453,17 @@ nni_win_ipc_init( nni_cv_init(&c->cv, &c->mtx); nni_aio_list_init(&c->recv_aios); nni_aio_list_init(&c->send_aios); - c->dialer = dialer; - c->sa = *sa; - c->stream.s_free = ipc_free; - c->stream.s_close = ipc_close; - c->stream.s_stop = ipc_stop; - c->stream.s_send = ipc_send; - c->stream.s_recv = ipc_recv; - c->stream.s_get = ipc_get; - c->stream.s_set = ipc_set; + c->dialer = dialer; + c->sa = *sa; + c->stream.s_free = ipc_free; + c->stream.s_close = ipc_close; + c->stream.s_stop = ipc_stop; + c->stream.s_send = ipc_send; + c->stream.s_recv = ipc_recv; + c->stream.s_get = ipc_get; + c->stream.s_set = ipc_set; + c->stream.s_self_addr = ipc_addr; + c->stream.s_peer_addr = ipc_addr; nni_win_io_init(&c->recv_io, ipc_recv_cb, c); nni_win_io_init(&c->send_io, ipc_send_cb, c); diff --git a/src/platform/windows/win_ipclisten.c b/src/platform/windows/win_ipclisten.c index 3bb71c7d..07c69507 100644 --- a/src/platform/windows/win_ipclisten.c +++ b/src/platform/windows/win_ipclisten.c @@ -9,7 +9,7 @@ // found online at https://opensource.org/licenses/MIT. // -#include "core/nng_impl.h" +#include "../../core/nng_impl.h" #include "win_ipc.h" @@ -158,7 +158,7 @@ ipc_listener_set_sec_desc(void *arg, void *desc) return (NNG_OK); } -static int +static nng_err ipc_listener_get_addr(void *arg, void *buf, size_t *szp, nni_type t) { ipc_listener *l = arg; @@ -175,7 +175,7 @@ static const nni_option ipc_listener_options[] = { }, }; -static int +static nng_err ipc_listener_set( void *arg, const char *name, const void *buf, size_t sz, nni_type t) { @@ -183,7 +183,7 @@ ipc_listener_set( return (nni_setopt(ipc_listener_options, name, l, buf, sz, t)); } -static int +static nng_err ipc_listener_get( void *arg, const char *name, void *buf, size_t *szp, nni_type t) { diff --git a/src/platform/windows/win_resolv.c b/src/platform/windows/win_resolv.c index 50b030da..3ccbf982 100644 --- a/src/platform/windows/win_resolv.c +++ b/src/platform/windows/win_resolv.c @@ -31,7 +31,7 @@ static nni_mtx resolv_mtx; static nni_cv resolv_cv; static void -resolv_cancel(nni_aio *aio, void *arg, int rv) +resolv_cancel(nni_aio *aio, void *arg, nng_err rv) { nni_resolv_item *item = arg; diff --git a/src/platform/windows/win_tcp.c b/src/platform/windows/win_tcp.c index 42667dea..006c99e8 100644 --- a/src/platform/windows/win_tcp.c +++ b/src/platform/windows/win_tcp.c @@ -12,7 +12,6 @@ #ifdef NNG_PLATFORM_WINDOWS -#include <malloc.h> #include <stdio.h> static LPFN_ACCEPTEX acceptex; diff --git a/src/platform/windows/win_tcp.h b/src/platform/windows/win_tcp.h index ec8ab80c..698160b2 100644 --- a/src/platform/windows/win_tcp.h +++ b/src/platform/windows/win_tcp.h @@ -1,5 +1,5 @@ // -// Copyright 2024 Staysail Systems, Inc. <info@staysail.tech> +// Copyright 2025 Staysail Systems, Inc. <info@staysail.tech> // Copyright 2018 Capitar IT Group BV <info@capitar.com> // Copyright 2019 Devolutions <info@devolutions.net> // @@ -14,30 +14,30 @@ // This header file is private to the TCP support for Windows. -#include "core/nng_impl.h" +#include "../../core/nng_impl.h" struct nni_tcp_conn { - nng_stream ops; - SOCKET s; - nni_win_io recv_io; - nni_win_io send_io; - nni_win_io conn_io; - nni_list recv_aios; - nni_list send_aios; - nni_aio *conn_aio; - SOCKADDR_STORAGE sockname; - SOCKADDR_STORAGE peername; - nni_tcp_dialer *dialer; - void *listener; - int recv_rv; - int send_rv; - int conn_rv; - bool closed; - char buf[512]; // to hold acceptex results - bool sending; - bool recving; - nni_mtx mtx; - nni_cv cv; + nng_stream ops; + SOCKET s; + nni_win_io recv_io; + nni_win_io send_io; + nni_win_io conn_io; + nni_list recv_aios; + nni_list send_aios; + nni_aio *conn_aio; + nng_sockaddr sockname; + nng_sockaddr peername; + nni_tcp_dialer *dialer; + void *listener; + int recv_rv; + int send_rv; + int conn_rv; + bool closed; + char buf[512]; // to hold acceptex results + bool sending; + bool recving; + nni_mtx mtx; + nni_cv cv; }; extern int nni_win_tcp_init(nni_tcp_conn **, SOCKET); diff --git a/src/platform/windows/win_tcpconn.c b/src/platform/windows/win_tcpconn.c index 102700ec..dae6b58d 100644 --- a/src/platform/windows/win_tcpconn.c +++ b/src/platform/windows/win_tcpconn.c @@ -9,11 +9,10 @@ // found online at https://opensource.org/licenses/MIT. // -#include "core/nng_impl.h" +#include "../../core/nng_impl.h" #include "win_tcp.h" -#include <malloc.h> #include <stdio.h> static void @@ -180,7 +179,7 @@ tcp_send_start(nni_tcp_conn *c) } static void -tcp_send_cancel(nni_aio *aio, void *arg, int rv) +tcp_send_cancel(nni_aio *aio, void *arg, nng_err rv) { nni_tcp_conn *c = arg; nni_mtx_lock(&c->mtx); @@ -263,30 +262,6 @@ tcp_close(void *arg) } static nng_err -tcp_get_peername(void *arg, void *buf, size_t *szp, nni_type t) -{ - nni_tcp_conn *c = arg; - nng_sockaddr sa; - - if (nni_win_sockaddr2nn(&sa, &c->peername, sizeof(c->peername)) < 0) { - return (NNG_EADDRINVAL); - } - return (nni_copyout_sockaddr(&sa, buf, szp, t)); -} - -static nng_err -tcp_get_sockname(void *arg, void *buf, size_t *szp, nni_type t) -{ - nni_tcp_conn *c = arg; - nng_sockaddr sa; - - if (nni_win_sockaddr2nn(&sa, &c->sockname, sizeof(c->sockname)) < 0) { - return (NNG_EADDRINVAL); - } - return (nni_copyout_sockaddr(&sa, buf, szp, t)); -} - -static nng_err tcp_get_nodelay(void *arg, void *buf, size_t *szp, nni_type t) { nni_tcp_conn *c = arg; @@ -314,16 +289,24 @@ tcp_get_keepalive(void *arg, void *buf, size_t *szp, nni_type t) return (nni_copyout_bool(b, buf, szp, t)); } +static nng_err +tcp_self_addr(void *arg, const nng_sockaddr **sap) +{ + nni_tcp_conn *c = arg; + *sap = &c->sockname; + return (NNG_OK); +} + +static nng_err +tcp_peer_addr(void *arg, const nng_sockaddr **sap) +{ + nni_tcp_conn *c = arg; + *sap = &c->peername; + return (NNG_OK); +} + static const nni_option tcp_options[] = { { - .o_name = NNG_OPT_REMADDR, - .o_get = tcp_get_peername, - }, - { - .o_name = NNG_OPT_LOCADDR, - .o_get = tcp_get_sockname, - }, - { .o_name = NNG_OPT_TCP_NODELAY, .o_get = tcp_get_nodelay, }, @@ -336,14 +319,14 @@ static const nni_option tcp_options[] = { }, }; -static int +static nng_err tcp_get(void *arg, const char *name, void *buf, size_t *szp, nni_type t) { nni_tcp_conn *c = arg; return (nni_getopt(tcp_options, name, c, buf, szp, t)); } -static int +static nng_err tcp_set(void *arg, const char *name, const void *buf, size_t sz, nni_type t) { nni_tcp_conn *c = arg; @@ -397,14 +380,16 @@ nni_win_tcp_init(nni_tcp_conn **connp, SOCKET s) nni_cv_init(&c->cv, &c->mtx); nni_aio_list_init(&c->recv_aios); nni_aio_list_init(&c->send_aios); - c->conn_aio = NULL; - c->ops.s_close = tcp_close; - c->ops.s_stop = tcp_stop; - c->ops.s_free = tcp_free; - c->ops.s_send = tcp_send; - c->ops.s_recv = tcp_recv; - c->ops.s_get = tcp_get; - c->ops.s_set = tcp_set; + c->conn_aio = NULL; + c->ops.s_close = tcp_close; + c->ops.s_stop = tcp_stop; + c->ops.s_free = tcp_free; + c->ops.s_send = tcp_send; + c->ops.s_recv = tcp_recv; + c->ops.s_get = tcp_get; + c->ops.s_set = tcp_set; + c->ops.s_peer_addr = tcp_peer_addr; + c->ops.s_self_addr = tcp_self_addr; nni_win_io_init(&c->recv_io, tcp_recv_cb, c); nni_win_io_init(&c->send_io, tcp_send_cb, c); diff --git a/src/platform/windows/win_tcpdial.c b/src/platform/windows/win_tcpdial.c index 72e4f8a7..a3d64869 100644 --- a/src/platform/windows/win_tcpdial.c +++ b/src/platform/windows/win_tcpdial.c @@ -9,11 +9,10 @@ // found online at https://opensource.org/licenses/MIT. // -#include "core/nng_impl.h" +#include "../../core/nng_impl.h" #include "win_tcp.h" -#include <malloc.h> #include <stdio.h> struct nni_tcp_dialer { @@ -145,8 +144,9 @@ tcp_dial_cb(nni_win_io *io, int rv, size_t cnt) nng_stream_free(&c->ops); nni_aio_finish_error(aio, rv); } else { - DWORD yes = 1; - int len; + DWORD yes = 1; + int len; + SOCKADDR_STORAGE sa; (void) setsockopt(c->s, SOL_SOCKET, SO_UPDATE_CONNECT_CONTEXT, (char *) &yes, sizeof(yes)); @@ -157,8 +157,13 @@ tcp_dial_cb(nni_win_io *io, int rv, size_t cnt) (void) setsockopt( c->s, IPPROTO_TCP, TCP_NODELAY, (char *) &nd, sizeof(nd)); - len = sizeof(SOCKADDR_STORAGE); - (void) getsockname(c->s, (SOCKADDR *) &c->sockname, &len); + len = sizeof(sa); + (void) getsockname(c->s, (SOCKADDR *) &sa, &len); + nni_win_sockaddr2nn(&c->sockname, &sa, len); + + len = sizeof(sa); + (void) getpeername(c->s, (SOCKADDR *) &sa, &len); + nni_win_sockaddr2nn(&c->peername, &sa, len); nni_aio_set_output(aio, 0, c); nni_aio_finish(aio, 0, 0); @@ -169,19 +174,21 @@ void nni_tcp_dial(nni_tcp_dialer *d, const nni_sockaddr *sa, nni_aio *aio) { SOCKET s; - SOCKADDR_STORAGE ss; + SOCKADDR_STORAGE peername; + SOCKADDR_STORAGE sockname; int len; nni_tcp_conn *c; int rv; nni_aio_reset(aio); - if ((len = nni_win_nn2sockaddr(&ss, sa)) <= 0) { + if ((len = nni_win_nn2sockaddr(&peername, sa)) <= 0) { nni_aio_finish_error(aio, NNG_EADDRINVAL); return; } - if ((s = socket(ss.ss_family, SOCK_STREAM, 0)) == INVALID_SOCKET) { + if ((s = socket(peername.ss_family, SOCK_STREAM, 0)) == + INVALID_SOCKET) { nni_aio_finish_error(aio, nni_win_error(GetLastError())); return; } @@ -192,8 +199,6 @@ nni_tcp_dial(nni_tcp_dialer *d, const nni_sockaddr *sa, nni_aio *aio) return; } - c->peername = ss; - nni_win_io_init(&c->conn_io, tcp_dial_cb, c); nni_mtx_lock(&d->mtx); @@ -209,12 +214,13 @@ nni_tcp_dial(nni_tcp_dialer *d, const nni_sockaddr *sa, nni_aio *aio) // same family, unless a different default was requested. if (d->srclen != 0) { len = (int) d->srclen; + memcpy(&sockname, &d->src, len); memcpy(&c->sockname, &d->src, len); } else { - ZeroMemory(&c->sockname, sizeof(c->sockname)); - c->sockname.ss_family = ss.ss_family; + ZeroMemory(&sockname, sizeof(sockname)); + sockname.ss_family = peername.ss_family; } - if (bind(s, (SOCKADDR *) &c->sockname, len) != 0) { + if (bind(s, (SOCKADDR *) &sockname, len) != 0) { rv = nni_win_error(GetLastError()); nni_mtx_unlock(&d->mtx); nng_stream_free(&c->ops); @@ -222,6 +228,8 @@ nni_tcp_dial(nni_tcp_dialer *d, const nni_sockaddr *sa, nni_aio *aio) return; } + nni_win_sockaddr2nn(&c->sockname, &sockname, sizeof(sockname)); + if (!nni_aio_start(aio, tcp_dial_cancel, d)) { nni_mtx_unlock(&d->mtx); nng_stream_free(&c->ops); @@ -234,7 +242,7 @@ nni_tcp_dial(nni_tcp_dialer *d, const nni_sockaddr *sa, nni_aio *aio) // dialing is concurrent. if (!nni_win_connectex( - s, (SOCKADDR *) &c->peername, len, &c->conn_io.olpd)) { + s, (SOCKADDR *) &peername, len, &c->conn_io.olpd)) { if ((rv = GetLastError()) != ERROR_IO_PENDING) { nni_aio_list_remove(aio); nni_mtx_unlock(&d->mtx); diff --git a/src/platform/windows/win_tcplisten.c b/src/platform/windows/win_tcplisten.c index 563cbcf0..0b11104d 100644 --- a/src/platform/windows/win_tcplisten.c +++ b/src/platform/windows/win_tcplisten.c @@ -9,12 +9,10 @@ // found online at https://opensource.org/licenses/MIT. // -#include "core/nng_impl.h" - -#include <malloc.h> #include <stdbool.h> #include <stdio.h> +#include "../../core/nng_impl.h" #include "win_tcp.h" typedef struct tcp_listener { @@ -220,10 +218,12 @@ tcp_accept_cancel(nni_aio *aio, void *arg, nng_err rv) static void tcp_listener_accepted(tcp_listener *l) { - BOOL nd; - BOOL ka; - nni_tcp_conn *c; - nni_aio *aio; + BOOL nd; + BOOL ka; + nni_tcp_conn *c; + nni_aio *aio; + SOCKADDR_STORAGE sockname; + SOCKADDR_STORAGE peername; aio = nni_list_first(&l->aios); c = l->pend_conn; @@ -232,7 +232,9 @@ tcp_listener_accepted(tcp_listener *l) nd = l->nodelay; nni_aio_list_remove(aio); - nni_win_get_acceptex_sockaddrs(c->buf, &c->sockname, &c->peername); + nni_win_get_acceptex_sockaddrs(c->buf, &sockname, &peername); + nni_win_sockaddr2nn(&c->sockname, &sockname, sizeof(sockname)); + nni_win_sockaddr2nn(&c->peername, &peername, sizeof(peername)); (void) setsockopt(c->s, SOL_SOCKET, SO_UPDATE_ACCEPT_CONTEXT, (char *) &l->s, sizeof(l->s)); diff --git a/src/supplemental/http/http_api.h b/src/supplemental/http/http_api.h index 74472f50..ca13bd09 100644 --- a/src/supplemental/http/http_api.h +++ b/src/supplemental/http/http_api.h @@ -72,8 +72,8 @@ extern void nni_http_read_chunks( extern nni_http_req *nni_http_conn_req(nni_http_conn *); extern nni_http_res *nni_http_conn_res(nni_http_conn *); -extern nng_err nni_http_get_addr( - nni_http_conn *, const char *, nng_sockaddr *); +extern nng_err nni_http_peer_addr(nni_http_conn *, const nng_sockaddr **); +extern nng_err nni_http_self_addr(nni_http_conn *, const nng_sockaddr **); // Private to the server. (Used to support session hijacking.) extern void nni_http_conn_set_ctx(nni_http_conn *, void *); diff --git a/src/supplemental/http/http_conn.c b/src/supplemental/http/http_conn.c index ac549649..bb3a0882 100644 --- a/src/supplemental/http/http_conn.c +++ b/src/supplemental/http/http_conn.c @@ -22,6 +22,7 @@ #include "http_api.h" #include "http_msg.h" +#include "nng/nng.h" // We insist that individual headers fit in 8K. // If you need more than that, you need something we can't do. @@ -160,13 +161,15 @@ nni_http_conn_close(nni_http_conn *conn) } nng_err -nni_http_get_addr(nni_http_conn *conn, const char *opt, nng_sockaddr *addrp) +nni_http_peer_addr(nni_http_conn *conn, const nng_sockaddr **sap) { - nng_err rv; - nni_mtx_lock(&conn->mtx); - rv = nng_stream_get_addr(conn->sock, opt, addrp); - nni_mtx_unlock(&conn->mtx); - return (rv); + return nng_stream_peer_addr(conn->sock, sap); +} + +nng_err +nni_http_self_addr(nni_http_conn *conn, const nng_sockaddr **sap) +{ + return nng_stream_self_addr(conn->sock, sap); } // http_buf_pull_up pulls the content of the read buffer back to the diff --git a/src/supplemental/http/http_public.c b/src/supplemental/http/http_public.c index 8c225e5e..edf5e609 100644 --- a/src/supplemental/http/http_public.c +++ b/src/supplemental/http/http_public.c @@ -309,13 +309,23 @@ nng_http_read_response(nng_http *conn, nng_aio *aio) nng_err nng_http_remote_address(nng_http *conn, nng_sockaddr *addrp) { - return (nni_http_get_addr(conn, NNG_OPT_REMADDR, addrp)); + const nng_sockaddr *sap; + nng_err rv; + if ((rv = nni_http_peer_addr(conn, &sap)) == NNG_OK) { + *addrp = *sap; + } + return (rv); } nng_err nng_http_local_address(nng_http *conn, nng_sockaddr *addrp) { - return (nni_http_get_addr(conn, NNG_OPT_LOCADDR, addrp)); + const nng_sockaddr *sap; + nng_err rv; + if ((rv = nni_http_self_addr(conn, &sap)) == NNG_OK) { + *addrp = *sap; + } + return (rv); } nng_err diff --git a/src/supplemental/tls/tls_stream.c b/src/supplemental/tls/tls_stream.c index d3dd9497..169e8fb0 100644 --- a/src/supplemental/tls/tls_stream.c +++ b/src/supplemental/tls/tls_stream.c @@ -143,6 +143,8 @@ tls_stream_conn_cb(void *arg) static nng_err tls_stream_get( void *arg, const char *name, void *buf, size_t *szp, nni_type t); +static nng_err tls_stream_self_addr(void *arg, const nng_sockaddr **); +static nng_err tls_stream_peer_addr(void *arg, const nng_sockaddr **); static nng_err tls_stream_peer_cert(void *arg, nng_tls_cert **); int @@ -168,6 +170,8 @@ nni_tls_stream_alloc(tls_stream **tsp, nng_tls_config *cfg, nng_aio *user_aio) ts->stream.s_send = tls_stream_send; ts->stream.s_recv = tls_stream_recv; ts->stream.s_get = tls_stream_get; + ts->stream.s_self_addr = tls_stream_self_addr; + ts->stream.s_peer_addr = tls_stream_peer_addr; ts->stream.s_peer_cert = tls_stream_peer_cert; nni_aio_init(&ts->conn_aio, tls_stream_conn_cb, ts); @@ -236,3 +240,17 @@ tls_stream_get(void *arg, const char *name, void *buf, size_t *szp, nni_type t) } return (nni_getopt(tls_stream_options, name, ts, buf, szp, t)); } + +static nng_err +tls_stream_self_addr(void *arg, const nng_sockaddr **sap) +{ + tls_stream *ts = arg; + return (nng_stream_self_addr(ts->conn.bio, sap)); +} + +static nng_err +tls_stream_peer_addr(void *arg, const nng_sockaddr **sap) +{ + tls_stream *ts = arg; + return (nng_stream_peer_addr(ts->conn.bio, sap)); +} diff --git a/src/supplemental/websocket/websocket.c b/src/supplemental/websocket/websocket.c index d78c032b..2ff126e3 100644 --- a/src/supplemental/websocket/websocket.c +++ b/src/supplemental/websocket/websocket.c @@ -193,6 +193,8 @@ static void ws_str_send(void *, nng_aio *); static void ws_str_recv(void *, nng_aio *); static nng_err ws_str_get(void *, const char *, void *, size_t *, nni_type); static nng_err ws_str_peer_cert(void *, nng_tls_cert **); +static nng_err ws_str_self_addr(void *, const nng_sockaddr **); +static nng_err ws_str_peer_addr(void *, const nng_sockaddr **); static void ws_listener_close(void *); static void ws_listener_free(void *); @@ -1402,6 +1404,8 @@ ws_init(nni_ws **wsp) ws->ops.s_recv = ws_str_recv; ws->ops.s_get = ws_str_get; ws->ops.s_peer_cert = ws_str_peer_cert; + ws->ops.s_peer_addr = ws_str_peer_addr; + ws->ops.s_self_addr = ws_str_self_addr; ws->fragsize = 1 << 20; // we won't send a frame larger than this *wsp = ws; @@ -2841,3 +2845,17 @@ ws_str_peer_cert(void *arg, nng_tls_cert **certp) nni_mtx_unlock(&ws->mtx); return (nni_http_conn_peer_cert(ws->http, certp)); } + +static nng_err +ws_str_peer_addr(void *arg, const nng_sockaddr **sap) +{ + nni_ws *ws = arg; + return (nni_http_peer_addr(ws->http, sap)); +} + +static nng_err +ws_str_self_addr(void *arg, const nng_sockaddr **sap) +{ + nni_ws *ws = arg; + return (nni_http_self_addr(ws->http, sap)); +} diff --git a/src/supplemental/websocket/websocket_test.c b/src/supplemental/websocket/websocket_test.c index cb502ef4..66c9617e 100644 --- a/src/supplemental/websocket/websocket_test.c +++ b/src/supplemental/websocket/websocket_test.c @@ -131,6 +131,8 @@ test_websocket_conn_props(void) nng_stream_listener *l = NULL; nng_sockaddr sa1; nng_sockaddr sa2; + const nng_sockaddr *sap1; + const nng_sockaddr *sap2; size_t sz; nng_aio *daio = NULL; nng_aio *laio = NULL; @@ -182,11 +184,15 @@ test_websocket_conn_props(void) NUTS_TRUE(c2 != NULL); // Let's compare the peer addresses + NUTS_PASS(nng_stream_self_addr(c1, &sap1)); + NUTS_PASS(nng_stream_peer_addr(c2, &sap2)); NUTS_PASS(nng_stream_get_addr(c1, NNG_OPT_LOCADDR, &sa1)); NUTS_PASS(nng_stream_get_addr(c2, NNG_OPT_REMADDR, &sa2)); NUTS_TRUE(sa1.s_family == sa2.s_family); NUTS_TRUE(sa1.s_in.sa_addr == sa2.s_in.sa_addr); NUTS_TRUE(sa1.s_in.sa_port == sa2.s_in.sa_port); + NUTS_TRUE(memcmp(sap1, &sa1, sizeof(sa1)) == 0); + NUTS_TRUE(memcmp(sap2, &sa2, sizeof(sa2)) == 0); NUTS_PASS(nng_stream_get_addr(c1, NNG_OPT_REMADDR, &sa1)); NUTS_PASS(nng_stream_get_addr(c2, NNG_OPT_LOCADDR, &sa2)); |
