From 4313a065a1892a96bf1d90c4b5dfd2a7b8870d4d Mon Sep 17 00:00:00 2001 From: Kubuxu Date: Tue, 17 Nov 2015 16:22:50 +0100 Subject: [PATCH 1/2] Create systemd socket activation. In future the socket activation IMHO should be standard way of starting cjdns. Thanks to that configurators don't have to know anything about cjdroute placement to start cjdns. --- contrib/bash/cjdns-trap.sh | 4 ++++ contrib/systemd/README.md | 6 ++++++ contrib/systemd/cjdns.socket | 11 +++++++++++ contrib/systemd/cjdns@.service | 16 ++++++++++++++++ 4 files changed, 37 insertions(+) create mode 100755 contrib/bash/cjdns-trap.sh create mode 100644 contrib/systemd/README.md create mode 100644 contrib/systemd/cjdns.socket create mode 100644 contrib/systemd/cjdns@.service diff --git a/contrib/bash/cjdns-trap.sh b/contrib/bash/cjdns-trap.sh new file mode 100755 index 000000000..731d2e3de --- /dev/null +++ b/contrib/bash/cjdns-trap.sh @@ -0,0 +1,4 @@ +#!/usr/bin/env sh +PIPE_NAME="client-core-$(tr -cd 'a-f0-9' < /dev/urandom | head -c 8)" +(sleep 1 && /usr/bin/env cjdroute core "$PIPE_NAME" > /dev/null) & +nc -lU "/tmp/cjdns_pipe_$PIPE_NAME" diff --git a/contrib/systemd/README.md b/contrib/systemd/README.md new file mode 100644 index 000000000..4ccfa7751 --- /dev/null +++ b/contrib/systemd/README.md @@ -0,0 +1,6 @@ +## How to install + +```bash +mv contrib/systemd/cjdns* /usr/lib/systemd/systemd/ +mv conrtib/bash/cjdns-trap.sh /usr/lib/systemd/scripts/ +``` diff --git a/contrib/systemd/cjdns.socket b/contrib/systemd/cjdns.socket new file mode 100644 index 000000000..f52b05583 --- /dev/null +++ b/contrib/systemd/cjdns.socket @@ -0,0 +1,11 @@ +[Unit] +Description=Cjdns activation socket. + +[Socket] +ListenStream=/run/cjdns/cjdns.socket +Accept=true +SocketMode=0600 + +[Install] +WantedBy=sockets.target + diff --git a/contrib/systemd/cjdns@.service b/contrib/systemd/cjdns@.service new file mode 100644 index 000000000..727ea6f1c --- /dev/null +++ b/contrib/systemd/cjdns@.service @@ -0,0 +1,16 @@ +[Unit] +Description=cjdns-multinstant: routing engine designed for security, scalability, speed and ease of use +Wants=network.target +After=network.target +Requires=cjdns.socket + +[Service] +ProtectHome=true +ProtectSystem=true +SyslogIdentifier=cjdroute + +Type=forking +ExecStart=/usr/lib/systemd/scripts/cjdns-trap.sh +StandardInput=socket +StandardOutput=socket +StandardError=journal From 24cdea6dfddfff79a978c610c33880166eeaed7d Mon Sep 17 00:00:00 2001 From: Kubuxu Date: Wed, 18 Nov 2015 08:59:38 +0100 Subject: [PATCH 2/2] Rework sockettrap to be a C program. This solves netcat incompatiblity issues. --- contrib/bash/cjdns-trap.sh | 4 -- contrib/c/sockettrap.c | 103 +++++++++++++++++++++++++++++++++ contrib/systemd/README.md | 2 +- contrib/systemd/cjdns@.service | 2 +- node_build/make.js | 4 ++ 5 files changed, 109 insertions(+), 6 deletions(-) delete mode 100755 contrib/bash/cjdns-trap.sh create mode 100644 contrib/c/sockettrap.c diff --git a/contrib/bash/cjdns-trap.sh b/contrib/bash/cjdns-trap.sh deleted file mode 100755 index 731d2e3de..000000000 --- a/contrib/bash/cjdns-trap.sh +++ /dev/null @@ -1,4 +0,0 @@ -#!/usr/bin/env sh -PIPE_NAME="client-core-$(tr -cd 'a-f0-9' < /dev/urandom | head -c 8)" -(sleep 1 && /usr/bin/env cjdroute core "$PIPE_NAME" > /dev/null) & -nc -lU "/tmp/cjdns_pipe_$PIPE_NAME" diff --git a/contrib/c/sockettrap.c b/contrib/c/sockettrap.c new file mode 100644 index 000000000..e84c1c9ef --- /dev/null +++ b/contrib/c/sockettrap.c @@ -0,0 +1,103 @@ +/* vim: set expandtab ts=4 sw=4: */ +/* + * You may redistribute this program and/or modify it under the terms of + * the GNU General Public License as published by the Free Software Foundation, + * either version 3 of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ +#include +#include +#include +#include +#include +#include +#include + +#include "util/Hex.h" +#include "memory/Allocator.h" +#include "memory/MallocAllocator.h" +#include "crypto/random/Random.h" +#include "io/FileReader.h" +#include "io/FileWriter.h" +#include "util/CString.h" +#include "util/Assert.h" +#include "util/log/Log.h" +#include "util/log/FileWriterLog.h" +#include "util/events/Time.h" +#include "util/events/EventBase.h" +#include "util/events/Pipe.h" +#include "util/events/Process.h" +#include "admin/angel/InterfaceWaiter.h" + +static void onCoreExit(int64_t exit_status, int term_signal) +{ + Assert_failure("Core exited with status [%d], signal [%d]\n", (int)exit_status, term_signal); +} + +/** + * Usage: + * pass an absolute path to cjdroute executable as an argument + * and this program will act as inetd boostrap, + * capturing data comming from STDIN and passing it as inital core config + * of cjdroute core and sending response on STDOUT. + **/ + +int main(int argc, char** argv) +{ + if (argc != 2) { + exit(EX_USAGE); + } + char* corePath = argv[1]; + + struct Except* eh = NULL; + + // Allow it to allocate 1MB + struct Allocator* allocator = MallocAllocator_new(1<<20); + struct Log* logger = NULL; // We don't want messages from the trap. + struct Random* rand = Random_new(allocator, logger, eh); + struct EventBase* eventBase = EventBase_new(allocator); + + struct Writer* stdoutWriter = FileWriter_new(stdout, allocator); + + struct Allocator* corePipeAlloc = Allocator_child(allocator); + char corePipeName[64] = "client-core-"; + Random_base32(rand, (uint8_t*)corePipeName+CString_strlen(corePipeName), 31); + Assert_ifParanoid(EventBase_eventCount(eventBase) == 0); + struct Pipe* corePipe = Pipe_named(corePipeName, eventBase, eh, corePipeAlloc); + corePipe->logger = logger; + Assert_ifParanoid(EventBase_eventCount(eventBase) == 2); + + struct Message* toCoreMsg = Message_new(0, 1024, allocator); + unsigned char buff[1024] = { 0 }; + int len; + do { + len = read(STDIN_FILENO, buff, 1024); + if (len <= 0 && errno != EAGAIN) { + fprintf(stderr, "Read returned: %d with errno %s.\n", len, strerror(errno)); + exit(EX_NOINPUT); + } + // read will return -1 and set errno if there is nonblocking pipe. + } while (len == -1 && errno == EAGAIN); + + Message_push(toCoreMsg, buff, len, eh); + + char* args[] = { "core", corePipeName, NULL }; + + Process_spawn(corePath, args, eventBase, allocator, onCoreExit); + + + Iface_CALL(corePipe->iface.send, toCoreMsg, &corePipe->iface); + + struct Message* fromCoreMsg = + InterfaceWaiter_waitForData(&corePipe->iface, eventBase, allocator, eh); + Writer_write(stdoutWriter, fromCoreMsg->bytes, fromCoreMsg->length); + + return 0; +} diff --git a/contrib/systemd/README.md b/contrib/systemd/README.md index 4ccfa7751..d168109fe 100644 --- a/contrib/systemd/README.md +++ b/contrib/systemd/README.md @@ -2,5 +2,5 @@ ```bash mv contrib/systemd/cjdns* /usr/lib/systemd/systemd/ -mv conrtib/bash/cjdns-trap.sh /usr/lib/systemd/scripts/ +mv ./sockettrap /usr/lib/systemd/scripts/cjdns-trap ``` diff --git a/contrib/systemd/cjdns@.service b/contrib/systemd/cjdns@.service index 727ea6f1c..7873a1ca9 100644 --- a/contrib/systemd/cjdns@.service +++ b/contrib/systemd/cjdns@.service @@ -10,7 +10,7 @@ ProtectSystem=true SyslogIdentifier=cjdroute Type=forking -ExecStart=/usr/lib/systemd/scripts/cjdns-trap.sh +ExecStart=/usr/lib/systemd/scripts/cjdns-trap /usr/bin/cjdroute StandardInput=socket StandardOutput=socket StandardError=journal diff --git a/node_build/make.js b/node_build/make.js index 76eba557b..fbaa4d875 100644 --- a/node_build/make.js +++ b/node_build/make.js @@ -409,6 +409,10 @@ Builder.configure({ builder.buildExecutable('contrib/c/privatetopublic.c'); builder.buildExecutable('contrib/c/sybilsim.c'); builder.buildExecutable('contrib/c/makekeys.c'); + if (builder.config.systemName !== 'win32') { + // Everything else is UNIX based. + builder.buildExecutable('contrib/c/sockettrap.c'); + } builder.buildExecutable('crypto/random/randombytes.c');