]> git.ipfire.org Git - thirdparty/systemd.git/blobdiff - src/core/dbus-execute.c
tree-wide: drop license boilerplate
[thirdparty/systemd.git] / src / core / dbus-execute.c
index 352852a75ed0838bee36894fabf47015b3d18bd6..09dc93e53b04caefe5b6fd25537bd0d2ecd6275e 100644 (file)
@@ -3,21 +3,9 @@
   This file is part of systemd.
 
   Copyright 2010 Lennart Poettering
-
-  systemd is free software; you can redistribute it and/or modify it
-  under the terms of the GNU Lesser General Public License as published by
-  the Free Software Foundation; either version 2.1 of the License, or
-  (at your option) any later version.
-
-  systemd 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
-  Lesser General Public License for more details.
-
-  You should have received a copy of the GNU Lesser General Public License
-  along with systemd; If not, see <http://www.gnu.org/licenses/>.
 ***/
 
+#include <sys/mount.h>
 #include <sys/prctl.h>
 #include <stdio_ext.h>
 
@@ -424,10 +412,8 @@ static int property_get_syscall_filter(
                                 if (r < 0)
                                         return -ENOMEM;
                         }
-                } else {
-                        s = name;
-                        name = NULL;
-                }
+                } else
+                        s = TAKE_PTR(name);
 
                 r = strv_consume(&l, s);
                 if (r < 0)
@@ -781,6 +767,42 @@ static int property_get_bind_paths(
         return sd_bus_message_close_container(reply);
 }
 
