Add .clang-format file and format code
.clang-format file was taken from the docs repo.
Change-Id: I7b2eb5f4b4ea966564c66e52eac156b158321406
Signed-off-by: Ed Tanous <edtanous@google.com>
diff --git a/nbd-proxy.c b/nbd-proxy.c
index 3928aac..83bada5 100644
--- a/nbd-proxy.c
+++ b/nbd-proxy.c
@@ -17,11 +17,15 @@
#define _GNU_SOURCE
+#include "config.h"
+
#include <dirent.h>
#include <err.h>
#include <errno.h>
#include <fcntl.h>
#include <getopt.h>
+#include <json.h>
+#include <libudev.h>
#include <limits.h>
#include <signal.h>
#include <stdbool.h>
@@ -29,203 +33,203 @@
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
-#include <unistd.h>
-
#include <sys/poll.h>
#include <sys/socket.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <sys/un.h>
#include <sys/wait.h>
+#include <unistd.h>
-#include <json.h>
-#include <libudev.h>
-
-#include "config.h"
-
-struct config {
- char *name;
- bool is_default;
- char *nbd_device;
- struct json_object *metadata;
+struct config
+{
+ char* name;
+ bool is_default;
+ char* nbd_device;
+ struct json_object* metadata;
};
-struct ctx {
- int sock;
- int sock_client;
- int signal_pipe[2];
- char *sock_path;
- pid_t nbd_client_pid;
- pid_t state_hook_pid;
- int nbd_timeout;
- dev_t nbd_devno;
- uint8_t *buf;
- size_t bufsize;
- struct config *configs;
- int n_configs;
- struct config *default_config;
- struct config *config;
- struct udev *udev;
- struct udev_monitor *monitor;
+struct ctx
+{
+ int sock;
+ int sock_client;
+ int signal_pipe[2];
+ char* sock_path;
+ pid_t nbd_client_pid;
+ pid_t state_hook_pid;
+ int nbd_timeout;
+ dev_t nbd_devno;
+ uint8_t* buf;
+ size_t bufsize;
+ struct config* configs;
+ int n_configs;
+ struct config* default_config;
+ struct config* config;
+ struct udev* udev;
+ struct udev_monitor* monitor;
};
-static const char *conf_path = SYSCONFDIR "/nbd-proxy/config.json";
-static const char *state_hook_path = SYSCONFDIR "/nbd-proxy/state";
-static const char *sockpath_tmpl = RUNSTATEDIR "/nbd.%d.sock";
+static const char* conf_path = SYSCONFDIR "/nbd-proxy/config.json";
+static const char* state_hook_path = SYSCONFDIR "/nbd-proxy/state";
+static const char* sockpath_tmpl = RUNSTATEDIR "/nbd.%d.sock";
static const size_t bufsize = 0x20000;
static const int nbd_timeout_default = 30;
-static int open_nbd_socket(struct ctx *ctx)
+static int open_nbd_socket(struct ctx* ctx)
{
- struct sockaddr_un addr;
- char *path;
- int sd, rc;
+ struct sockaddr_un addr;
+ char* path;
+ int sd, rc;
- rc = asprintf(&path, sockpath_tmpl, getpid());
- if (rc < 0)
- return -1;
+ rc = asprintf(&path, sockpath_tmpl, getpid());
+ if (rc < 0)
+ return -1;
- sd = socket(AF_UNIX, SOCK_STREAM | SOCK_CLOEXEC, 0);
- if (sd < 0) {
- warn("can't create socket");
- goto err_free;
- }
+ sd = socket(AF_UNIX, SOCK_STREAM | SOCK_CLOEXEC, 0);
+ if (sd < 0)
+ {
+ warn("can't create socket");
+ goto err_free;
+ }
- rc = fchmod(sd, S_IRUSR | S_IWUSR);
- if (rc) {
- warn("can't set permissions on socket");
- goto err_close;
- }
+ rc = fchmod(sd, S_IRUSR | S_IWUSR);
+ if (rc)
+ {
+ warn("can't set permissions on socket");
+ goto err_close;
+ }
- addr.sun_family = AF_UNIX;
- strncpy(addr.sun_path, path, sizeof(addr.sun_path) -1);
+ addr.sun_family = AF_UNIX;
+ strncpy(addr.sun_path, path, sizeof(addr.sun_path) - 1);
- rc = bind(sd, (struct sockaddr *)&addr, sizeof(addr));
- if (rc) {
- warn("can't bind to path %s", path);
- goto err_close;
- }
+ rc = bind(sd, (struct sockaddr*)&addr, sizeof(addr));
+ if (rc)
+ {
+ warn("can't bind to path %s", path);
+ goto err_close;
+ }
- rc = listen(sd, 1);
- if (rc) {
- warn("can't listen on socket %s", path);
- goto err_unlink;
- }
+ rc = listen(sd, 1);
+ if (rc)
+ {
+ warn("can't listen on socket %s", path);
+ goto err_unlink;
+ }
- ctx->sock = sd;
- ctx->sock_path = path;
- return 0;
+ ctx->sock = sd;
+ ctx->sock_path = path;
+ return 0;
err_unlink:
- unlink(path);
+ unlink(path);
err_close:
- close(sd);
+ close(sd);
err_free:
- free(path);
- return -1;
+ free(path);
+ return -1;
}
-static int start_nbd_client(struct ctx *ctx)
+static int start_nbd_client(struct ctx* ctx)
{
- pid_t pid;
+ pid_t pid;
- pid = fork();
- if (pid < 0) {
- warn("can't create client process");
- return -1;
- }
+ pid = fork();
+ if (pid < 0)
+ {
+ warn("can't create client process");
+ return -1;
+ }
- /* child process: run nbd-client in non-fork mode */
- if (pid == 0) {
- char timeout_str[10];
- int fd;
+ /* child process: run nbd-client in non-fork mode */
+ if (pid == 0)
+ {
+ char timeout_str[10];
+ int fd;
- snprintf(timeout_str, sizeof(timeout_str),
- "%d", ctx->nbd_timeout);
+ snprintf(timeout_str, sizeof(timeout_str), "%d", ctx->nbd_timeout);
- fd = open("/dev/null", O_RDWR | O_CLOEXEC);
- if (fd < 0)
- err(EXIT_FAILURE, "can't open /dev/null");
+ fd = open("/dev/null", O_RDWR | O_CLOEXEC);
+ if (fd < 0)
+ err(EXIT_FAILURE, "can't open /dev/null");
- dup2(fd, STDIN_FILENO);
- dup2(fd, STDOUT_FILENO);
- close(fd);
+ dup2(fd, STDIN_FILENO);
+ dup2(fd, STDOUT_FILENO);
+ close(fd);
- execlp("nbd-client", "nbd-client",
- "-u", ctx->sock_path,
- "-n",
- "-L",
- "-t", timeout_str,
- ctx->config->nbd_device,
- NULL);
- err(EXIT_FAILURE, "can't start ndb client");
- }
+ execlp("nbd-client", "nbd-client", "-u", ctx->sock_path, "-n", "-L",
+ "-t", timeout_str, ctx->config->nbd_device, NULL);
+ err(EXIT_FAILURE, "can't start ndb client");
+ }
- ctx->nbd_client_pid = pid;
- return 0;
+ ctx->nbd_client_pid = pid;
+ return 0;
}
-static void stop_nbd_client(struct ctx *ctx)
+static void stop_nbd_client(struct ctx* ctx)
{
- int rc;
+ int rc;
- if (!ctx->nbd_client_pid)
- return;
+ if (!ctx->nbd_client_pid)
+ return;
- rc = kill(ctx->nbd_client_pid, SIGTERM);
- if (rc)
- return;
+ rc = kill(ctx->nbd_client_pid, SIGTERM);
+ if (rc)
+ return;
- waitpid(ctx->nbd_client_pid, NULL, 0);
- ctx->nbd_client_pid = 0;
+ waitpid(ctx->nbd_client_pid, NULL, 0);
+ ctx->nbd_client_pid = 0;
}
-static int copy_fd(struct ctx *ctx, int fd_in, int fd_out)
+static int copy_fd(struct ctx* ctx, int fd_in, int fd_out)
{
#ifdef HAVE_SPLICE
- int rc;
+ int rc;
- rc = splice(fd_in, NULL, fd_out, NULL, ctx->bufsize, 0);
- if (rc < 0)
- warn("splice");
+ rc = splice(fd_in, NULL, fd_out, NULL, ctx->bufsize, 0);
+ if (rc < 0)
+ warn("splice");
- return rc;
+ return rc;
#else
- size_t len, pos;
- ssize_t rc;
+ size_t len, pos;
+ ssize_t rc;
- for (;;) {
- errno = 0;
- rc = read(fd_in, ctx->buf, ctx->bufsize);
- if (rc < 0) {
- if (errno == EINTR)
- continue;
- warn("read failure");
- return -1;
- }
- if (rc == 0)
- return 0;
- break;
- }
+ for (;;)
+ {
+ errno = 0;
+ rc = read(fd_in, ctx->buf, ctx->bufsize);
+ if (rc < 0)
+ {
+ if (errno == EINTR)
+ continue;
+ warn("read failure");
+ return -1;
+ }
+ if (rc == 0)
+ return 0;
+ break;
+ }
- len = rc;
+ len = rc;
- for (pos = 0; pos < len;) {
- errno = 0;
- rc = write(fd_out, ctx->buf + pos, len - pos);
- if (rc < 0) {
- if (errno == EINTR)
- continue;
- warn("write failure");
- return -1;
- }
- if (rc == 0)
- break;
- pos += rc;
- }
+ for (pos = 0; pos < len;)
+ {
+ errno = 0;
+ rc = write(fd_out, ctx->buf + pos, len - pos);
+ if (rc < 0)
+ {
+ if (errno == EINTR)
+ continue;
+ warn("write failure");
+ return -1;
+ }
+ if (rc == 0)
+ break;
+ pos += rc;
+ }
- return pos;
+ return pos;
#endif
}
@@ -233,243 +237,260 @@
static void signal_handler(int signal)
{
- int rc;
+ int rc;
- rc = write(signal_pipe_fd, &signal, sizeof(signal));
+ rc = write(signal_pipe_fd, &signal, sizeof(signal));
- /* not a lot we can do here but exit... */
- if (rc != sizeof(signal))
- exit(EXIT_FAILURE);
+ /* not a lot we can do here but exit... */
+ if (rc != sizeof(signal))
+ exit(EXIT_FAILURE);
}
-static int setup_signals(struct ctx *ctx)
+static int setup_signals(struct ctx* ctx)
{
- struct sigaction sa;
- int rc;
+ struct sigaction sa;
+ int rc;
- rc = pipe2(ctx->signal_pipe, O_CLOEXEC);
- if (rc) {
- warn("cant setup signal pipe");
- return -1;
- }
+ rc = pipe2(ctx->signal_pipe, O_CLOEXEC);
+ if (rc)
+ {
+ warn("cant setup signal pipe");
+ return -1;
+ }
- signal_pipe_fd = ctx->signal_pipe[1];
+ signal_pipe_fd = ctx->signal_pipe[1];
- memset(&sa, 0, sizeof(sa));
- sa.sa_handler = signal_handler;
+ memset(&sa, 0, sizeof(sa));
+ sa.sa_handler = signal_handler;
- sigaction(SIGINT, &sa, NULL);
- sigaction(SIGTERM, &sa, NULL);
- sigaction(SIGCHLD, &sa, NULL);
+ sigaction(SIGINT, &sa, NULL);
+ sigaction(SIGTERM, &sa, NULL);
+ sigaction(SIGCHLD, &sa, NULL);
- return 0;
+ return 0;
}
-static void cleanup_signals(struct ctx *ctx)
+static void cleanup_signals(struct ctx* ctx)
{
- struct sigaction sa;
- memset(&sa, 0, sizeof(sa));
- sa.sa_handler = SIG_DFL;
+ struct sigaction sa;
+ memset(&sa, 0, sizeof(sa));
+ sa.sa_handler = SIG_DFL;
- sigaction(SIGINT, &sa, NULL);
- sigaction(SIGTERM, &sa, NULL);
- sigaction(SIGCHLD, &sa, NULL);
+ sigaction(SIGINT, &sa, NULL);
+ sigaction(SIGTERM, &sa, NULL);
+ sigaction(SIGCHLD, &sa, NULL);
- close(ctx->signal_pipe[0]);
- close(ctx->signal_pipe[1]);
+ close(ctx->signal_pipe[0]);
+ close(ctx->signal_pipe[1]);
}
-static void process_sigchld(struct ctx *ctx, bool *exit)
+static void process_sigchld(struct ctx* ctx, bool* exit)
{
- int status;
- pid_t pid;
+ int status;
+ pid_t pid;
- for (;;) {
- pid = waitpid(-1, &status, WNOHANG);
- if (pid == 0)
- break;
+ for (;;)
+ {
+ pid = waitpid(-1, &status, WNOHANG);
+ if (pid == 0)
+ break;
- if (pid == ctx->nbd_client_pid) {
- warnx("nbd client stopped (%s: %d); exiting",
- WIFEXITED(status) ? "rc" : "sig",
- WIFEXITED(status) ?
- WEXITSTATUS(status) :
- WTERMSIG(status));
- ctx->nbd_client_pid = 0;
- *exit = true;
-
- } else if (pid == ctx->state_hook_pid) {
- if (!WIFEXITED(status) || WEXITSTATUS(status)) {
- warnx("state hook failed (%s: %d); exiting",
- WIFEXITED(status) ? "rc" : "sig",
- WIFEXITED(status) ?
- WEXITSTATUS(status) :
- WTERMSIG(status));
- *exit = true;
- }
- ctx->state_hook_pid = 0;
- }
- }
+ if (pid == ctx->nbd_client_pid)
+ {
+ warnx("nbd client stopped (%s: %d); exiting",
+ WIFEXITED(status) ? "rc" : "sig",
+ WIFEXITED(status) ? WEXITSTATUS(status) : WTERMSIG(status));
+ ctx->nbd_client_pid = 0;
+ *exit = true;
+ }
+ else if (pid == ctx->state_hook_pid)
+ {
+ if (!WIFEXITED(status) || WEXITSTATUS(status))
+ {
+ warnx("state hook failed (%s: %d); exiting",
+ WIFEXITED(status) ? "rc" : "sig",
+ WIFEXITED(status) ? WEXITSTATUS(status)
+ : WTERMSIG(status));
+ *exit = true;
+ }
+ ctx->state_hook_pid = 0;
+ }
+ }
}
-static int process_signal_pipe(struct ctx *ctx, bool *exit)
+static int process_signal_pipe(struct ctx* ctx, bool* exit)
{
- int buf, rc;
+ int buf, rc;
- rc = read(ctx->signal_pipe[0], &buf, sizeof(buf));
- if (rc != sizeof(buf))
- return -1;
+ rc = read(ctx->signal_pipe[0], &buf, sizeof(buf));
+ if (rc != sizeof(buf))
+ return -1;
- *exit = false;
+ *exit = false;
- switch (buf) {
- case SIGCHLD:
- process_sigchld(ctx, exit);
- break;
- case SIGINT:
- case SIGTERM:
- *exit = true;
- break;
- }
+ switch (buf)
+ {
+ case SIGCHLD:
+ process_sigchld(ctx, exit);
+ break;
+ case SIGINT:
+ case SIGTERM:
+ *exit = true;
+ break;
+ }
- return 0;
+ return 0;
}
-static int wait_for_nbd_client(struct ctx *ctx)
+static int wait_for_nbd_client(struct ctx* ctx)
{
- struct pollfd pollfds[2];
- int rc;
+ struct pollfd pollfds[2];
+ int rc;
- pollfds[0].fd = ctx->sock;
- pollfds[0].events = POLLIN;
- pollfds[1].fd = ctx->signal_pipe[0];
- pollfds[1].events = POLLIN;
+ pollfds[0].fd = ctx->sock;
+ pollfds[0].events = POLLIN;
+ pollfds[1].fd = ctx->signal_pipe[0];
+ pollfds[1].events = POLLIN;
- for (;;) {
- errno = 0;
- rc = poll(pollfds, 2, -1);
- if (rc < 0) {
- if (errno == EINTR)
- continue;
- warn("poll failed");
- return -1;
- }
+ for (;;)
+ {
+ errno = 0;
+ rc = poll(pollfds, 2, -1);
+ if (rc < 0)
+ {
+ if (errno == EINTR)
+ continue;
+ warn("poll failed");
+ return -1;
+ }
- if (pollfds[0].revents) {
- rc = accept4(ctx->sock, NULL, NULL, SOCK_CLOEXEC);
- if (rc < 0) {
- warn("can't create connection");
- return -1;
- }
- ctx->sock_client = rc;
- break;
- }
+ if (pollfds[0].revents)
+ {
+ rc = accept4(ctx->sock, NULL, NULL, SOCK_CLOEXEC);
+ if (rc < 0)
+ {
+ warn("can't create connection");
+ return -1;
+ }
+ ctx->sock_client = rc;
+ break;
+ }
- if (pollfds[1].revents) {
- bool exit;
- rc = process_signal_pipe(ctx, &exit);
- if (rc || exit)
- return -1;
- }
- }
+ if (pollfds[1].revents)
+ {
+ bool exit;
+ rc = process_signal_pipe(ctx, &exit);
+ if (rc || exit)
+ return -1;
+ }
+ }
- return 0;
+ return 0;
}
-static int run_state_hook(struct ctx *ctx, const char *action, bool wait)
+static int run_state_hook(struct ctx* ctx, const char* action, bool wait)
{
- int status, rc, fd;
- pid_t pid;
+ int status, rc, fd;
+ pid_t pid;
- /* if the hook isn't present or executable, that's not necessarily
- * an error condition */
- if (access(state_hook_path, X_OK))
- return 0;
+ /* if the hook isn't present or executable, that's not necessarily
+ * an error condition */
+ if (access(state_hook_path, X_OK))
+ return 0;
- pid = fork();
- if (pid < 0) {
- warn("can't fork to execute hook %s", state_hook_path);
- return -1;
- }
+ pid = fork();
+ if (pid < 0)
+ {
+ warn("can't fork to execute hook %s", state_hook_path);
+ return -1;
+ }
- if (!pid) {
- const char *argv0;
+ if (!pid)
+ {
+ const char* argv0;
- argv0 = strchr(state_hook_path, '/');
- if (!argv0)
- argv0 = state_hook_path;
+ argv0 = strchr(state_hook_path, '/');
+ if (!argv0)
+ argv0 = state_hook_path;
- fd = open("/dev/null", O_RDWR | O_CLOEXEC);
- if (fd < 0)
- exit(EXIT_FAILURE);
+ fd = open("/dev/null", O_RDWR | O_CLOEXEC);
+ if (fd < 0)
+ exit(EXIT_FAILURE);
- dup2(fd, STDIN_FILENO);
- dup2(fd, STDOUT_FILENO);
- execl(state_hook_path, argv0, action, ctx->config->name, NULL);
- exit(EXIT_FAILURE);
- }
+ dup2(fd, STDIN_FILENO);
+ dup2(fd, STDOUT_FILENO);
+ execl(state_hook_path, argv0, action, ctx->config->name, NULL);
+ exit(EXIT_FAILURE);
+ }
- if (!wait) {
- ctx->state_hook_pid = pid;
- return 0;
- }
+ if (!wait)
+ {
+ ctx->state_hook_pid = pid;
+ return 0;
+ }
- rc = waitpid(pid, &status, 0);
- if (rc < 0) {
- warn("wait");
- return -1;
- }
+ rc = waitpid(pid, &status, 0);
+ if (rc < 0)
+ {
+ warn("wait");
+ return -1;
+ }
- if (!WIFEXITED(status) || WEXITSTATUS(status) != 0) {
- warnx("hook %s failed", state_hook_path);
- return -1;
- }
+ if (!WIFEXITED(status) || WEXITSTATUS(status) != 0)
+ {
+ warnx("hook %s failed", state_hook_path);
+ return -1;
+ }
- return 0;
+ return 0;
}
-static int udev_init(struct ctx *ctx)
+static int udev_init(struct ctx* ctx)
{
- int rc;
+ int rc;
- ctx->udev = udev_new();
- if (!ctx) {
- warn("can't create udev object");
- return -1;
- }
+ ctx->udev = udev_new();
+ if (!ctx)
+ {
+ warn("can't create udev object");
+ return -1;
+ }
- ctx->monitor = udev_monitor_new_from_netlink(ctx->udev, "kernel");
- if (!ctx->monitor) {
- warn("can't create udev monitor");
- goto out_unref_udev;
- }
+ ctx->monitor = udev_monitor_new_from_netlink(ctx->udev, "kernel");
+ if (!ctx->monitor)
+ {
+ warn("can't create udev monitor");
+ goto out_unref_udev;
+ }
- rc = udev_monitor_filter_add_match_subsystem_devtype(
- ctx->monitor, "block", "disk");
- if (rc) {
- warn("can't create udev monitor filter");
- goto out_unref_monitor;
- }
+ rc = udev_monitor_filter_add_match_subsystem_devtype(ctx->monitor, "block",
+ "disk");
+ if (rc)
+ {
+ warn("can't create udev monitor filter");
+ goto out_unref_monitor;
+ }
- rc = udev_monitor_enable_receiving(ctx->monitor);
- if (rc) {
- warn("can't start udev monitor");
- goto out_unref_monitor;
- }
+ rc = udev_monitor_enable_receiving(ctx->monitor);
+ if (rc)
+ {
+ warn("can't start udev monitor");
+ goto out_unref_monitor;
+ }
- return 0;
+ return 0;
out_unref_monitor:
- udev_monitor_unref(ctx->monitor);
+ udev_monitor_unref(ctx->monitor);
out_unref_udev:
- udev_unref(ctx->udev);
- return -1;
+ udev_unref(ctx->udev);
+ return -1;
}
-static void udev_free(struct ctx *ctx)
+static void udev_free(struct ctx* ctx)
{
- udev_monitor_unref(ctx->monitor);
- udev_unref(ctx->udev);
+ udev_monitor_unref(ctx->monitor);
+ udev_unref(ctx->udev);
}
/* Check for the change event on our nbd device, signifying that the kernel
@@ -480,402 +501,432 @@
* 0 if no processing was performed
* -1 on state hook error (and the nbd session should be closed)
*/
-static int udev_process(struct ctx *ctx)
+static int udev_process(struct ctx* ctx)
{
- struct udev_device *dev;
- bool action_is_change;
- dev_t devno;
- int rc;
+ struct udev_device* dev;
+ bool action_is_change;
+ dev_t devno;
+ int rc;
- dev = udev_monitor_receive_device(ctx->monitor);
- if (!dev)
- return 0;
+ dev = udev_monitor_receive_device(ctx->monitor);
+ if (!dev)
+ return 0;
- devno = udev_device_get_devnum(dev);
- action_is_change = !strcmp(udev_device_get_action(dev), "change");
- udev_device_unref(dev);
+ devno = udev_device_get_devnum(dev);
+ action_is_change = !strcmp(udev_device_get_action(dev), "change");
+ udev_device_unref(dev);
- if (devno != ctx->nbd_devno)
- return 0;
+ if (devno != ctx->nbd_devno)
+ return 0;
- if (!action_is_change)
- return 0;
+ if (!action_is_change)
+ return 0;
- udev_monitor_unref(ctx->monitor);
- udev_unref(ctx->udev);
- ctx->monitor = NULL;
- ctx->udev = NULL;
+ udev_monitor_unref(ctx->monitor);
+ udev_unref(ctx->udev);
+ ctx->monitor = NULL;
+ ctx->udev = NULL;
- rc = run_state_hook(ctx, "start", false);
+ rc = run_state_hook(ctx, "start", false);
- return rc;
+ return rc;
}
-static int run_proxy(struct ctx *ctx)
+static int run_proxy(struct ctx* ctx)
{
- struct pollfd pollfds[4];
- bool exit = false;
- int rc, n_fd;
+ struct pollfd pollfds[4];
+ bool exit = false;
+ int rc, n_fd;
- /* main proxy: forward data between stdio & socket */
- pollfds[0].fd = ctx->sock_client;
- pollfds[0].events = POLLIN;
- pollfds[1].fd = STDIN_FILENO;
- pollfds[1].events = POLLIN;
- pollfds[2].fd = ctx->signal_pipe[0];
- pollfds[2].events = POLLIN;
- pollfds[3].fd = udev_monitor_get_fd(ctx->monitor);
- pollfds[3].events = POLLIN;
+ /* main proxy: forward data between stdio & socket */
+ pollfds[0].fd = ctx->sock_client;
+ pollfds[0].events = POLLIN;
+ pollfds[1].fd = STDIN_FILENO;
+ pollfds[1].events = POLLIN;
+ pollfds[2].fd = ctx->signal_pipe[0];
+ pollfds[2].events = POLLIN;
+ pollfds[3].fd = udev_monitor_get_fd(ctx->monitor);
+ pollfds[3].events = POLLIN;
- n_fd = 4;
+ n_fd = 4;
- for (;;) {
- errno = 0;
- rc = poll(pollfds, n_fd, -1);
- if (rc < 0) {
- if (errno == EINTR)
- continue;
- warn("poll failed");
- break;
- }
+ for (;;)
+ {
+ errno = 0;
+ rc = poll(pollfds, n_fd, -1);
+ if (rc < 0)
+ {
+ if (errno == EINTR)
+ continue;
+ warn("poll failed");
+ break;
+ }
- if (pollfds[0].revents) {
- rc = copy_fd(ctx, ctx->sock_client, STDOUT_FILENO);
- if (rc <= 0)
- break;
- }
+ if (pollfds[0].revents)
+ {
+ rc = copy_fd(ctx, ctx->sock_client, STDOUT_FILENO);
+ if (rc <= 0)
+ break;
+ }
- if (pollfds[1].revents) {
- rc = copy_fd(ctx, STDIN_FILENO, ctx->sock_client);
- if (rc <= 0)
- break;
- }
+ if (pollfds[1].revents)
+ {
+ rc = copy_fd(ctx, STDIN_FILENO, ctx->sock_client);
+ if (rc <= 0)
+ break;
+ }
- if (pollfds[2].revents) {
- rc = process_signal_pipe(ctx, &exit);
- if (rc || exit)
- break;
- }
+ if (pollfds[2].revents)
+ {
+ rc = process_signal_pipe(ctx, &exit);
+ if (rc || exit)
+ break;
+ }
- if (pollfds[3].revents) {
- rc = udev_process(ctx);
- if (rc)
- break;
+ if (pollfds[3].revents)
+ {
+ rc = udev_process(ctx);
+ if (rc)
+ break;
- /* udev_process may have closed the udev connection,
- * in which case we can stop polling on its fd */
- if (!ctx->udev) {
- pollfds[3].fd = 0;
- pollfds[3].revents = 0;
- n_fd = 3;
- }
- }
- }
+ /* udev_process may have closed the udev connection,
+ * in which case we can stop polling on its fd */
+ if (!ctx->udev)
+ {
+ pollfds[3].fd = 0;
+ pollfds[3].revents = 0;
+ n_fd = 3;
+ }
+ }
+ }
- return rc ? -1 : 0;
+ return rc ? -1 : 0;
}
-static void print_metadata(struct ctx *ctx)
+static void print_metadata(struct ctx* ctx)
{
- struct json_object *md;
- int i;
+ struct json_object* md;
+ int i;
- md = json_object_new_object();
+ md = json_object_new_object();
- for (i = 0; i < ctx->n_configs; i++) {
- struct config *config = &ctx->configs[i];
- json_object_object_add(md, config->name,
- json_object_get(config->metadata));
- }
+ for (i = 0; i < ctx->n_configs; i++)
+ {
+ struct config* config = &ctx->configs[i];
+ json_object_object_add(md, config->name,
+ json_object_get(config->metadata));
+ }
- puts(json_object_get_string(md));
+ puts(json_object_get_string(md));
- json_object_put(md);
+ json_object_put(md);
}
-static void config_free_one(struct config *config)
+static void config_free_one(struct config* config)
{
- if (config->metadata)
- json_object_put(config->metadata);
- free(config->nbd_device);
- free(config->name);
+ if (config->metadata)
+ json_object_put(config->metadata);
+ free(config->nbd_device);
+ free(config->name);
}
-static int config_parse_one(struct config *config, const char *name,
- json_object *obj)
+static int config_parse_one(struct config* config, const char* name,
+ json_object* obj)
{
- struct json_object *tmp, *meta;
- json_bool jrc;
+ struct json_object *tmp, *meta;
+ json_bool jrc;
- jrc = json_object_object_get_ex(obj, "nbd-device", &tmp);
- if (!jrc) {
- warnx("config %s doesn't specify a nbd-device", name);
- return -1;
- }
+ jrc = json_object_object_get_ex(obj, "nbd-device", &tmp);
+ if (!jrc)
+ {
+ warnx("config %s doesn't specify a nbd-device", name);
+ return -1;
+ }
- if (!json_object_is_type(tmp, json_type_string)) {
- warnx("config %s has invalid nbd-device", name);
- return -1;
- }
+ if (!json_object_is_type(tmp, json_type_string))
+ {
+ warnx("config %s has invalid nbd-device", name);
+ return -1;
+ }
- config->nbd_device = strdup(json_object_get_string(tmp));
- config->name = strdup(name);
+ config->nbd_device = strdup(json_object_get_string(tmp));
+ config->name = strdup(name);
- jrc = json_object_object_get_ex(obj, "default", &tmp);
- config->is_default = jrc && json_object_get_boolean(tmp);
+ jrc = json_object_object_get_ex(obj, "default", &tmp);
+ config->is_default = jrc && json_object_get_boolean(tmp);
- jrc = json_object_object_get_ex(obj, "metadata", &meta);
- if (jrc && json_object_is_type(meta, json_type_object))
- config->metadata = json_object_get(meta);
- else
- config->metadata = NULL;
+ jrc = json_object_object_get_ex(obj, "metadata", &meta);
+ if (jrc && json_object_is_type(meta, json_type_object))
+ config->metadata = json_object_get(meta);
+ else
+ config->metadata = NULL;
- return 0;
+ return 0;
}
-static void config_free(struct ctx *ctx)
+static void config_free(struct ctx* ctx)
{
- int i;
+ int i;
- for (i = 0; i < ctx->n_configs; i++)
- config_free_one(&ctx->configs[i]);
+ for (i = 0; i < ctx->n_configs; i++)
+ config_free_one(&ctx->configs[i]);
- free(ctx->configs);
- ctx->n_configs = 0;
+ free(ctx->configs);
+ ctx->n_configs = 0;
}
-static int config_init(struct ctx *ctx)
+static int config_init(struct ctx* ctx)
{
- struct json_object *obj, *tmp;
- json_bool jrc;
- int i, rc;
+ struct json_object *obj, *tmp;
+ json_bool jrc;
+ int i, rc;
- /* apply defaults */
- ctx->nbd_timeout = nbd_timeout_default;
+ /* apply defaults */
+ ctx->nbd_timeout = nbd_timeout_default;
- obj = json_object_from_file(conf_path);
- if (!obj) {
- warnx("can't read configuration from %s\n", conf_path);
- return -1;
- }
+ obj = json_object_from_file(conf_path);
+ if (!obj)
+ {
+ warnx("can't read configuration from %s\n", conf_path);
+ return -1;
+ }
- /* global configuration */
- jrc = json_object_object_get_ex(obj, "timeout", &tmp);
- if (jrc) {
- errno = 0;
- ctx->nbd_timeout = json_object_get_int(tmp);
- if (ctx->nbd_timeout == 0 && errno) {
- warnx("can't parse timeout value");
- goto err_free;
- }
- }
+ /* global configuration */
+ jrc = json_object_object_get_ex(obj, "timeout", &tmp);
+ if (jrc)
+ {
+ errno = 0;
+ ctx->nbd_timeout = json_object_get_int(tmp);
+ if (ctx->nbd_timeout == 0 && errno)
+ {
+ warnx("can't parse timeout value");
+ goto err_free;
+ }
+ }
- /* per-config configuration */
- jrc = json_object_object_get_ex(obj, "configurations", &tmp);
- if (!jrc) {
- warnx("no configurations specified");
- goto err_free;
- }
+ /* per-config configuration */
+ jrc = json_object_object_get_ex(obj, "configurations", &tmp);
+ if (!jrc)
+ {
+ warnx("no configurations specified");
+ goto err_free;
+ }
- if (!json_object_is_type(tmp, json_type_object)) {
- warnx("invalid configurations format");
- goto err_free;
- }
+ if (!json_object_is_type(tmp, json_type_object))
+ {
+ warnx("invalid configurations format");
+ goto err_free;
+ }
- ctx->n_configs = json_object_object_length(tmp);
- ctx->configs = calloc(ctx->n_configs, sizeof(*ctx->configs));
+ ctx->n_configs = json_object_object_length(tmp);
+ ctx->configs = calloc(ctx->n_configs, sizeof(*ctx->configs));
- i = 0;
- json_object_object_foreach(tmp, name, config_json) {
- struct config *config = &ctx->configs[i];
+ i = 0;
+ json_object_object_foreach(tmp, name, config_json)
+ {
+ struct config* config = &ctx->configs[i];
- rc = config_parse_one(config, name, config_json);
- if (rc)
- goto err_free;
+ rc = config_parse_one(config, name, config_json);
+ if (rc)
+ goto err_free;
- if (config->is_default) {
- if (ctx->default_config) {
- warn("multiple configs flagged as default");
- goto err_free;
- }
- ctx->default_config = config;
- }
- i++;
- }
+ if (config->is_default)
+ {
+ if (ctx->default_config)
+ {
+ warn("multiple configs flagged as default");
+ goto err_free;
+ }
+ ctx->default_config = config;
+ }
+ i++;
+ }
- json_object_put(obj);
+ json_object_put(obj);
- if (ctx->n_configs == 1)
- ctx->default_config = &ctx->configs[0];
+ if (ctx->n_configs == 1)
+ ctx->default_config = &ctx->configs[0];
- return 0;
+ return 0;
err_free:
- warnx("failed to load config from %s", conf_path);
- json_object_put(obj);
- return -1;
+ warnx("failed to load config from %s", conf_path);
+ json_object_put(obj);
+ return -1;
}
-static int config_select(struct ctx *ctx, const char *name)
+static int config_select(struct ctx* ctx, const char* name)
{
- struct config *config;
- struct stat statbuf;
- int i, rc;
+ struct config* config;
+ struct stat statbuf;
+ int i, rc;
- config = NULL;
+ config = NULL;
- if (!name) {
- /* no config specified: use the default */
- if (!ctx->default_config) {
- warnx("no config specified, and no default");
- return -1;
- }
- config = ctx->default_config;
+ if (!name)
+ {
+ /* no config specified: use the default */
+ if (!ctx->default_config)
+ {
+ warnx("no config specified, and no default");
+ return -1;
+ }
+ config = ctx->default_config;
+ }
+ else
+ {
+ /* find a matching config... */
+ for (i = 0; i < ctx->n_configs; i++)
+ {
+ if (!strcmp(ctx->configs[i].name, name))
+ {
+ config = &ctx->configs[i];
+ break;
+ }
+ }
- } else {
- /* find a matching config... */
- for (i = 0; i < ctx->n_configs; i++) {
- if (!strcmp(ctx->configs[i].name, name)) {
- config = &ctx->configs[i];
- break;
- }
- }
+ if (!config)
+ {
+ warnx("no such configuration '%s'", name);
+ return -1;
+ }
+ }
- if (!config) {
- warnx("no such configuration '%s'", name);
- return -1;
- }
- }
+ /* check that the device exists */
+ rc = stat(config->nbd_device, &statbuf);
+ if (rc)
+ {
+ warn("can't stat nbd device %s", config->nbd_device);
+ return -1;
+ }
- /* check that the device exists */
- rc = stat(config->nbd_device, &statbuf);
- if (rc) {
- warn("can't stat nbd device %s", config->nbd_device);
- return -1;
- }
+ if (!S_ISBLK(statbuf.st_mode))
+ {
+ warn("specified nbd path %s isn't a block device", config->nbd_device);
+ return -1;
+ }
- if (!S_ISBLK(statbuf.st_mode)) {
- warn("specified nbd path %s isn't a block device",
- config->nbd_device);
- return -1;
- }
+ /* ... and apply it */
+ ctx->config = config;
+ ctx->nbd_devno = statbuf.st_rdev;
- /* ... and apply it */
- ctx->config = config;
- ctx->nbd_devno = statbuf.st_rdev;
-
- return 0;
+ return 0;
}
static const struct option options[] = {
- { .name = "help", .val = 'h' },
- { .name = "metadata", .val = 'm' },
- { 0 },
+ {.name = "help", .val = 'h'},
+ {.name = "metadata", .val = 'm'},
+ {0},
};
-enum action {
- ACTION_PROXY,
- ACTION_METADATA,
-};
-
-static void print_usage(const char *progname)
+enum action
{
- fprintf(stderr, "usage:\n");
- fprintf(stderr, "\t%s [configuration]\n", progname);
- fprintf(stderr, "\t%s --metadata\n", progname);
+ ACTION_PROXY,
+ ACTION_METADATA,
+};
+
+static void print_usage(const char* progname)
+{
+ fprintf(stderr, "usage:\n");
+ fprintf(stderr, "\t%s [configuration]\n", progname);
+ fprintf(stderr, "\t%s --metadata\n", progname);
}
-int main(int argc, char **argv)
+int main(int argc, char** argv)
{
- enum action action = ACTION_PROXY;
- const char *config_name;
- struct ctx _ctx, *ctx;
- int rc;
+ enum action action = ACTION_PROXY;
+ const char* config_name;
+ struct ctx _ctx, *ctx;
+ int rc;
- config_name = NULL;
+ config_name = NULL;
- for (;;) {
- int c = getopt_long(argc, argv, "h", options, NULL);
- if (c == -1)
- break;
+ for (;;)
+ {
+ int c = getopt_long(argc, argv, "h", options, NULL);
+ if (c == -1)
+ break;
- switch (c) {
- case 'm':
- action = ACTION_METADATA;
- break;
- case 'h':
- case '?':
- print_usage(argv[0]);
- return c == 'h' ? EXIT_SUCCESS : EXIT_FAILURE;
- }
- }
+ switch (c)
+ {
+ case 'm':
+ action = ACTION_METADATA;
+ break;
+ case 'h':
+ case '?':
+ print_usage(argv[0]);
+ return c == 'h' ? EXIT_SUCCESS : EXIT_FAILURE;
+ }
+ }
- if (optind < argc)
- config_name = argv[optind];
+ if (optind < argc)
+ config_name = argv[optind];
- ctx = &_ctx;
- memset(ctx, 0, sizeof(*ctx));
- ctx->bufsize = bufsize;
- ctx->buf = malloc(ctx->bufsize);
+ ctx = &_ctx;
+ memset(ctx, 0, sizeof(*ctx));
+ ctx->bufsize = bufsize;
+ ctx->buf = malloc(ctx->bufsize);
- rc = config_init(ctx);
- if (rc)
- goto out_free;
+ rc = config_init(ctx);
+ if (rc)
+ goto out_free;
- if (action == ACTION_METADATA) {
- print_metadata(ctx);
- goto out_free;
- }
+ if (action == ACTION_METADATA)
+ {
+ print_metadata(ctx);
+ goto out_free;
+ }
- rc = config_select(ctx, config_name);
- if (rc)
- goto out_free;
+ rc = config_select(ctx, config_name);
+ if (rc)
+ goto out_free;
- rc = open_nbd_socket(ctx);
- if (rc)
- goto out_free;
+ rc = open_nbd_socket(ctx);
+ if (rc)
+ goto out_free;
- rc = setup_signals(ctx);
- if (rc)
- goto out_close;
+ rc = setup_signals(ctx);
+ if (rc)
+ goto out_close;
- rc = start_nbd_client(ctx);
- if (rc)
- goto out_stop_client;
+ rc = start_nbd_client(ctx);
+ if (rc)
+ goto out_stop_client;
- rc = wait_for_nbd_client(ctx);
- if (rc)
- goto out_stop_client;
+ rc = wait_for_nbd_client(ctx);
+ if (rc)
+ goto out_stop_client;
- rc = udev_init(ctx);
- if (rc)
- goto out_stop_client;
+ rc = udev_init(ctx);
+ if (rc)
+ goto out_stop_client;
- rc = run_proxy(ctx);
+ rc = run_proxy(ctx);
- if (ctx->udev)
- udev_free(ctx);
+ if (ctx->udev)
+ udev_free(ctx);
- run_state_hook(ctx, "stop", true);
+ run_state_hook(ctx, "stop", true);
out_stop_client:
- /* we cleanup signals before stopping the client, because we
- * no longer care about SIGCHLD from the stopping nbd-client
- * process. stop_nbd_client will be a no-op if the client hasn't
- * been started. */
- cleanup_signals(ctx);
+ /* we cleanup signals before stopping the client, because we
+ * no longer care about SIGCHLD from the stopping nbd-client
+ * process. stop_nbd_client will be a no-op if the client hasn't
+ * been started. */
+ cleanup_signals(ctx);
- stop_nbd_client(ctx);
- close(ctx->sock_client);
+ stop_nbd_client(ctx);
+ close(ctx->sock_client);
out_close:
- if (ctx->sock_path) {
- unlink(ctx->sock_path);
- free(ctx->sock_path);
- }
- close(ctx->sock);
+ if (ctx->sock_path)
+ {
+ unlink(ctx->sock_path);
+ free(ctx->sock_path);
+ }
+ close(ctx->sock);
out_free:
- config_free(ctx);
- free(ctx->buf);
- return rc ? EXIT_FAILURE : EXIT_SUCCESS;
+ config_free(ctx);
+ free(ctx->buf);
+ return rc ? EXIT_FAILURE : EXIT_SUCCESS;
}