diff options
author | David Gibson <david@gibson.dropbear.id.au> | 2024-11-06 14:03:22 +1100 |
---|---|---|
committer | Stefano Brivio <sbrivio@redhat.com> | 2024-11-07 12:47:30 +0100 |
commit | 1699083f291ca8e639d0711eff59c61eecdf02c1 (patch) | |
tree | 78e465d06825069a9961a4b36d116b87ecd1fd5e | |
parent | b456ee1b53171c46b6f25c1c43d9fc17f6116745 (diff) | |
download | passt-1699083f291ca8e639d0711eff59c61eecdf02c1.tar passt-1699083f291ca8e639d0711eff59c61eecdf02c1.tar.gz passt-1699083f291ca8e639d0711eff59c61eecdf02c1.tar.bz2 passt-1699083f291ca8e639d0711eff59c61eecdf02c1.tar.lz passt-1699083f291ca8e639d0711eff59c61eecdf02c1.tar.xz passt-1699083f291ca8e639d0711eff59c61eecdf02c1.tar.zst passt-1699083f291ca8e639d0711eff59c61eecdf02c1.zip |
test: Make nstool hold robust against interruptions to control clients
Currently nstool die()s on essentially any error. In most cases that's
fine for our purposes. However, it's a problem when in "hold" mode and
getting an IO error on an accept()ed socket. This could just indicate that
the control client aborted prematurely, in which case we don't want to
kill of the namespace we're holding.
Adjust these to print an error, close() the control client socket and
carry on. In addition, we need to explicitly ignore SIGPIPE in order not
to be killed by an abruptly closed client connection.
Signed-off-by: David Gibson <david@gibson.dropbear.id.au>
Signed-off-by: Stefano Brivio <sbrivio@redhat.com>
-rw-r--r-- | test/nstool.c | 36 |
1 files changed, 26 insertions, 10 deletions
diff --git a/test/nstool.c b/test/nstool.c index 3f75edd..7ab5d2a 100644 --- a/test/nstool.c +++ b/test/nstool.c @@ -31,10 +31,15 @@ #define ARRAY_SIZE(a) ((int)(sizeof(a) / sizeof((a)[0]))) -#define die(...) \ - do { \ - fprintf(stderr, __VA_ARGS__); \ - exit(1); \ +#define die(...) \ + do { \ + fprintf(stderr, "nstool: " __VA_ARGS__); \ + exit(1); \ + } while (0) + +#define err(...) \ + do { \ + fprintf(stderr, "nstool: " __VA_ARGS__); \ } while (0) struct ns_type { @@ -156,6 +161,9 @@ static int connect_ctl(const char *sockpath, bool wait, static void cmd_hold(int argc, char *argv[]) { + struct sigaction sa = { + .sa_handler = SIG_IGN, + }; int fd = socket(AF_UNIX, SOCK_STREAM | SOCK_CLOEXEC, PF_UNIX); struct sockaddr_un addr; const char *sockpath = argv[1]; @@ -185,6 +193,10 @@ static void cmd_hold(int argc, char *argv[]) if (!getcwd(info.cwd, sizeof(info.cwd))) die("getcwd(): %s\n", strerror(errno)); + rc = sigaction(SIGPIPE, &sa, NULL); + if (rc) + die("sigaction(SIGPIPE): %s\n", strerror(errno)); + do { int afd = accept(fd, NULL, NULL); char buf; @@ -193,17 +205,21 @@ static void cmd_hold(int argc, char *argv[]) die("accept(): %s\n", strerror(errno)); rc = write(afd, &info, sizeof(info)); - if (rc < 0) - die("write(): %s\n", strerror(errno)); + if (rc < 0) { + err("holder write() to control socket: %s\n", + strerror(errno)); + } if ((size_t)rc < sizeof(info)) - die("short write() on control socket\n"); + err("holder short write() on control socket\n"); rc = read(afd, &buf, sizeof(buf)); - if (rc < 0) - die("read(): %s\n", strerror(errno)); + if (rc < 0) { + err("holder read() on control socket: %s\n", + strerror(errno)); + } close(afd); - } while (rc == 0); + } while (rc <= 0); unlink(sockpath); } |