aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/CMakeLists.txt1
-rw-r--r--src/core/platform.h15
-rw-r--r--src/platform/posix/posix_ipcconn.c93
-rw-r--r--src/platform/windows/win_impl.h4
-rw-r--r--src/platform/windows/win_ipc.h38
-rw-r--r--src/platform/windows/win_ipcconn.c48
-rw-r--r--src/platform/windows/win_ipcdial.c17
-rw-r--r--src/platform/windows/win_ipclisten.c13
-rw-r--r--src/platform/windows/win_sockaddr.c5
-rw-r--r--src/supplemental/ipc/CMakeLists.txt16
-rw-r--r--src/supplemental/ipc/ipc.c136
-rw-r--r--src/supplemental/util/options.c4
12 files changed, 341 insertions, 49 deletions
diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt
index c0380a0f..c31539c2 100644
--- a/src/CMakeLists.txt
+++ b/src/CMakeLists.txt
@@ -183,6 +183,7 @@ add_subdirectory(transport/zerotier)
add_subdirectory(supplemental/base64)
add_subdirectory(supplemental/http)
+add_subdirectory(supplemental/ipc)
add_subdirectory(supplemental/sha1)
add_subdirectory(supplemental/tcp)
add_subdirectory(supplemental/tls)
diff --git a/src/core/platform.h b/src/core/platform.h
index 0a0709d1..2b7eb9f1 100644
--- a/src/core/platform.h
+++ b/src/core/platform.h
@@ -1,6 +1,7 @@
//
// Copyright 2018 Staysail Systems, Inc. <info@staysail.tech>
// Copyright 2018 Capitar IT Group BV <info@capitar.com>
+// Copyright 2018 Devolutions <infos@devolutions.net>
//
// This software is supplied under the terms of the MIT License, a
// copy of which should be located in the distribution where this
@@ -375,6 +376,20 @@ extern int nni_ipc_conn_get_peer_pid(nni_ipc_conn *, uint64_t *);
// NB: Only illumos & SunOS systems have the notion of "zones".
extern int nni_ipc_conn_get_peer_zoneid(nni_ipc_conn *, uint64_t *);
+// nni_ipc_conn_setopt is like setsockopt, but uses string names. These
+// are the same names from the IPC transport, generally. There are no
+// options that are generally settable on an IPC connection.
+// NNG_OPT_REMADDR, NNG_OPT_LOCADDR, NNG_OPT_IPC_PERMISSIONS,
+// NNG_OPT_
+extern int nni_ipc_conn_setopt(
+ nni_ipc_conn *, const char *, const void *, size_t);
+
+// nni_ipc_conn_getopt is like getsockopt, but uses string names.
+// We support NNG_OPT_REMADDR and NNG_OPT_LOCADDR (with argument type
+// nng_sockaddr), and on some platforms NNG_OPT_IPC_PEER_[UID,GID,ZONEID]
+// (with type uint64_t.)
+extern int nni_ipc_conn_getopt(nni_ipc_conn *, const char *, void *, size_t *);
+
// nni_ipc_dialer_init creates a new dialer object.
extern int nni_ipc_dialer_init(nni_ipc_dialer **);
diff --git a/src/platform/posix/posix_ipcconn.c b/src/platform/posix/posix_ipcconn.c
index 0dae8bae..595ebe62 100644
--- a/src/platform/posix/posix_ipcconn.c
+++ b/src/platform/posix/posix_ipcconn.c
@@ -1,6 +1,7 @@
//
// Copyright 2018 Staysail Systems, Inc. <info@staysail.tech>
// Copyright 2018 Capitar IT Group BV <info@capitar.com>
+// Copyright 2018 Devolutions <infos@devolutions.net>
//
// This software is supplied under the terms of the MIT License, a
// copy of which should be located in the distribution where this
@@ -10,8 +11,6 @@
#include "core/nng_impl.h"
-#ifdef NNG_PLATFORM_POSIX
-
#include <errno.h>
#include <fcntl.h>
#include <poll.h>
@@ -40,6 +39,8 @@
#include "posix_ipc.h"
+#include <nng/transport/ipc/ipc.h>
+
static void
ipc_conn_dowrite(nni_ipc_conn *c)
{
@@ -464,6 +465,19 @@ nni_ipc_conn_get_peer_pid(nni_ipc_conn *c, uint64_t *pid)
}
int
+nni_ipc_conn_sockname(nni_ipc_conn *c, nni_sockaddr *sa)
+{
+ struct sockaddr_storage ss;
+ socklen_t sslen = sizeof(ss);
+ int fd = nni_posix_pfd_fd(c->pfd);
+
+ if (getsockname(fd, (void *) &ss, &sslen) != 0) {
+ return (nni_plat_errno(errno));
+ }
+ return (nni_posix_sockaddr2nn(sa, &ss));
+}
+
+int
nni_posix_ipc_conn_init(nni_ipc_conn **cp, nni_posix_pfd *pfd)
{
nni_ipc_conn *c;
@@ -502,4 +516,77 @@ nni_ipc_conn_fini(nni_ipc_conn *c)
NNI_FREE_STRUCT(c);
}
-#endif // NNG_PLATFORM_POSIX
+int
+nni_ipc_conn_setopt(
+ nni_ipc_conn *c, const char *name, const void *val, size_t sz)
+{
+ NNI_ARG_UNUSED(c);
+ NNI_ARG_UNUSED(val);
+ NNI_ARG_UNUSED(sz);
+ if ((strcmp(name, NNG_OPT_LOCADDR) == 0) ||
+ (strcmp(name, NNG_OPT_REMADDR) == 0) ||
+ (strcmp(name, NNG_OPT_IPC_PEER_PID) == 0) ||
+ (strcmp(name, NNG_OPT_IPC_PEER_UID) == 0) ||
+ (strcmp(name, NNG_OPT_IPC_PEER_GID) == 0) ||
+ (strcmp(name, NNG_OPT_IPC_PEER_ZONEID) == 0)) {
+ return (NNG_EREADONLY);
+ }
+ return (NNG_ENOTSUP);
+}
+
+int
+nni_ipc_conn_getopt(nni_ipc_conn *c, const char *name, void *val, size_t *szp)
+{
+ int rv;
+ uint64_t *idp = val;
+
+ if ((strcmp(name, NNG_OPT_LOCADDR) == 0) ||
+ (strcmp(name, NNG_OPT_REMADDR) == 0)) {
+ nng_sockaddr *sa = val;
+ if (*szp < sizeof(*sa)) {
+ return (NNG_EINVAL);
+ }
+
+ if ((rv = nni_ipc_conn_sockname(c, sa)) == 0) {
+ *szp = sizeof(*sa);
+ }
+ return (rv);
+ }
+ if (strcmp(name, NNG_OPT_IPC_PEER_PID) == 0) {
+ if (*szp < sizeof(*idp)) {
+ return (NNG_EINVAL);
+ }
+ if ((rv = nni_ipc_conn_get_peer_pid(c, idp)) == 0) {
+ *szp = sizeof(*idp);
+ }
+ return (rv);
+ }
+ if (strcmp(name, NNG_OPT_IPC_PEER_UID) == 0) {
+ if (*szp < sizeof(*idp)) {
+ return (NNG_EINVAL);
+ }
+ if ((rv = nni_ipc_conn_get_peer_uid(c, idp)) == 0) {
+ *szp = sizeof(*idp);
+ }
+ return (rv);
+ }
+ if (strcmp(name, NNG_OPT_IPC_PEER_GID) == 0) {
+ if (*szp < sizeof(*idp)) {
+ return (NNG_EINVAL);
+ }
+ if ((rv = nni_ipc_conn_get_peer_gid(c, idp)) == 0) {
+ *szp = sizeof(*idp);
+ }
+ return (rv);
+ }
+ if (strcmp(name, NNG_OPT_IPC_PEER_ZONEID) == 0) {
+ if (*szp < sizeof(*idp)) {
+ return (NNG_EINVAL);
+ }
+ if ((rv = nni_ipc_conn_get_peer_zoneid(c, idp)) == 0) {
+ *szp = sizeof(*idp);
+ }
+ return (rv);
+ }
+ return (NNG_ENOTSUP);
+}
diff --git a/src/platform/windows/win_impl.h b/src/platform/windows/win_impl.h
index 462e1707..fd4c9343 100644
--- a/src/platform/windows/win_impl.h
+++ b/src/platform/windows/win_impl.h
@@ -11,8 +11,6 @@
#ifndef PLATFORM_WIN_IMPL_H
#define PLATFORM_WIN_IMPL_H
-#ifdef NNG_PLATFORM_WINDOWS
-
#ifndef WIN32_LEAN_AND_MEAN
#define WIN32_LEAN_AND_MEAN
#endif
@@ -106,6 +104,4 @@ extern int nni_win_nn2sockaddr(SOCKADDR_STORAGE *, const nni_sockaddr *);
#define NNG_PLATFORM_DIR_SEP "\\"
-#endif // NNG_PLATFORM_WINDOWS
-
#endif // PLATFORM_WIN_IMPL_H
diff --git a/src/platform/windows/win_ipc.h b/src/platform/windows/win_ipc.h
index 51ce5548..9a4e245a 100644
--- a/src/platform/windows/win_ipc.h
+++ b/src/platform/windows/win_ipc.h
@@ -1,6 +1,7 @@
//
// Copyright 2018 Staysail Systems, Inc. <info@staysail.tech>
// Copyright 2018 Capitar IT Group BV <info@capitar.com>
+// Copyright 2018 Devolutions <infos@devolutions.net>
//
// This software is supplied under the terms of the MIT License, a
// copy of which should be located in the distribution where this
@@ -14,26 +15,27 @@
// This header file is private to the IPC (named pipes) support for Windows.
#include "core/nng_impl.h"
+#include "win_impl.h"
-#ifdef NNG_PLATFORM_WINDOWS
+#define IPC_PIPE_PREFIX "\\\\.\\pipe\\"
struct nni_ipc_conn {
- HANDLE f;
- 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;
- nni_ipc_dialer * dialer;
- nni_ipc_listener *listener;
- int recv_rv;
- int send_rv;
- int conn_rv;
- bool closed;
- nni_mtx mtx;
- nni_cv cv;
- nni_reap_item reap;
+ HANDLE f;
+ 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 sa;
+ bool dialer;
+ int recv_rv;
+ int send_rv;
+ int conn_rv;
+ bool closed;
+ nni_mtx mtx;
+ nni_cv cv;
+ nni_reap_item reap;
};
struct nni_ipc_dialer {
@@ -57,6 +59,4 @@ struct nni_ipc_listener {
extern int nni_win_ipc_conn_init(nni_ipc_conn **, HANDLE);
-#endif // NNG_PLATFORM_WINDOWS
-
#endif // NNG_PLATFORM_WIN_WINIPC_H
diff --git a/src/platform/windows/win_ipcconn.c b/src/platform/windows/win_ipcconn.c
index d4e7f5ac..107ffb9d 100644
--- a/src/platform/windows/win_ipcconn.c
+++ b/src/platform/windows/win_ipcconn.c
@@ -1,6 +1,7 @@
//
// Copyright 2018 Staysail Systems, Inc. <info@staysail.tech>
// Copyright 2018 Capitar IT Group BV <info@capitar.com>
+// Copyright 2018 Devolutions <infos@devolutions.net>
//
// This software is supplied under the terms of the MIT License, a
// copy of which should be located in the distribution where this
@@ -10,12 +11,12 @@
#include "core/nng_impl.h"
-#ifdef NNG_PLATFORM_WINDOWS
-
#include "win_ipc.h"
#include <stdio.h>
+#include <nng/transport/ipc/ipc.h>
+
static void
ipc_recv_start(nni_ipc_conn *c)
{
@@ -385,4 +386,45 @@ nni_ipc_conn_get_peer_pid(nni_ipc_conn *c, uint64_t *pid)
return (0);
}
-#endif // NNG_PLATFORM_WINDOWS
+int
+nni_ipc_conn_setopt(
+ nni_ipc_conn *c, const char *name, const void *val, size_t sz)
+{
+ NNI_ARG_UNUSED(c);
+ NNI_ARG_UNUSED(val);
+ NNI_ARG_UNUSED(sz);
+ if ((strcmp(name, NNG_OPT_LOCADDR) == 0) ||
+ (strcmp(name, NNG_OPT_REMADDR) == 0) ||
+ (strcmp(name, NNG_OPT_IPC_PEER_PID) == 0)) {
+ return (NNG_EREADONLY);
+ }
+ return (NNG_ENOTSUP);
+}
+
+int
+nni_ipc_conn_getopt(nni_ipc_conn *c, const char *name, void *val, size_t *szp)
+{
+ if ((strcmp(name, NNG_OPT_LOCADDR) == 0) ||
+ (strcmp(name, NNG_OPT_REMADDR) == 0)) {
+ if (*szp < sizeof(c->sa)) {
+ return (NNG_EINVAL);
+ }
+
+ memcpy(val, &c->sa, sizeof(c->sa));
+ *szp = sizeof(c->sa);
+ return (0);
+ }
+ if (strcmp(name, NNG_OPT_IPC_PEER_PID) == 0) {
+ int rv;
+ uint64_t *idp = val;
+ if (*szp < sizeof(*idp)) {
+ return (NNG_EINVAL);
+ }
+ if ((rv = nni_ipc_conn_get_peer_pid(c, idp)) == 0) {
+ ;
+ *szp = sizeof(*idp);
+ }
+ return (rv);
+ }
+ return (NNG_ENOTSUP);
+}
diff --git a/src/platform/windows/win_ipcdial.c b/src/platform/windows/win_ipcdial.c
index 67865687..4c3d5c6c 100644
--- a/src/platform/windows/win_ipcdial.c
+++ b/src/platform/windows/win_ipcdial.c
@@ -10,8 +10,6 @@
#include "core/nng_impl.h"
-#ifdef NNG_PLATFORM_WINDOWS
-
#include "win_ipc.h"
#include <stdio.h>
@@ -108,16 +106,21 @@ ipc_dial_thr(void *arg)
nni_list_remove(&d->aios, aio);
nni_aio_set_prov_extra(aio, 0, NULL);
- nni_strfree(path);
if (((rv = nni_win_io_register(f)) != 0) ||
((rv = nni_win_ipc_conn_init(&c, f)) != 0)) {
DisconnectNamedPipe(f);
CloseHandle(f);
nni_aio_finish_error(aio, rv);
+ nni_strfree(path);
continue;
}
- c->dialer = d;
+ c->dialer = true;
+ c->sa.s_ipc.sa_family = NNG_AF_IPC;
+ snprintf(c->sa.s_ipc.sa_path,
+ sizeof(c->sa.s_ipc.sa_path), "%s",
+ path + strlen(IPC_PIPE_PREFIX));
+ nni_strfree(path);
nni_aio_set_output(aio, 0, c);
nni_aio_finish(aio, 0, 0);
}
@@ -169,8 +172,8 @@ nni_ipc_dialer_dial(nni_ipc_dialer *d, const nni_sockaddr *sa, nni_aio *aio)
nni_aio_finish_error(aio, NNG_EADDRINVAL);
return;
}
- if ((rv = nni_asprintf(&path, "\\\\.\\pipe\\%s", sa->s_ipc.sa_path)) !=
- 0) {
+ if ((rv = nni_asprintf(
+ &path, IPC_PIPE_PREFIX "%s", sa->s_ipc.sa_path)) != 0) {
nni_aio_finish_error(aio, rv);
return;
}
@@ -261,5 +264,3 @@ nni_win_ipc_sysfini(void)
nni_cv_fini(&worker->cv);
nni_mtx_fini(&worker->mtx);
}
-
-#endif // NNG_PLATFORM_WINDOWS
diff --git a/src/platform/windows/win_ipclisten.c b/src/platform/windows/win_ipclisten.c
index 0fc1c9fc..d0fd6ef9 100644
--- a/src/platform/windows/win_ipclisten.c
+++ b/src/platform/windows/win_ipclisten.c
@@ -10,8 +10,6 @@
#include "core/nng_impl.h"
-#ifdef NNG_PLATFORM_WINDOWS
-
#include "win_ipc.h"
#include <stdio.h>
@@ -58,8 +56,11 @@ ipc_accept_done(nni_ipc_listener *l, int rv)
nni_aio_finish_error(aio, rv);
return;
}
- l->f = f;
- c->listener = l;
+ l->f = f;
+ c->sa.s_ipc.sa_family = NNG_AF_IPC;
+ snprintf(c->sa.s_ipc.sa_path, sizeof(c->sa.s_ipc.sa_path), "%s",
+ l->path + strlen(IPC_PIPE_PREFIX));
+ c->dialer = false;
nni_aio_set_output(aio, 0, c);
nni_aio_finish(aio, 0, 0);
}
@@ -185,7 +186,7 @@ nni_ipc_listener_listen(nni_ipc_listener *l, const nni_sockaddr *sa)
nni_mtx_unlock(&l->mtx);
return (NNG_ECLOSED);
}
- rv = nni_asprintf(&path, "\\\\.\\pipe\\%s", sa->s_ipc.sa_path);
+ rv = nni_asprintf(&path, IPC_PIPE_PREFIX "%s", sa->s_ipc.sa_path);
if (rv != 0) {
nni_mtx_unlock(&l->mtx);
return (rv);
@@ -292,5 +293,3 @@ nni_ipc_listener_fini(nni_ipc_listener *l)
nni_mtx_fini(&l->mtx);
NNI_FREE_STRUCT(l);
}
-
-#endif // NNG_PLATFORM_WINDOWS
diff --git a/src/platform/windows/win_sockaddr.c b/src/platform/windows/win_sockaddr.c
index fbb960b7..d1fed2c7 100644
--- a/src/platform/windows/win_sockaddr.c
+++ b/src/platform/windows/win_sockaddr.c
@@ -9,8 +9,7 @@
//
#include "core/nng_impl.h"
-
-#ifdef NNG_PLATFORM_WINDOWS
+#include "win_impl.h"
#include <string.h>
@@ -69,5 +68,3 @@ nni_win_sockaddr2nn(nni_sockaddr *sa, const SOCKADDR_STORAGE *ss)
}
return (-1);
}
-
-#endif // NNG_PLATFORM_WINDOWS
diff --git a/src/supplemental/ipc/CMakeLists.txt b/src/supplemental/ipc/CMakeLists.txt
new file mode 100644
index 00000000..691522f0
--- /dev/null
+++ b/src/supplemental/ipc/CMakeLists.txt
@@ -0,0 +1,16 @@
+#
+# Copyright 2018 Capitar IT Group BV <info@capitar.com>
+# Copyright 2018 Staysail Systems, Inc. <info@staysail.tech>
+# Copyright 2018 Devolutions <infos@devolutions.net>
+#
+# This software is supplied under the terms of the MIT License, a
+# copy of which should be located in the distribution where this
+# file was obtained (LICENSE.txt). A copy of the license may also be
+# found online at https://opensource.org/licenses/MIT.
+#
+
+set(_SRCS supplemental/ipc/ipc.c
+ ${PROJECT_SOURCE_DIR}/include/nng/supplemental/ipc/ipc.h
+)
+
+set(NNG_SRCS ${NNG_SRCS} ${_SRCS} PARENT_SCOPE)
diff --git a/src/supplemental/ipc/ipc.c b/src/supplemental/ipc/ipc.c
new file mode 100644
index 00000000..36c18563
--- /dev/null
+++ b/src/supplemental/ipc/ipc.c
@@ -0,0 +1,136 @@
+//
+// Copyright 2018 Staysail Systems, Inc. <info@staysail.tech>
+// Copyright 2018 Capitar IT Group BV <info@capitar.com>
+// Copyright 2018 Devolutions <infos@devolutions.net>
+//
+// This software is supplied under the terms of the MIT License, a
+// copy of which should be located in the distribution where this
+// file was obtained (LICENSE.txt). A copy of the license may also be
+// found online at https://opensource.org/licenses/MIT.
+//
+
+#include <stddef.h>
+#include <stdint.h>
+
+#include <nng/nng.h>
+#include <nng/supplemental/ipc/ipc.h>
+
+#include "core/nng_impl.h"
+
+// This is our "public" IPC API. This allows applications to access
+// basic IPC functions, using our AIO framework. Most applications will
+// not need this.
+
+// We treat nng_ipc as nni_ipc_conn, nng_ipc_dialer as nni_ipc_dialer,
+// and nng_ipc_listener as nni_ipc_listener. We cast through void to
+// provide isolation of the names in a way that makes the compiler happy.
+// It turns out we can pretty much just wrap the platform API for IPC that
+// we have already created.
+
+void
+nng_ipc_close(nng_ipc *ipc)
+{
+ nni_ipc_conn_close((void *) ipc);
+}
+
+void
+nng_ipc_free(nng_ipc *ipc)
+{
+ nni_ipc_conn_fini((void *) ipc);
+}
+
+void
+nng_ipc_send(nng_ipc *ipc, nng_aio *aio)
+{
+ nni_ipc_conn_send((void *) ipc, aio);
+}
+
+void
+nng_ipc_recv(nng_ipc *ipc, nng_aio *aio)
+{
+ nni_ipc_conn_recv((void *) ipc, aio);
+}
+
+int
+nng_ipc_setopt(nng_ipc *ipc, const char *name, const void *val, size_t sz)
+{
+ return (nni_ipc_conn_setopt((void *) ipc, name, val, sz));
+}
+
+int
+nng_ipc_getopt(nng_ipc *ipc, const char *name, void *val, size_t *szp)
+{
+ return (nni_ipc_conn_getopt((void *) ipc, name, val, szp));
+}
+
+int
+nng_ipc_dialer_alloc(nng_ipc_dialer **dp)
+{
+ nni_ipc_dialer *d;
+ int rv;
+
+ if ((rv = nni_init()) != 0) {
+ return (rv);
+ }
+ if ((rv = nni_ipc_dialer_init(&d)) == 0) {
+ *dp = (void *) d;
+ }
+ return (rv);
+}
+
+void
+nng_ipc_dialer_close(nng_ipc_dialer *d)
+{
+ nni_ipc_dialer_close((void *) d);
+}
+
+void
+nng_ipc_dialer_free(nng_ipc_dialer *d)
+{
+ nni_ipc_dialer_fini((void *) d);
+}
+
+void
+nng_ipc_dialer_dial(nng_ipc_dialer *d, const nng_sockaddr *sa, nng_aio *aio)
+{
+ nni_ipc_dialer_dial((void *) d, sa, aio);
+}
+
+int
+nng_ipc_listener_alloc(nng_ipc_listener **lp)
+{
+ nni_ipc_listener *l;
+ int rv;
+
+ if ((rv = nni_init()) != 0) {
+ return (rv);
+ }
+ if ((rv = nni_ipc_listener_init(&l)) == 0) {
+ *lp = (void *) l;
+ }
+ return (rv);
+}
+
+void
+nng_ipc_listener_close(nng_ipc_listener *l)
+{
+ nni_ipc_listener_close((void *) l);
+}
+
+void
+nng_ipc_listener_free(nng_ipc_listener *l)
+{
+ nni_ipc_listener_fini((void *) l);
+}
+
+int
+nng_ipc_listener_listen(nng_ipc_listener *l, const nng_sockaddr *sa)
+{
+ return (nni_ipc_listener_listen((void *) l, sa));
+}
+
+void
+nng_ipc_listener_accept(nng_ipc_listener *l, nng_aio *aio)
+{
+ nni_ipc_listener_accept((void *) l, aio);
+}
diff --git a/src/supplemental/util/options.c b/src/supplemental/util/options.c
index c8dafed8..961e0bb2 100644
--- a/src/supplemental/util/options.c
+++ b/src/supplemental/util/options.c
@@ -11,8 +11,10 @@
#include <stdlib.h>
#include <string.h>
+#include <nng/nng.h>
+#include <nng/supplemental/util/options.h>
+
#include "core/nng_impl.h"
-#include "nng/supplemental/util/options.h"
// Call with optidx set to 1 to start parsing.
int