diff --git a/flock/flock.c b/flock/flock.c index 3320cd28..28b6a0f1 100644 --- a/flock/flock.c +++ b/flock/flock.c @@ -99,16 +99,33 @@ main(int argc, char **argv, char **argh UNUSED) log_switch(1, NULL, NULL); + /* Find the original UID/GIDs */ + uid_t euid = geteuid(), egid = getegid(); + /* Parse args */ flock_config.exec_name = argv[0] ?: "flock-sim"; int opt; - while ((opt = getopt(argc, argv, "")) != -1) + while ((opt = getopt(argc, argv, "ls:")) != -1) { - /* TODO: add some options */ - usage(stderr); - return 2; + switch (opt) + { + case 'l': + flock_config.control_socket_path = "flock-sim.ctl"; + break; + + case 's': + flock_config.control_socket_path = mb_strdup(&root_pool, optarg); + break; + + default: + usage(stderr); + return 2; + } } + /* FIXME: have a default */ + ASSERT_DIE(flock_config.control_socket_path); + /* Get hypervisor name */ if (optind != argc - 1) { @@ -127,11 +144,9 @@ main(int argc, char **argv, char **argh UNUSED) #undef FROB sigprocmask(SIG_BLOCK, &newmask, &oldmask); - /* Keep the original UID/GIDs */ - uid_t euid = geteuid(), egid = getegid(); - - /* First we need to create the PID + mount + user namespace to acquire capabilities */ - SYSCALL(unshare, CLONE_NEWPID | CLONE_NEWNS | CLONE_NEWUSER); + /* First we need to create the PID + mount + user namespace to acquire capabilities, + * and also time namespace for good measure */ + SYSCALL(unshare, CLONE_NEWPID | CLONE_NEWNS | CLONE_NEWUSER | CLONE_NEWTIME); /* Then we have to fork() to become PID 1 of the new PID namespace */ pid_t init_pid = fork(); @@ -173,8 +188,11 @@ main(int argc, char **argv, char **argh UNUSED) * let's spawn a child to do external communication before unsharing */ hypervisor_exposed_fork(); - /* And now finally we can go for unsharing the rest -- networks and time */ - SYSCALL(unshare, CLONE_NEWTIME | CLONE_NEWNET); + /* We also need to prepare all the hypervisor-init stuff */ + hypervisor_control_socket(); + + /* And now finally we can go for unsharing the networks */ + SYSCALL(unshare, CLONE_NEWNET); /* Set signal handlers as this process is init in its PID namespace */ signal(SIGTERM, hypervisor_poweroff_sighandler); @@ -190,6 +208,10 @@ main(int argc, char **argv, char **argh UNUSED) getrlimit(RLIMIT_CORE, &corelimit); log(L_INFO "Core limit %u %u", corelimit.rlim_cur, corelimit.rlim_max); + /* Run worker threads */ + struct thread_config tc = {}; + bird_thread_commit(&tc); + /* Wait for Godot */ log(L_INFO "Hypervisor running"); while (1) diff --git a/flock/flock.h b/flock/flock.h index 285339ae..988e4fa8 100644 --- a/flock/flock.h +++ b/flock/flock.h @@ -5,10 +5,12 @@ #include "lib/birdlib.h" void hypervisor_exposed_fork(void); +void hypervisor_control_socket(void); struct flock_config { const char *hypervisor_name; const char *exec_name; + const char *control_socket_path; }; extern struct flock_config flock_config; diff --git a/flock/hypervisor.c b/flock/hypervisor.c index 8b2f955a..0f62c52b 100644 --- a/flock/hypervisor.c +++ b/flock/hypervisor.c @@ -2,10 +2,56 @@ #include "lib/resource.h" #include "lib/io-loop.h" +#include "lib/socket.h" + +#include "flock/flock.h" #include -/* Local communication structure */ +/** + * Main control socket + **/ + +pool *hypervisor_control_socket_pool; + +static int +hcs_connect(sock *s, uint size UNUSED) +{ + log(L_INFO "CLI connected: %p", s); + sk_close(s); + return 1; +} + +static void +hcs_connect_err(sock *s UNUSED, int err) +{ + ASSERT_DIE(err); + log(L_INFO "Failed to accept CLI connection: %s", strerror(err)); +} + +void +hypervisor_control_socket(void) +{ + struct birdloop *loop = birdloop_new(&root_pool, DOMAIN_ORDER(control), 0, "Control socket"); + birdloop_enter(loop); + + pool *p = hypervisor_control_socket_pool = rp_new(birdloop_pool(loop), birdloop_domain(loop), "Control socket pool"); + sock *s = sk_new(p); + s->type = SK_UNIX_PASSIVE; + s->rx_hook = hcs_connect; + s->err_hook = hcs_connect_err; + s->rbsize = 1024; + + unlink(flock_config.control_socket_path); + if (sk_open_unix(s, loop, flock_config.control_socket_path) < 0) + die("Can't create control socket %s: %m", flock_config.control_socket_path); + + birdloop_leave(loop); +} + +/** + * Exposed process' communication structure + **/ static struct hypervisor_exposed { pool *p; sock *s;