+static int property_get_temporary_filesystems(
+                sd_bus *bus,
+                const char *path,
+                const char *interface,
+                const char *property,
+                sd_bus_message *reply,
+                void *userdata,
+                sd_bus_error *error) {
+
+        ExecContext *c = userdata;
+        unsigned i;
+        int r;
+
+        assert(bus);
+        assert(c);
+        assert(property);
+        assert(reply);
+
+        r = sd_bus_message_open_container(reply, 'a', "(ss)");
+        if (r < 0)
+                return r;
+
+        for (i = 0; i < c->n_temporary_filesystems; i++) {
+                TemporaryFileSystem *t = c->temporary_filesystems + i;
+
+                r = sd_bus_message_append(
+                                reply, "(ss)",
+                                t->path,
+                                t->options);
+                if (r < 0)
+                        return r;
+        }
+
+        return sd_bus_message_close_container(reply);
+}
+
 static int property_get_log_extra_fields(
                 sd_bus *bus,
                 const char *path,
@@ -934,6 +956,7 @@ const sd_bus_vtable bus_exec_vtable[] = {
         SD_BUS_PROPERTY("RestrictNamespaces", "t", bus_property_get_ulong, offsetof(ExecContext, restrict_namespaces), SD_BUS_VTABLE_PROPERTY_CONST),
         SD_BUS_PROPERTY("BindPaths", "a(ssbt)", property_get_bind_paths, 0, SD_BUS_VTABLE_PROPERTY_CONST),
         SD_BUS_PROPERTY("BindReadOnlyPaths", "a(ssbt)", property_get_bind_paths, 0, SD_BUS_VTABLE_PROPERTY_CONST),
+        SD_BUS_PROPERTY("TemporaryFileSystem", "a(ss)", property_get_temporary_filesystems, 0, SD_BUS_VTABLE_PROPERTY_CONST),
         SD_BUS_PROPERTY("MountAPIVFS", "b", bus_property_get_bool, offsetof(ExecContext, mount_apivfs), SD_BUS_VTABLE_PROPERTY_CONST),
         SD_BUS_PROPERTY("KeyringMode", "s", property_get_exec_keyring_mode, offsetof(ExecContext, keyring_mode), SD_BUS_VTABLE_PROPERTY_CONST),
 
@@ -1088,8 +1111,7 @@ int bus_set_transient_exec_command(
                                 return -ENOMEM;
                         }
 
-                        c->argv = argv;
-                        argv = NULL;
+                        c->argv = TAKE_PTR(argv);
 
                         c->flags = b ? EXEC_COMMAND_IGNORE_FAILURE : 0;
 
@@ -1174,7 +1196,9 @@ static const char* mount_propagation_flags_to_string_with_check(unsigned long n)
 
 static BUS_DEFINE_SET_TRANSIENT(nsec, "t", uint64_t, nsec_t, NSEC_FMT);
 static BUS_DEFINE_SET_TRANSIENT_IS_VALID(log_level, "i", int32_t, int, "%" PRIi32, log_level_is_valid);
+#if HAVE_SECCOMP
 static BUS_DEFINE_SET_TRANSIENT_IS_VALID(errno, "i", int32_t, int, "%" PRIi32, errno_is_valid);
+#endif
 static BUS_DEFINE_SET_TRANSIENT_IS_VALID(sched_priority, "i", int32_t, int, "%" PRIi32, sched_priority_is_valid);
 static BUS_DEFINE_SET_TRANSIENT_IS_VALID(nice, "i", int32_t, int, "%" PRIi32, nice_is_valid);
 static BUS_DEFINE_SET_TRANSIENT_PARSE(std_input, ExecInput, exec_input_from_string);
@@ -1479,7 +1503,7 @@ int bus_exec_context_set_transient_property(
                                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Journal field invalid");
 
                         if (!UNIT_WRITE_FLAGS_NOOP(flags)) {
-                                t = realloc_multiply(c->log_extra_fields, sizeof(struct iovec), c->n_log_extra_fields+1);
+                                t = reallocarray(c->log_extra_fields, c->n_log_extra_fields+1, sizeof(struct iovec));
                                 if (!t)
                                         return -ENOMEM;
                                 c->log_extra_fields = t;
@@ -1563,7 +1587,7 @@ int bus_exec_context_set_transient_property(
                                 c->syscall_whitelist = whitelist;
 
                                 if (c->syscall_whitelist) {
-                                        r = seccomp_parse_syscall_filter(invert, "@default", -1, c->syscall_filter, true);
+                                        r = seccomp_parse_syscall_filter("@default", -1, c->syscall_filter, SECCOMP_PARSE_WHITELIST | (invert ? SECCOMP_PARSE_INVERT : 0));
                                         if (r < 0)
                                                 return r;
                                 }
@@ -1577,7 +1601,7 @@ int bus_exec_context_set_transient_property(
                                 if (r < 0)
                                         return r;
 
-                                r = seccomp_parse_syscall_filter(invert, n, e, c->syscall_filter, c->syscall_whitelist);
+                                r = seccomp_parse_syscall_filter(n, e, c->syscall_filter, (invert ? SECCOMP_PARSE_INVERT : 0) | (c->syscall_whitelist ? SECCOMP_PARSE_WHITELIST : 0));
                                 if (r < 0)
                                         return r;
                         }
@@ -2291,11 +2315,7 @@ int bus_exec_context_set_transient_property(
                 int ignore;
                 const char *s;
 
-                r = sd_bus_message_enter_container(message, 'r', "bs");
-                if (r < 0)
-                        return r;
-
-                r = sd_bus_message_read(message, "bs", &ignore, &s);
+                r = sd_bus_message_read(message, "(bs)", &ignore, &s);
                 if (r < 0)
                         return r;
 
@@ -2326,24 +2346,16 @@ int bus_exec_context_set_transient_property(
                 return 1;
 
         } else if (STR_IN_SET(name, "BindPaths", "BindReadOnlyPaths")) {
-                unsigned empty = true;
+                const char *source, *destination;
+                int ignore_enoent;
+                uint64_t mount_flags;
+                bool empty = true;
 
                 r = sd_bus_message_enter_container(message, 'a', "(ssbt)");
                 if (r < 0)
                         return r;
 
-                while ((r = sd_bus_message_enter_container(message, 'r', "ssbt")) > 0) {
-                        const char *source, *destination;
-                        int ignore_enoent;
-                        uint64_t mount_flags;
-
-                        r = sd_bus_message_read(message, "ssbt", &source, &destination, &ignore_enoent, &mount_flags);
-                        if (r < 0)
-                                return r;
-
-                        r = sd_bus_message_exit_container(message);
-                        if (r < 0)
-                                return r;
+                while ((r = sd_bus_message_read(message, "(ssbt)", &source, &destination, &ignore_enoent, &mount_flags)) > 0) {
 
                         if (!path_is_absolute(source))
                                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Source path %s is not absolute.", source);
@@ -2391,6 +2403,51 @@ int bus_exec_context_set_transient_property(
                         unit_write_settingf(u, flags, name, "%s=", name);
                 }
 
+                return 1;
+
+        } else if (streq(name, "TemporaryFileSystem")) {
+                const char *path, *options;
+                bool empty = true;
+
+                r = sd_bus_message_enter_container(message, 'a', "(ss)");
+                if (r < 0)
+                        return r;
+
+                while ((r = sd_bus_message_read(message, "(ss)", &path, &options)) > 0) {
+
+                        if (!path_is_absolute(path))
+                                return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Mount point %s is not absolute.", path);
+
+                        if (!UNIT_WRITE_FLAGS_NOOP(flags)) {
+                                r = temporary_filesystem_add(&c->temporary_filesystems, &c->n_temporary_filesystems, path, options);
+                                if (r < 0)
+                                        return r;
+
+                                unit_write_settingf(
+                                                u, flags|UNIT_ESCAPE_SPECIFIERS, name,
+                                                "%s=%s:%s",
+                                                name,
+                                                path,
+                                                options);
+                        }
+
+                        empty = false;
+                }
+                if (r < 0)
+                        return r;
+
+                r = sd_bus_message_exit_container(message);
+                if (r < 0)
+                        return r;
+
+                if (empty) {
+                        temporary_filesystem_free_many(c->temporary_filesystems, c->n_temporary_filesystems);
+                        c->temporary_filesystems = NULL;
+                        c->n_temporary_filesystems = 0;
+
+                        unit_write_settingf(u, flags, name, "%s=", name);
+                }
+
                 return 1;
         }