tools/xenstore: handle CLOEXEC flag for local files and pipes
authorJuergen Gross <jgross@suse.com>
Wed, 13 Jan 2021 13:00:19 +0000 (14:00 +0100)
committerJuergen Gross <jgross@suse.com>
Thu, 21 Jan 2021 16:31:37 +0000 (17:31 +0100)
For support of live update the locally used files need to have the
"close on exec" flag set. Fortunately the used Xen libraries are
already doing this, so only the logging and tdb related files and
pipes are affected. openlog() has the close on exec attribute, too.

In order to be able to keep the event channels open specify the
XENEVTCHN_NO_CLOEXEC flag when calling xenevtchn_open().

Signed-off-by: Juergen Gross <jgross@suse.com>
Acked-by: Julien Grall <julien.grall@amazon.com>
Acked-by: Wei Liu <wl@xen.org>
tools/xenstore/xenstored_control.c
tools/xenstore/xenstored_core.c
tools/xenstore/xenstored_core.h
tools/xenstore/xenstored_domain.c
tools/xenstore/xenstored_posix.c

index 72a03c99d4031abdaa91fbb9379f65863ad3e72c..63b1f9a8b7bd837b3ef64746ffc78fd52a131c73 100644 (file)
@@ -41,6 +41,7 @@ Interactive commands for Xen Store Daemon.
 #define MAP_ANONYMOUS MAP_ANON
 #endif
 
+#ifndef NO_LIVE_UPDATE
 struct live_update {
        /* For verification the correct connection is acting. */
        struct connection *conn;
@@ -90,6 +91,7 @@ static const char *lu_begin(struct connection *conn)
 
        return NULL;
 }
+#endif
 
 struct cmd_s {
        char *cmd;
@@ -214,6 +216,7 @@ static int do_control_print(void *ctx, struct connection *conn,
        return 0;
 }
 
+#ifndef NO_LIVE_UPDATE
 static const char *lu_abort(const void *ctx, struct connection *conn)
 {
        syslog(LOG_INFO, "live-update: abort\n");
@@ -559,6 +562,7 @@ static int do_control_lu(void *ctx, struct connection *conn,
        send_reply(conn, XS_CONTROL, resp, strlen(resp) + 1);
        return 0;
 }
+#endif
 
 static int do_control_help(void *, struct connection *, char **, int);
 
@@ -566,6 +570,7 @@ static struct cmd_s cmds[] = {
        { "check", do_control_check, "" },
        { "log", do_control_log, "on|off" },
 
+#ifndef NO_LIVE_UPDATE
        /*
         * The parameters are those of the xenstore-control utility!
         * Depending on environment (Mini-OS or daemon) the live-update
@@ -585,6 +590,7 @@ static struct cmd_s cmds[] = {
        { "live-update", do_control_lu,
                "[-c <cmdline>] [-F] [-t <timeout>] <file>\n"
                "    Default timeout is 60 seconds.", 4 },
+#endif
 #ifdef __MINIOS__
        { "memreport", do_control_memreport, "" },
 #else
index 97f9f0ffa924a0cc1eae9fe3e0ce6b9e75eaa8b7..2ef4534de7edfaa8ec5fa81cdae5bb7d383f2d27 100644 (file)
@@ -198,7 +198,8 @@ void reopen_log(void)
        if (tracefile) {
                close_log();
 
-               tracefd = open(tracefile, O_WRONLY|O_CREAT|O_APPEND, 0600);
+               tracefd = open(tracefile,
+                              O_WRONLY | O_CREAT | O_APPEND | O_CLOEXEC, 0600);
 
                if (tracefd < 0)
                        perror("Could not open tracefile");
@@ -1696,7 +1697,8 @@ static void setup_structure(void)
        if (!(tdb_flags & TDB_INTERNAL))
                unlink(tdbname);
 
-       tdb_ctx = tdb_open_ex(tdbname, 7919, tdb_flags, O_RDWR|O_CREAT|O_EXCL,
+       tdb_ctx = tdb_open_ex(tdbname, 7919, tdb_flags,
+                             O_RDWR | O_CREAT | O_EXCL | O_CLOEXEC,
                              0640, &tdb_logger, NULL);
        if (!tdb_ctx)
                barf_perror("Could not create tdb file %s", tdbname);
index 22287ddfe94a303d9f18cda0d2395121ded4ea9d..c7567eaf0b6e1af88a082077856c8173409dcd96 100644 (file)
 #include "tdb.h"
 #include "hashtable.h"
 
+#ifndef O_CLOEXEC
+#define O_CLOEXEC 0
+/* O_CLOEXEC support is needed for Live Update in the daemon case. */
+#ifndef __MINIOS__
+#define NO_LIVE_UPDATE
+#endif
+#endif
+
 /* DEFAULT_BUFFER_SIZE should be large enough for each errno string. */
 #define DEFAULT_BUFFER_SIZE 16
 
index 919a4d98cf8bf89add4e092e3348cd57903bb1ca..38d250fbed67d252e1205166381939f226850950 100644 (file)
@@ -743,7 +743,7 @@ void domain_init(void)
 
        talloc_set_destructor(xgt_handle, close_xgt_handle);
 
-       xce_handle = xenevtchn_open(NULL, 0);
+       xce_handle = xenevtchn_open(NULL, XENEVTCHN_NO_CLOEXEC);
 
        if (xce_handle == NULL)
                barf_perror("Failed to open evtchn device");
index 1f9603fea2dc64e18dd465c48287ad33e4dd2aed..ae3e63e07f051776895a7c514cb1bfc975909753 100644 (file)
@@ -90,9 +90,21 @@ void finish_daemonize(void)
 
 void init_pipe(int reopen_log_pipe[2])
 {
+       int flags;
+       unsigned int i;
+
        if (pipe(reopen_log_pipe)) {
                barf_perror("pipe");
        }
+
+       for (i = 0; i < 2; i++) {
+               flags = fcntl(reopen_log_pipe[i], F_GETFD);
+               if (flags < 0)
+                       barf_perror("pipe get flags");
+               flags |= FD_CLOEXEC;
+               if (fcntl(reopen_log_pipe[i],  F_SETFD, flags) < 0)
+                       barf_perror("pipe set flags");
+       }
 }
 
 void unmap_xenbus(void *interface)