From 04b56d9d9c38993e00f90cf13884a3685917d0ce Mon Sep 17 00:00:00 2001 From: Lennart Poettering Date: Wed, 25 Apr 2018 13:31:48 +0200 Subject: [PATCH 1/3] core: hide snapshot method calls from introspection data They are obsolete, let's hide them --- src/core/dbus-manager.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/core/dbus-manager.c b/src/core/dbus-manager.c index 2d651a2196..de3f9db445 100644 --- a/src/core/dbus-manager.c +++ b/src/core/dbus-manager.c @@ -2570,8 +2570,8 @@ const sd_bus_vtable bus_manager_vtable[] = { SD_BUS_METHOD("Subscribe", NULL, NULL, method_subscribe, SD_BUS_VTABLE_UNPRIVILEGED), SD_BUS_METHOD("Unsubscribe", NULL, NULL, method_unsubscribe, SD_BUS_VTABLE_UNPRIVILEGED), SD_BUS_METHOD("Dump", NULL, "s", method_dump, SD_BUS_VTABLE_UNPRIVILEGED), - SD_BUS_METHOD("CreateSnapshot", "sb", "o", method_refuse_snapshot, SD_BUS_VTABLE_UNPRIVILEGED), - SD_BUS_METHOD("RemoveSnapshot", "s", NULL, method_refuse_snapshot, SD_BUS_VTABLE_UNPRIVILEGED), + SD_BUS_METHOD("CreateSnapshot", "sb", "o", method_refuse_snapshot, SD_BUS_VTABLE_UNPRIVILEGED|SD_BUS_VTABLE_HIDDEN), + SD_BUS_METHOD("RemoveSnapshot", "s", NULL, method_refuse_snapshot, SD_BUS_VTABLE_UNPRIVILEGED|SD_BUS_VTABLE_HIDDEN), SD_BUS_METHOD("Reload", NULL, NULL, method_reload, SD_BUS_VTABLE_UNPRIVILEGED), SD_BUS_METHOD("Reexecute", NULL, NULL, method_reexecute, SD_BUS_VTABLE_UNPRIVILEGED), SD_BUS_METHOD("Exit", NULL, NULL, method_exit, 0), From 267dd427da9f7a215db772a9ac82656dcae683fb Mon Sep 17 00:00:00 2001 From: Lennart Poettering Date: Wed, 25 Apr 2018 13:34:47 +0200 Subject: [PATCH 2/3] core: add a new GetUnitByControlGroup() bus call This is useful for foreign container runtimes implementing the OCI runtime spec, which only wants to deal with cgroup paths. There's already an API to translate units into cgroup paths, with this we add the reverse. --- src/core/dbus-manager.c | 27 ++++++++++++++++++++++++++ src/core/org.freedesktop.systemd1.conf | 4 ++++ 2 files changed, 31 insertions(+) diff --git a/src/core/dbus-manager.c b/src/core/dbus-manager.c index de3f9db445..d5a9f524ea 100644 --- a/src/core/dbus-manager.c +++ b/src/core/dbus-manager.c @@ -544,6 +544,32 @@ static int method_get_unit_by_invocation_id(sd_bus_message *message, void *userd return sd_bus_reply_method_return(message, "o", path); } +static int method_get_unit_by_control_group(sd_bus_message *message, void *userdata, sd_bus_error *error) { + _cleanup_free_ char *path = NULL; + Manager *m = userdata; + const char *cgroup; + Unit *u; + int r; + + r = sd_bus_message_read(message, "s", &cgroup); + if (r < 0) + return r; + + u = manager_get_unit_by_cgroup(m, cgroup); + if (!u) + return sd_bus_error_setf(error, BUS_ERROR_NO_SUCH_UNIT, "Control group '%s' is not valid or not managed by this instance", cgroup); + + r = mac_selinux_unit_access_check(u, message, "status", error); + if (r < 0) + return r; + + path = unit_dbus_path(u); + if (!path) + return -ENOMEM; + + return sd_bus_reply_method_return(message, "o", path); +} + static int method_load_unit(sd_bus_message *message, void *userdata, sd_bus_error *error) { _cleanup_free_ char *path = NULL; Manager *m = userdata; @@ -2539,6 +2565,7 @@ const sd_bus_vtable bus_manager_vtable[] = { SD_BUS_METHOD("GetUnit", "s", "o", method_get_unit, SD_BUS_VTABLE_UNPRIVILEGED), SD_BUS_METHOD("GetUnitByPID", "u", "o", method_get_unit_by_pid, SD_BUS_VTABLE_UNPRIVILEGED), SD_BUS_METHOD("GetUnitByInvocationID", "ay", "o", method_get_unit_by_invocation_id, SD_BUS_VTABLE_UNPRIVILEGED), + SD_BUS_METHOD("GetUnitByControlGroup", "s", "o", method_get_unit_by_control_group, SD_BUS_VTABLE_UNPRIVILEGED), SD_BUS_METHOD("LoadUnit", "s", "o", method_load_unit, SD_BUS_VTABLE_UNPRIVILEGED), SD_BUS_METHOD("StartUnit", "ss", "o", method_start_unit, SD_BUS_VTABLE_UNPRIVILEGED), SD_BUS_METHOD("StartUnitReplace", "sss", "o", method_start_unit_replace, SD_BUS_VTABLE_UNPRIVILEGED), diff --git a/src/core/org.freedesktop.systemd1.conf b/src/core/org.freedesktop.systemd1.conf index 5e72fe7e8e..0114128a57 100644 --- a/src/core/org.freedesktop.systemd1.conf +++ b/src/core/org.freedesktop.systemd1.conf @@ -60,6 +60,10 @@ send_interface="org.freedesktop.systemd1.Manager" send_member="GetUnitByInvocationID"/> + + From 3ee9b2f6e77b341f5249f6797eef3e34d6c1f580 Mon Sep 17 00:00:00 2001 From: Lennart Poettering Date: Wed, 25 Apr 2018 13:36:06 +0200 Subject: [PATCH 3/3] doc: recommend GetUnitByControlGroup() in the docs --- doc/CGROUP_DELEGATION.md | 12 +++++++++++- 1 file changed, 11 insertions(+), 1 deletion(-) diff --git a/doc/CGROUP_DELEGATION.md b/doc/CGROUP_DELEGATION.md index 3124eabcc0..5f11a1c402 100644 --- a/doc/CGROUP_DELEGATION.md +++ b/doc/CGROUP_DELEGATION.md @@ -431,7 +431,17 @@ unified you (of course, I guess) need to provide only `/sys/fs/cgroup/` itself. replace it with an intermediary `tmpfs`, as long as the path to the delegated sub-tree remains accessible as-is. -5. ⚡ Think twice before delegating cgroupsv1 controllers to less privileged +5. ⚡ Currently, the algorithm for mapping between slice/scope/service unit + naming and their cgroup paths is not considered public API of systemd, and + may change in future versions. This means: it's best to avoid implementing a + local logic of translating cgroup paths to slice/scope/service names in your + program, or vice versa — it's likely going to break sooner or later. Use the + appropriate D-Bus API calls for that instead, so that systemd translates + this for you. (Specifically: each Unit object has a `ControlGroup` property + to get the cgroup for a unit. The method `GetUnitByControlGroup()` may be + used to get the unit for a cgroup.) + +6. ⚡ Think twice before delegating cgroupsv1 controllers to less privileged containers. It's not safe, you basically allow your containers to freeze the system with that and worse. Delegation is a strongpoint of cgroupsv2 though, and there it's safe to treat delegation boundaries as privilege boundaries.