]> git.ipfire.org Git - thirdparty/systemd.git/blame - src/core/dbus-scope.c
po: Update German translation
[thirdparty/systemd.git] / src / core / dbus-scope.c
CommitLineData
6c12b52e
LP
1/*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
2
3/***
4 This file is part of systemd.
5
6 Copyright 2013 Lennart Poettering
7
8 systemd is free software; you can redistribute it and/or modify it
9 under the terms of the GNU Lesser General Public License as published by
10 the Free Software Foundation; either version 2.1 of the License, or
11 (at your option) any later version.
12
13 systemd is distributed in the hope that it will be useful, but
14 WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 Lesser General Public License for more details.
17
18 You should have received a copy of the GNU Lesser General Public License
19 along with systemd; If not, see <http://www.gnu.org/licenses/>.
20***/
21
718db961
LP
22#include "unit.h"
23#include "scope.h"
6c12b52e 24#include "dbus-unit.h"
6c12b52e
LP
25#include "dbus-cgroup.h"
26#include "dbus-kill.h"
6c12b52e 27#include "dbus-scope.h"
283868e1 28#include "dbus.h"
718db961 29#include "bus-util.h"
2d4a39e7 30#include "bus-internal.h"
96aad8d1 31#include "bus-common-errors.h"
6c12b52e 32
a911bb9a
LP
33static int bus_scope_abandon(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
34 Scope *s = userdata;
4e2f8d27 35 int r;
a911bb9a
LP
36
37 assert(bus);
38 assert(message);
39 assert(s);
40
283868e1
SW
41 r = bus_verify_manage_unit_async(UNIT(s)->manager, message, error);
42 if (r < 0)
43 return r;
44 if (r == 0)
45 return 1; /* No authorization for now, but the async polkit stuff will call us again when it has it */
46
4e2f8d27
LP
47 r = scope_abandon(s);
48 if (sd_bus_error_is_set(error))
49 return r;
50
51 if (r == -ESTALE)
52 return sd_bus_error_setf(error, BUS_ERROR_SCOPE_NOT_RUNNING, "Scope %s is not running, cannot abandon.", UNIT(s)->id);
53
54 return sd_bus_reply_method_return(message, NULL);
a911bb9a
LP
55}
56
718db961 57static BUS_DEFINE_PROPERTY_GET_ENUM(property_get_result, scope_result, ScopeResult);
6c12b52e 58
718db961
LP
59const sd_bus_vtable bus_scope_vtable[] = {
60 SD_BUS_VTABLE_START(0),
2d4a39e7 61 SD_BUS_PROPERTY("Controller", "s", NULL, offsetof(Scope, controller), SD_BUS_VTABLE_PROPERTY_CONST),
556089dc 62 SD_BUS_PROPERTY("TimeoutStopUSec", "t", bus_property_get_usec, offsetof(Scope, timeout_stop_usec), SD_BUS_VTABLE_PROPERTY_CONST),
718db961 63 SD_BUS_PROPERTY("Result", "s", property_get_result, offsetof(Scope, result), SD_BUS_VTABLE_PROPERTY_EMITS_CHANGE),
2d4a39e7 64 SD_BUS_SIGNAL("RequestStop", NULL, 0),
a911bb9a 65 SD_BUS_METHOD("Abandon", NULL, NULL, bus_scope_abandon, 0),
718db961
LP
66 SD_BUS_VTABLE_END
67};
6c12b52e 68
9f2e86af 69static int bus_scope_set_transient_property(
6c12b52e
LP
70 Scope *s,
71 const char *name,
718db961 72 sd_bus_message *message,
6c12b52e 73 UnitSetPropertiesMode mode,
718db961 74 sd_bus_error *error) {
6c12b52e
LP
75
76 int r;
77
6c12b52e 78 assert(s);
718db961
LP
79 assert(name);
80 assert(message);
6c12b52e
LP
81
82 if (streq(name, "PIDs")) {
294a90cc 83 unsigned n = 0;
718db961 84 uint32_t pid;
6c12b52e 85
718db961
LP
86 r = sd_bus_message_enter_container(message, 'a', "u");
87 if (r < 0)
88 return r;
6c12b52e 89
718db961 90 while ((r = sd_bus_message_read(message, "u", &pid)) > 0) {
6c12b52e
LP
91
92 if (pid <= 1)
93 return -EINVAL;
94
adb3a45d 95 if (mode != UNIT_CHECK) {
a911bb9a 96 r = unit_watch_pid(UNIT(s), pid);
adb3a45d
LP
97 if (r < 0 && r != -EEXIST)
98 return r;
99 }
6c12b52e 100
adb3a45d 101 n++;
6c12b52e 102 }
718db961
LP
103 if (r < 0)
104 return r;
105
106 r = sd_bus_message_exit_container(message);
107 if (r < 0)
108 return r;
6c12b52e 109
adb3a45d 110 if (n <= 0)
6c12b52e
LP
111 return -EINVAL;
112
113 return 1;
cc23f9f1 114
2d4a39e7
LP
115 } else if (streq(name, "Controller")) {
116 const char *controller;
117 char *c;
118
119 r = sd_bus_message_read(message, "s", &controller);
120 if (r < 0)
121 return r;
122
123 if (!isempty(controller) && !service_name_is_valid(controller))
124 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Controller '%s' is not a valid bus name.", controller);
125
126 if (mode != UNIT_CHECK) {
127 if (isempty(controller))
128 c = NULL;
129 else {
130 c = strdup(controller);
131 if (!c)
132 return -ENOMEM;
133 }
134
135 free(s->controller);
136 s->controller = c;
137 }
138
139 return 1;
140
cc23f9f1
LP
141 } else if (streq(name, "TimeoutStopUSec")) {
142
cc23f9f1 143 if (mode != UNIT_CHECK) {
718db961
LP
144 r = sd_bus_message_read(message, "t", &s->timeout_stop_usec);
145 if (r < 0)
146 return r;
147
de0671ee 148 unit_write_drop_in_format(UNIT(s), mode, name, "[Scope]\nTimeoutStopSec="USEC_FMT"us\n", s->timeout_stop_usec);
718db961
LP
149 } else {
150 r = sd_bus_message_skip(message, "t");
151 if (r < 0)
152 return r;
cc23f9f1
LP
153 }
154
155 return 1;
6c12b52e
LP
156 }
157
158 return 0;
159}
160
161int bus_scope_set_property(
162 Unit *u,
163 const char *name,
718db961 164 sd_bus_message *message,
6c12b52e 165 UnitSetPropertiesMode mode,
718db961 166 sd_bus_error *error) {
6c12b52e
LP
167
168 Scope *s = SCOPE(u);
169 int r;
170
718db961 171 assert(s);
6c12b52e 172 assert(name);
718db961 173 assert(message);
6c12b52e 174
718db961 175 r = bus_cgroup_set_property(u, &s->cgroup_context, name, message, mode, error);
6c12b52e
LP
176 if (r != 0)
177 return r;
178
179 if (u->load_state == UNIT_STUB) {
180 /* While we are created we still accept PIDs */
181
718db961 182 r = bus_scope_set_transient_property(s, name, message, mode, error);
6c12b52e
LP
183 if (r != 0)
184 return r;
a6c0353b 185
718db961 186 r = bus_kill_context_set_transient_property(u, &s->kill_context, name, message, mode, error);
a6c0353b
LP
187 if (r != 0)
188 return r;
6c12b52e
LP
189 }
190
191 return 0;
192}
193
194int bus_scope_commit_properties(Unit *u) {
195 assert(u);
196
bc432dc7 197 unit_update_cgroup_members_masks(u);
6c12b52e 198 unit_realize_cgroup(u);
bc432dc7 199
6c12b52e
LP
200 return 0;
201}
2d4a39e7
LP
202
203int bus_scope_send_request_stop(Scope *s) {
204 _cleanup_bus_message_unref_ sd_bus_message *m = NULL;
205 _cleanup_free_ char *p = NULL;
206 int r;
207
208 assert(s);
209
210 if (!s->controller)
211 return 0;
212
213 p = unit_dbus_path(UNIT(s));
214 if (!p)
215 return -ENOMEM;
216
217 r = sd_bus_message_new_signal(
218 UNIT(s)->manager->api_bus,
151b9b96 219 &m,
2d4a39e7
LP
220 p,
221 "org.freedesktop.systemd1.Scope",
151b9b96 222 "RequestStop");
2d4a39e7
LP
223 if (r < 0)
224 return r;
225
226 return sd_bus_send_to(UNIT(s)->manager->api_bus, m, /* s->controller */ NULL, NULL);
227}