chiark / gitweb /
f1e344c180edeed5dbe30111c5744fdf4ca15fa8
[elogind.git] / src / core / dbus-manager.c
1 /*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
2
3 /***
4   This file is part of systemd.
5
6   Copyright 2010 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
22 #include <errno.h>
23 #include <unistd.h>
24
25 #include "log.h"
26 #include "strv.h"
27 #include "build.h"
28 #include "install.h"
29 #include "selinux-access.h"
30 #include "watchdog.h"
31 #include "hwclock.h"
32 #include "path-util.h"
33 #include "virt.h"
34 #include "architecture.h"
35 #include "env-util.h"
36 #include "dbus.h"
37 #include "dbus-manager.h"
38 #include "dbus-unit.h"
39 #include "dbus-snapshot.h"
40 #include "dbus-client-track.h"
41 #include "dbus-execute.h"
42 #include "bus-errors.h"
43
44 static int property_get_version(
45                 sd_bus *bus,
46                 const char *path,
47                 const char *interface,
48                 const char *property,
49                 sd_bus_message *reply,
50                 void *userdata,
51                 sd_bus_error *error) {
52
53         assert(bus);
54         assert(reply);
55
56         return sd_bus_message_append(reply, "s", PACKAGE_VERSION);
57 }
58
59 static int property_get_features(
60                 sd_bus *bus,
61                 const char *path,
62                 const char *interface,
63                 const char *property,
64                 sd_bus_message *reply,
65                 void *userdata,
66                 sd_bus_error *error) {
67
68         assert(bus);
69         assert(reply);
70
71         return sd_bus_message_append(reply, "s", SYSTEMD_FEATURES);
72 }
73
74 static int property_get_virtualization(
75                 sd_bus *bus,
76                 const char *path,
77                 const char *interface,
78                 const char *property,
79                 sd_bus_message *reply,
80                 void *userdata,
81                 sd_bus_error *error) {
82
83         const char *id = NULL;
84
85         assert(bus);
86         assert(reply);
87
88         detect_virtualization(&id);
89
90         return sd_bus_message_append(reply, "s", id);
91 }
92
93 static int property_get_architecture(
94                 sd_bus *bus,
95                 const char *path,
96                 const char *interface,
97                 const char *property,
98                 sd_bus_message *reply,
99                 void *userdata,
100                 sd_bus_error *error) {
101
102         assert(bus);
103         assert(reply);
104
105         return sd_bus_message_append(reply, "s", architecture_to_string(uname_architecture()));
106 }
107
108 static int property_get_tainted(
109                 sd_bus *bus,
110                 const char *path,
111                 const char *interface,
112                 const char *property,
113                 sd_bus_message *reply,
114                 void *userdata,
115                 sd_bus_error *error) {
116
117         char buf[sizeof("split-usr:mtab-not-symlink:cgroups-missing:local-hwclock:")] = "", *e = buf;
118         _cleanup_free_ char *p = NULL;
119         Manager *m = userdata;
120
121         assert(bus);
122         assert(reply);
123         assert(m);
124
125         if (m->taint_usr)
126                 e = stpcpy(e, "split-usr:");
127
128         if (readlink_malloc("/etc/mtab", &p) < 0)
129                 e = stpcpy(e, "mtab-not-symlink:");
130
131         if (access("/proc/cgroups", F_OK) < 0)
132                 e = stpcpy(e, "cgroups-missing:");
133
134         if (hwclock_is_localtime() > 0)
135                 e = stpcpy(e, "local-hwclock:");
136
137         /* remove the last ':' */
138         if (e != buf)
139                 e[-1] = 0;
140
141         return sd_bus_message_append(reply, "s", buf);
142 }
143
144 static int property_get_log_target(
145                 sd_bus *bus,
146                 const char *path,
147                 const char *interface,
148                 const char *property,
149                 sd_bus_message *reply,
150                 void *userdata,
151                 sd_bus_error *error) {
152
153         assert(bus);
154         assert(reply);
155
156         return sd_bus_message_append(reply, "s", log_target_to_string(log_get_target()));
157 }
158
159 static int property_set_log_target(
160                 sd_bus *bus,
161                 const char *path,
162                 const char *interface,
163                 const char *property,
164                 sd_bus_message *value,
165                 void *userdata,
166                 sd_bus_error *error) {
167
168         const char *t;
169         int r;
170
171         assert(bus);
172         assert(value);
173
174         r = sd_bus_message_read(value, "s", &t);
175         if (r < 0)
176                 return r;
177
178         return log_set_target_from_string(t);
179 }
180
181 static int property_get_log_level(
182                 sd_bus *bus,
183                 const char *path,
184                 const char *interface,
185                 const char *property,
186                 sd_bus_message *reply,
187                 void *userdata,
188                 sd_bus_error *error) {
189
190         _cleanup_free_ char *t = NULL;
191         int r;
192
193         assert(bus);
194         assert(reply);
195
196         r = log_level_to_string_alloc(log_get_max_level(), &t);
197         if (r < 0)
198                 return r;
199
200         return sd_bus_message_append(reply, "s", t);
201 }
202
203 static int property_set_log_level(
204                 sd_bus *bus,
205                 const char *path,
206                 const char *interface,
207                 const char *property,
208                 sd_bus_message *value,
209                 void *userdata,
210                 sd_bus_error *error) {
211
212         const char *t;
213         int r;
214
215         assert(bus);
216         assert(value);
217
218         r = sd_bus_message_read(value, "s", &t);
219         if (r < 0)
220                 return r;
221
222         return log_set_max_level_from_string(t);
223 }
224
225 static int property_get_n_names(
226                 sd_bus *bus,
227                 const char *path,
228                 const char *interface,
229                 const char *property,
230                 sd_bus_message *reply,
231                 void *userdata,
232                 sd_bus_error *error) {
233
234         Manager *m = userdata;
235
236         assert(bus);
237         assert(reply);
238         assert(m);
239
240         return sd_bus_message_append(reply, "u", (uint32_t) hashmap_size(m->units));
241 }
242
243 static int property_get_n_jobs(
244                 sd_bus *bus,
245                 const char *path,
246                 const char *interface,
247                 const char *property,
248                 sd_bus_message *reply,
249                 void *userdata,
250                 sd_bus_error *error) {
251
252         Manager *m = userdata;
253
254         assert(bus);
255         assert(reply);
256         assert(m);
257
258         return sd_bus_message_append(reply, "u", (uint32_t) hashmap_size(m->jobs));
259 }
260
261 static int property_get_progress(
262                 sd_bus *bus,
263                 const char *path,
264                 const char *interface,
265                 const char *property,
266                 sd_bus_message *reply,
267                 void *userdata,
268                 sd_bus_error *error) {
269
270         Manager *m = userdata;
271         double d;
272
273         assert(bus);
274         assert(reply);
275         assert(m);
276
277         if (dual_timestamp_is_set(&m->finish_timestamp))
278                 d = 1.0;
279         else
280                 d = 1.0 - ((double) hashmap_size(m->jobs) / (double) m->n_installed_jobs);
281
282         return sd_bus_message_append(reply, "d", d);
283 }
284
285 static int property_set_runtime_watchdog(
286                 sd_bus *bus,
287                 const char *path,
288                 const char *interface,
289                 const char *property,
290                 sd_bus_message *value,
291                 void *userdata,
292                 sd_bus_error *error) {
293
294         usec_t *t = userdata;
295         int r;
296
297         assert(bus);
298         assert(value);
299
300         assert_cc(sizeof(usec_t) == sizeof(uint64_t));
301
302         r = sd_bus_message_read(value, "t", t);
303         if (r < 0)
304                 return r;
305
306         return watchdog_set_timeout(t);
307 }
308
309 static int method_get_unit(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
310         _cleanup_free_ char *path = NULL;
311         Manager *m = userdata;
312         const char *name;
313         Unit *u;
314         int r;
315
316         assert(bus);
317         assert(message);
318         assert(m);
319
320         r = sd_bus_message_read(message, "s", &name);
321         if (r < 0)
322                 return r;
323
324         u = manager_get_unit(m, name);
325         if (!u)
326                 return sd_bus_error_setf(error, BUS_ERROR_NO_SUCH_UNIT, "Unit %s not loaded.", name);
327
328         r = selinux_unit_access_check(u, bus, message, "status", error);
329         if (r < 0)
330                 return r;
331
332         path = unit_dbus_path(u);
333         if (!path)
334                 return -ENOMEM;
335
336         return sd_bus_reply_method_return(message, "o", path);
337 }
338
339 static int method_get_unit_by_pid(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
340         _cleanup_free_ char *path = NULL;
341         Manager *m = userdata;
342         pid_t pid;
343         Unit *u;
344         int r;
345
346         assert(bus);
347         assert(message);
348         assert(m);
349
350         assert_cc(sizeof(pid_t) == sizeof(uint32_t));
351
352         r = sd_bus_message_read(message, "u", &pid);
353         if (r < 0)
354                 return r;
355
356         if (pid == 0) {
357                 _cleanup_bus_creds_unref_ sd_bus_creds *creds = NULL;
358
359                 r = sd_bus_query_sender_creds(message, SD_BUS_CREDS_PID, &creds);
360                 if (r < 0)
361                         return r;
362
363                 r = sd_bus_creds_get_pid(creds, &pid);
364                 if (r < 0)
365                         return r;
366         }
367
368         u = manager_get_unit_by_pid(m, pid);
369         if (!u)
370                 return sd_bus_error_setf(error, BUS_ERROR_NO_UNIT_FOR_PID, "PID %u does not belong to any loaded unit.", pid);
371
372         r = selinux_unit_access_check(u, bus, message, "status", error);
373         if (r < 0)
374                 return r;
375
376         path = unit_dbus_path(u);
377         if (!path)
378                 return -ENOMEM;
379
380         return sd_bus_reply_method_return(message, "o", path);
381 }
382
383 static int method_load_unit(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
384         _cleanup_free_ char *path = NULL;
385         Manager *m = userdata;
386         const char *name;
387         Unit *u;
388         int r;
389
390         assert(bus);
391         assert(message);
392         assert(m);
393
394         r = sd_bus_message_read(message, "s", &name);
395         if (r < 0)
396                 return r;
397
398         r = manager_load_unit(m, name, NULL, error, &u);
399         if (r < 0)
400                 return r;
401
402         r = selinux_unit_access_check(u, bus, message, "status", error);
403         if (r < 0)
404                 return r;
405
406         path = unit_dbus_path(u);
407         if (!path)
408                 return -ENOMEM;
409
410         return sd_bus_reply_method_return(message, "o", path);
411 }
412
413 static int method_start_unit_generic(sd_bus *bus, sd_bus_message *message, Manager *m, JobType job_type, bool reload_if_possible, sd_bus_error *error) {
414         const char *name;
415         Unit *u;
416         int r;
417
418         assert(bus);
419         assert(message);
420         assert(m);
421
422         r = sd_bus_message_read(message, "s", &name);
423         if (r < 0)
424                 return r;
425
426         r = manager_load_unit(m, name, NULL, error, &u);
427         if (r < 0)
428                 return r;
429
430         return bus_unit_method_start_generic(bus, message, u, job_type, reload_if_possible, error);
431 }
432
433 static int method_start_unit(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
434         return method_start_unit_generic(bus, message, userdata, JOB_START, false, error);
435 }
436
437 static int method_stop_unit(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
438         return method_start_unit_generic(bus, message, userdata, JOB_STOP, false, error);
439 }
440
441 static int method_reload_unit(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
442         return method_start_unit_generic(bus, message, userdata, JOB_RELOAD, false, error);
443 }
444
445 static int method_restart_unit(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
446         return method_start_unit_generic(bus, message, userdata, JOB_RESTART, false, error);
447 }
448
449 static int method_try_restart_unit(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
450         return method_start_unit_generic(bus, message, userdata, JOB_TRY_RESTART, false, error);
451 }
452
453 static int method_reload_or_restart_unit(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
454         return method_start_unit_generic(bus, message, userdata, JOB_RESTART, true, error);
455 }
456
457 static int method_reload_or_try_restart_unit(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
458         return method_start_unit_generic(bus, message, userdata, JOB_TRY_RESTART, true, error);
459 }
460
461 static int method_start_unit_replace(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
462         Manager *m = userdata;
463         const char *old_name;
464         Unit *u;
465         int r;
466
467         assert(bus);
468         assert(message);
469         assert(m);
470
471         r = sd_bus_message_read(message, "s", &old_name);
472         if (r < 0)
473                 return r;
474
475         u = manager_get_unit(m, old_name);
476         if (!u || !u->job || u->job->type != JOB_START)
477                 return sd_bus_error_setf(error, BUS_ERROR_NO_SUCH_JOB, "No job queued for unit %s", old_name);
478
479         return method_start_unit_generic(bus, message, m, JOB_START, false, error);
480 }
481
482 static int method_kill_unit(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
483         Manager *m = userdata;
484         const char *name;
485         Unit *u;
486         int r;
487
488         assert(bus);
489         assert(message);
490         assert(m);
491
492         r = sd_bus_message_read(message, "s", &name);
493         if (r < 0)
494                 return r;
495
496         u = manager_get_unit(m, name);
497         if (!u)
498                 return sd_bus_error_setf(error, BUS_ERROR_NO_SUCH_UNIT, "Unit %s is not loaded.", name);
499
500         return bus_unit_method_kill(bus, message, u, error);
501 }
502
503 static int method_reset_failed_unit(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
504         Manager *m = userdata;
505         const char *name;
506         Unit *u;
507         int r;
508
509         assert(bus);
510         assert(message);
511         assert(m);
512
513         r = sd_bus_message_read(message, "s", &name);
514         if (r < 0)
515                 return r;
516
517         u = manager_get_unit(m, name);
518         if (!u)
519                 return sd_bus_error_setf(error, BUS_ERROR_NO_SUCH_UNIT, "Unit %s is not loaded.", name);
520
521         return bus_unit_method_reset_failed(bus, message, u, error);
522 }
523
524 static int method_set_unit_properties(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
525         Manager *m = userdata;
526         const char *name;
527         Unit *u;
528         int r;
529
530         assert(bus);
531         assert(message);
532         assert(m);
533
534         r = sd_bus_message_read(message, "s", &name);
535         if (r < 0)
536                 return r;
537
538         u = manager_get_unit(m, name);
539         if (!u)
540                 return sd_bus_error_setf(error, BUS_ERROR_NO_SUCH_UNIT, "Unit %s is not loaded.", name);
541
542         return bus_unit_method_set_properties(bus, message, u, error);
543 }
544
545 static int method_start_transient_unit(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
546         const char *name, *smode;
547         Manager *m = userdata;
548         JobMode mode;
549         UnitType t;
550         Unit *u;
551         int r;
552
553         assert(bus);
554         assert(message);
555         assert(m);
556
557         r = sd_bus_message_read(message, "ss", &name, &smode);
558         if (r < 0)
559                 return r;
560
561         t = unit_name_to_type(name);
562         if (t < 0)
563                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Invalid unit type.");
564
565         if (!unit_vtable[t]->can_transient)
566                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Unit type %s does not support transient units.", unit_type_to_string(t));
567
568         mode = job_mode_from_string(smode);
569         if (mode < 0)
570                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Job mode %s is invalid.", smode);
571
572         r = selinux_access_check(bus, message, "start", error);
573         if (r < 0)
574                 return r;
575
576         r = manager_load_unit(m, name, NULL, error, &u);
577         if (r < 0)
578                 return r;
579
580         if (u->load_state != UNIT_NOT_FOUND || set_size(u->dependencies[UNIT_REFERENCED_BY]) > 0)
581                 return sd_bus_error_setf(error, BUS_ERROR_UNIT_EXISTS, "Unit %s already exists.", name);
582
583         /* OK, the unit failed to load and is unreferenced, now let's
584          * fill in the transient data instead */
585         r = unit_make_transient(u);
586         if (r < 0)
587                 return r;
588
589         /* Set our properties */
590         r = bus_unit_set_properties(u, message, UNIT_RUNTIME, false, error);
591         if (r < 0)
592                 return r;
593
594         /* And load this stub fully */
595         r = unit_load(u);
596         if (r < 0)
597                 return r;
598
599         manager_dispatch_load_queue(m);
600
601         /* Finally, start it */
602         return bus_unit_queue_job(bus, message, u, JOB_START, mode, false, error);
603 }
604
605 static int method_get_job(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
606         _cleanup_free_ char *path = NULL;
607         Manager *m = userdata;
608         uint32_t id;
609         Job *j;
610         int r;
611
612         assert(bus);
613         assert(message);
614         assert(m);
615
616         r = sd_bus_message_read(message, "u", &id);
617         if (r < 0)
618                 return r;
619
620         j = manager_get_job(m, id);
621         if (!j)
622                 return sd_bus_error_setf(error, BUS_ERROR_NO_SUCH_JOB, "Job %u does not exist.", (unsigned) id);
623
624         r = selinux_unit_access_check(j->unit, bus, message, "status", error);
625         if (r < 0)
626                 return r;
627
628         path = job_dbus_path(j);
629         if (!path)
630                 return -ENOMEM;
631
632         return sd_bus_reply_method_return(message, "o", path);
633 }
634
635 static int method_cancel_job(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
636         Manager *m = userdata;
637         uint32_t id;
638         Job *j;
639         int r;
640
641         assert(bus);
642         assert(message);
643         assert(m);
644
645         r = sd_bus_message_read(message, "u", &id);
646         if (r < 0)
647                 return r;
648
649         j = manager_get_job(m, id);
650         if (!j)
651                 return sd_bus_error_setf(error, BUS_ERROR_NO_SUCH_JOB, "Job %u does not exist.", (unsigned) id);
652
653         r = selinux_unit_access_check(j->unit, bus, message, "stop", error);
654         if (r < 0)
655                 return r;
656
657         job_finish_and_invalidate(j, JOB_CANCELED, true);
658
659         return sd_bus_reply_method_return(message, NULL);
660 }
661
662 static int method_clear_jobs(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
663         Manager *m = userdata;
664         int r;
665
666         assert(bus);
667         assert(message);
668         assert(m);
669
670         r = selinux_access_check(bus, message, "reboot", error);
671         if (r < 0)
672                 return r;
673
674         manager_clear_jobs(m);
675
676         return sd_bus_reply_method_return(message, NULL);
677 }
678
679 static int method_reset_failed(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
680         Manager *m = userdata;
681         int r;
682
683         assert(bus);
684         assert(message);
685         assert(m);
686
687         r = selinux_access_check(bus, message, "reload", error);
688         if (r < 0)
689                 return r;
690
691         manager_reset_failed(m);
692
693         return sd_bus_reply_method_return(message, NULL);
694 }
695
696 static int method_list_units(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
697         _cleanup_bus_message_unref_ sd_bus_message *reply = NULL;
698         Manager *m = userdata;
699         const char *k;
700         Iterator i;
701         Unit *u;
702         int r;
703
704         assert(bus);
705         assert(message);
706         assert(m);
707
708         r = selinux_access_check(bus, message, "status", error);
709         if (r < 0)
710                 return r;
711
712         r = sd_bus_message_new_method_return(message, &reply);
713         if (r < 0)
714                 return r;
715
716         r = sd_bus_message_open_container(reply, 'a', "(ssssssouso)");
717         if (r < 0)
718                 return r;
719
720         HASHMAP_FOREACH_KEY(u, k, m->units, i) {
721                 _cleanup_free_ char *unit_path = NULL, *job_path = NULL;
722                 Unit *following;
723
724                 if (k != u->id)
725                         continue;
726
727                 following = unit_following(u);
728
729                 unit_path = unit_dbus_path(u);
730                 if (!unit_path)
731                         return -ENOMEM;
732
733                 if (u->job) {
734                         job_path = job_dbus_path(u->job);
735                         if (!job_path)
736                                 return -ENOMEM;
737                 }
738
739                 r = sd_bus_message_append(
740                                 reply, "(ssssssouso)",
741                                 u->id,
742                                 unit_description(u),
743                                 unit_load_state_to_string(u->load_state),
744                                 unit_active_state_to_string(unit_active_state(u)),
745                                 unit_sub_state_to_string(u),
746                                 following ? following->id : "",
747                                 unit_path,
748                                 u->job ? u->job->id : 0,
749                                 u->job ? job_type_to_string(u->job->type) : "",
750                                 job_path ? job_path : "/");
751                 if (r < 0)
752                         return r;
753         }
754
755         r = sd_bus_message_close_container(reply);
756         if (r < 0)
757                 return r;
758
759         return sd_bus_send(bus, reply, NULL);
760 }
761
762 static int method_list_jobs(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
763         _cleanup_bus_message_unref_ sd_bus_message *reply = NULL;
764         Manager *m = userdata;
765         Iterator i;
766         Job *j;
767         int r;
768
769         assert(bus);
770         assert(message);
771         assert(m);
772
773         r = selinux_access_check(bus, message, "status", error);
774         if (r < 0)
775                 return r;
776
777         r = sd_bus_message_new_method_return(message, &reply);
778         if (r < 0)
779                 return r;
780
781         r = sd_bus_message_open_container(reply, 'a', "(usssoo)");
782         if (r < 0)
783                 return r;
784
785         HASHMAP_FOREACH(j, m->jobs, i) {
786                 _cleanup_free_ char *unit_path = NULL, *job_path = NULL;
787
788                 job_path = job_dbus_path(j);
789                 if (!job_path)
790                         return -ENOMEM;
791
792                 unit_path = unit_dbus_path(j->unit);
793                 if (!unit_path)
794                         return -ENOMEM;
795
796                 r = sd_bus_message_append(
797                                 reply, "(usssoo)",
798                                 j->id,
799                                 j->unit->id,
800                                 job_type_to_string(j->type),
801                                 job_state_to_string(j->state),
802                                 job_path,
803                                 unit_path);
804                 if (r < 0)
805                         return r;
806         }
807
808         r = sd_bus_message_close_container(reply);
809         if (r < 0)
810                 return r;
811
812         return sd_bus_send(bus, reply, NULL);
813 }
814
815 static int method_subscribe(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
816         Manager *m = userdata;
817         int r;
818
819         assert(bus);
820         assert(message);
821         assert(m);
822
823         r = selinux_access_check(bus, message, "status", error);
824         if (r < 0)
825                 return r;
826
827         r = bus_client_track(&m->subscribed, bus, sd_bus_message_get_sender(message));
828         if (r < 0)
829                 return r;
830         if (r == 0)
831                 return sd_bus_error_setf(error, BUS_ERROR_ALREADY_SUBSCRIBED, "Client is already subscribed.");
832
833         return sd_bus_reply_method_return(message, NULL);
834 }
835
836 static int method_unsubscribe(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
837         Manager *m = userdata;
838         int r;
839
840         assert(bus);
841         assert(message);
842         assert(m);
843
844         r = selinux_access_check(bus, message, "status", error);
845         if (r < 0)
846                 return r;
847
848         r = bus_client_untrack(m->subscribed, bus, sd_bus_message_get_sender(message));
849         if (r < 0)
850                 return r;
851         if (r == 0)
852                 return sd_bus_error_setf(error, BUS_ERROR_NOT_SUBSCRIBED, "Client is not subscribed.");
853
854         return sd_bus_reply_method_return(message, NULL);
855 }
856
857 static int method_dump(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
858         _cleanup_free_ char *dump = NULL;
859         _cleanup_fclose_ FILE *f = NULL;
860         Manager *m = userdata;
861         size_t size;
862         int r;
863
864         assert(bus);
865         assert(message);
866         assert(m);
867
868         r = selinux_access_check(bus, message, "status", error);
869         if (r < 0)
870                 return r;
871
872         f = open_memstream(&dump, &size);
873         if (!f)
874                 return -ENOMEM;
875
876         manager_dump_units(m, f, NULL);
877         manager_dump_jobs(m, f, NULL);
878
879         fflush(f);
880
881         if (ferror(f))
882                 return -ENOMEM;
883
884         return sd_bus_reply_method_return(message, "s", dump);
885 }
886
887 static int method_create_snapshot(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
888         _cleanup_free_ char *path = NULL;
889         Manager *m = userdata;
890         const char *name;
891         int cleanup;
892         Snapshot *s = NULL;
893         int r;
894
895         assert(bus);
896         assert(message);
897         assert(m);
898
899         r = selinux_access_check(bus, message, "start", error);
900         if (r < 0)
901                 return r;
902
903         r = sd_bus_message_read(message, "sb", &name, &cleanup);
904         if (r < 0)
905                 return r;
906
907         if (isempty(name))
908                 name = NULL;
909
910         r = snapshot_create(m, name, cleanup, error, &s);
911         if (r < 0)
912                 return r;
913
914         path = unit_dbus_path(UNIT(s));
915         if (!path)
916                 return -ENOMEM;
917
918         return sd_bus_reply_method_return(message, "o", path);
919 }
920
921 static int method_remove_snapshot(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
922         Manager *m = userdata;
923         const char *name;
924         Unit *u;
925         int r;
926
927         assert(bus);
928         assert(message);
929         assert(m);
930
931         r = selinux_access_check(bus, message, "stop", error);
932         if (r < 0)
933                 return r;
934
935         r = sd_bus_message_read(message, "s", &name);
936         if (r < 0)
937                 return r;
938
939         u = manager_get_unit(m, name);
940         if (!u)
941                 return sd_bus_error_setf(error, BUS_ERROR_NO_SUCH_UNIT, "Unit %s does not exist.", name);
942
943         if (u->type != UNIT_SNAPSHOT)
944                 return sd_bus_error_setf(error, BUS_ERROR_NO_SUCH_UNIT, "Unit %s is not a snapshot", name);
945
946         return bus_snapshot_method_remove(bus, message, u, error);
947 }
948
949 static int method_reload(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
950         Manager *m = userdata;
951         int r;
952
953         assert(bus);
954         assert(message);
955         assert(m);
956
957         r = selinux_access_check(bus, message, "reload", error);
958         if (r < 0)
959                 return r;
960
961         /* Instead of sending the reply back right away, we just
962          * remember that we need to and then send it after the reload
963          * is finished. That way the caller knows when the reload
964          * finished. */
965
966         assert(!m->queued_message);
967         r = sd_bus_message_new_method_return(message, &m->queued_message);
968         if (r < 0)
969                 return r;
970
971         m->queued_message_bus = sd_bus_ref(bus);
972         m->exit_code = MANAGER_RELOAD;
973
974         return 1;
975 }
976
977 static int method_reexecute(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
978         Manager *m = userdata;
979         int r;
980
981         assert(bus);
982         assert(message);
983         assert(m);
984
985         r = selinux_access_check(bus, message, "reload", error);
986         if (r < 0)
987                 return r;
988
989         /* We don't send a reply back here, the client should
990          * just wait for us disconnecting. */
991
992         m->exit_code = MANAGER_REEXECUTE;
993         return 1;
994 }
995
996 static int method_exit(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
997         Manager *m = userdata;
998         int r;
999
1000         assert(bus);
1001         assert(message);
1002         assert(m);
1003
1004         r = selinux_access_check(bus, message, "halt", error);
1005         if (r < 0)
1006                 return r;
1007
1008         if (m->running_as == SYSTEMD_SYSTEM)
1009                 return sd_bus_error_setf(error, SD_BUS_ERROR_NOT_SUPPORTED, "Exit is only supported for user service managers.");
1010
1011         m->exit_code = MANAGER_EXIT;
1012
1013         return sd_bus_reply_method_return(message, NULL);
1014 }
1015
1016 static int method_reboot(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1017         Manager *m = userdata;
1018         int r;
1019
1020         assert(bus);
1021         assert(message);
1022         assert(m);
1023
1024         r = selinux_access_check(bus, message, "reboot", error);
1025         if (r < 0)
1026                 return r;
1027
1028         if (m->running_as != SYSTEMD_SYSTEM)
1029                 return sd_bus_error_setf(error, SD_BUS_ERROR_NOT_SUPPORTED, "Reboot is only supported for system managers.");
1030
1031         m->exit_code = MANAGER_REBOOT;
1032
1033         return sd_bus_reply_method_return(message, NULL);
1034 }
1035
1036
1037 static int method_poweroff(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1038         Manager *m = userdata;
1039         int r;
1040
1041         assert(bus);
1042         assert(message);
1043         assert(m);
1044
1045         r = selinux_access_check(bus, message, "halt", error);
1046         if (r < 0)
1047                 return r;
1048
1049         if (m->running_as != SYSTEMD_SYSTEM)
1050                 return sd_bus_error_setf(error, SD_BUS_ERROR_NOT_SUPPORTED, "Powering off is only supported for system managers.");
1051
1052         m->exit_code = MANAGER_POWEROFF;
1053
1054         return sd_bus_reply_method_return(message, NULL);
1055 }
1056
1057 static int method_halt(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1058         Manager *m = userdata;
1059         int r;
1060
1061         assert(bus);
1062         assert(message);
1063         assert(m);
1064
1065         r = selinux_access_check(bus, message, "halt", error);
1066         if (r < 0)
1067                 return r;
1068
1069         if (m->running_as != SYSTEMD_SYSTEM)
1070                 return sd_bus_error_setf(error, SD_BUS_ERROR_NOT_SUPPORTED, "Halt is only supported for system managers.");
1071
1072         m->exit_code = MANAGER_HALT;
1073
1074         return sd_bus_reply_method_return(message, NULL);
1075 }
1076
1077 static int method_kexec(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1078         Manager *m = userdata;
1079         int r;
1080
1081         assert(bus);
1082         assert(message);
1083         assert(m);
1084
1085         r = selinux_access_check(bus, message, "reboot", error);
1086         if (r < 0)
1087                 return r;
1088
1089         if (m->running_as != SYSTEMD_SYSTEM)
1090                 return sd_bus_error_setf(error, SD_BUS_ERROR_NOT_SUPPORTED, "KExec is only supported for system managers.");
1091
1092         m->exit_code = MANAGER_KEXEC;
1093
1094         return sd_bus_reply_method_return(message, NULL);
1095 }
1096
1097 static int method_switch_root(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1098         char *ri = NULL, *rt = NULL;
1099         const char *root, *init;
1100         Manager *m = userdata;
1101         int r;
1102
1103         assert(bus);
1104         assert(message);
1105         assert(m);
1106
1107         r = selinux_access_check(bus, message, "reboot", error);
1108         if (r < 0)
1109                 return r;
1110
1111         if (m->running_as != SYSTEMD_SYSTEM)
1112                 return sd_bus_error_setf(error, SD_BUS_ERROR_NOT_SUPPORTED, "KExec is only supported for system managers.");
1113
1114         r = sd_bus_message_read(message, "ss", &root, &init);
1115         if (r < 0)
1116                 return r;
1117
1118         if (path_equal(root, "/") || !path_is_absolute(root))
1119                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Invalid switch root path %s", root);
1120
1121         /* Safety check */
1122         if (isempty(init)) {
1123                 if (! path_is_os_tree(root))
1124                         return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Specified switch root path %s does not seem to be an OS tree. /etc/os-release is missing.", root);
1125         } else {
1126                 _cleanup_free_ char *p = NULL;
1127
1128                 if (!path_is_absolute(init))
1129                         return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Invalid init path %s", init);
1130
1131                 p = strappend(root, init);
1132                 if (!p)
1133                         return -ENOMEM;
1134
1135                 if (access(p, X_OK) < 0)
1136                         return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Specified init binary %s does not exist.", p);
1137         }
1138
1139         rt = strdup(root);
1140         if (!rt)
1141                 return -ENOMEM;
1142
1143         if (!isempty(init)) {
1144                 ri = strdup(init);
1145                 if (!ri) {
1146                         free(rt);
1147                         return -ENOMEM;
1148                 }
1149         }
1150
1151         free(m->switch_root);
1152         m->switch_root = rt;
1153
1154         free(m->switch_root_init);
1155         m->switch_root_init = ri;
1156
1157         m->exit_code = MANAGER_SWITCH_ROOT;
1158
1159         return sd_bus_reply_method_return(message, NULL);
1160 }
1161
1162 static int method_set_environment(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1163         _cleanup_strv_free_ char **plus = NULL;
1164         Manager *m = userdata;
1165         int r;
1166
1167         assert(bus);
1168         assert(message);
1169         assert(m);
1170
1171         r = selinux_access_check(bus, message, "reload", error);
1172         if (r < 0)
1173                 return r;
1174
1175         r = sd_bus_message_read_strv(message, &plus);
1176         if (r < 0)
1177                 return r;
1178         if (!strv_env_is_valid(plus))
1179                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Invalid environment assignments");
1180
1181         r = manager_environment_add(m, NULL, plus);
1182         if (r < 0)
1183                 return r;
1184
1185         return sd_bus_reply_method_return(message, NULL);
1186 }
1187
1188 static int method_unset_environment(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1189         _cleanup_strv_free_ char **minus = NULL;
1190         Manager *m = userdata;
1191         int r;
1192
1193         assert(bus);
1194         assert(message);
1195         assert(m);
1196
1197         r = selinux_access_check(bus, message, "reload", error);
1198         if (r < 0)
1199                 return r;
1200
1201         r = sd_bus_message_read_strv(message, &minus);
1202         if (r < 0)
1203                 return r;
1204
1205         if (!strv_env_name_or_assignment_is_valid(minus))
1206                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Invalid environment variable names or assignments");
1207
1208         r = manager_environment_add(m, minus, NULL);
1209         if (r < 0)
1210                 return r;
1211
1212         return sd_bus_reply_method_return(message, NULL);
1213 }
1214
1215 static int method_unset_and_set_environment(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1216         _cleanup_strv_free_ char **minus = NULL, **plus = NULL;
1217         Manager *m = userdata;
1218         int r;
1219
1220         assert(bus);
1221         assert(message);
1222         assert(m);
1223
1224         r = selinux_access_check(bus, message, "reload", error);
1225         if (r < 0)
1226                 return r;
1227
1228         r = sd_bus_message_read_strv(message, &plus);
1229         if (r < 0)
1230                 return r;
1231
1232         r = sd_bus_message_read_strv(message, &minus);
1233         if (r < 0)
1234                 return r;
1235
1236         if (!strv_env_is_valid(plus))
1237                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Invalid environment assignments");
1238         if (!strv_env_name_or_assignment_is_valid(minus))
1239                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Invalid environment variable names or assignments");
1240
1241         r = manager_environment_add(m, minus, plus);
1242         if (r < 0)
1243                 return r;
1244
1245         return sd_bus_reply_method_return(message, NULL);
1246 }
1247
1248 static int method_list_unit_files(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1249         _cleanup_bus_message_unref_ sd_bus_message *reply = NULL;
1250         Manager *m = userdata;
1251         UnitFileList *item;
1252         Hashmap *h;
1253         Iterator i;
1254         int r;
1255
1256         assert(bus);
1257         assert(message);
1258         assert(m);
1259
1260         r = selinux_access_check(bus, message, "status", error);
1261         if (r < 0)
1262                 return r;
1263
1264         r = sd_bus_message_new_method_return(message, &reply);
1265         if (r < 0)
1266                 return r;
1267
1268         h = hashmap_new(string_hash_func, string_compare_func);
1269         if (!h)
1270                 return -ENOMEM;
1271
1272         r = unit_file_get_list(m->running_as == SYSTEMD_SYSTEM ? UNIT_FILE_SYSTEM : UNIT_FILE_USER, NULL, h);
1273         if (r < 0)
1274                 goto fail;
1275
1276         r = sd_bus_message_open_container(reply, 'a', "(ss)");
1277         if (r < 0)
1278                 goto fail;
1279
1280         HASHMAP_FOREACH(item, h, i) {
1281
1282                 r = sd_bus_message_append(reply, "(ss)", item->path, unit_file_state_to_string(item->state));
1283                 if (r < 0)
1284                         goto fail;
1285         }
1286
1287         unit_file_list_free(h);
1288
1289         r = sd_bus_message_close_container(reply);
1290         if (r < 0)
1291                 return r;
1292
1293         return sd_bus_send(bus, reply, NULL);
1294
1295 fail:
1296         unit_file_list_free(h);
1297         return r;
1298 }
1299
1300 static int method_get_unit_file_state(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1301         Manager *m = userdata;
1302         const char *name;
1303         UnitFileState state;
1304         UnitFileScope scope;
1305         int r;
1306
1307         assert(bus);
1308         assert(message);
1309         assert(m);
1310
1311         r = selinux_access_check(bus, message, "status", error);
1312         if (r < 0)
1313                 return r;
1314
1315         r = sd_bus_message_read(message, "s", &name);
1316         if (r < 0)
1317                 return r;
1318
1319         scope = m->running_as == SYSTEMD_SYSTEM ? UNIT_FILE_SYSTEM : UNIT_FILE_USER;
1320
1321         state = unit_file_get_state(scope, NULL, name);
1322         if (state < 0)
1323                 return state;
1324
1325         return sd_bus_reply_method_return(message, "s", unit_file_state_to_string(state));
1326 }
1327
1328 static int method_get_default_target(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1329         _cleanup_free_ char *default_target = NULL;
1330         Manager *m = userdata;
1331         UnitFileScope scope;
1332         int r;
1333
1334         assert(bus);
1335         assert(message);
1336         assert(m);
1337
1338         r = selinux_access_check(bus, message, "status", error);
1339         if (r < 0)
1340                 return r;
1341
1342         scope = m->running_as == SYSTEMD_SYSTEM ? UNIT_FILE_SYSTEM : UNIT_FILE_USER;
1343
1344         r = unit_file_get_default(scope, NULL, &default_target);
1345         if (r < 0)
1346                 return r;
1347
1348         return sd_bus_reply_method_return(message, "s", default_target);
1349 }
1350
1351 static int send_unit_files_changed(sd_bus *bus, const char *destination, void *userdata) {
1352         _cleanup_bus_message_unref_ sd_bus_message *message = NULL;
1353         int r;
1354
1355         assert(bus);
1356
1357         r = sd_bus_message_new_signal(bus, &message, "/org/freedesktop/systemd1", "org.freedesktop.systemd1.Manager", "UnitFilesChanged");
1358         if (r < 0)
1359                 return r;
1360
1361         return sd_bus_send_to(bus, message, destination, NULL);
1362 }
1363
1364 static int reply_unit_file_changes_and_free(
1365                 Manager *m,
1366                 sd_bus *bus,
1367                 sd_bus_message *message,
1368                 int carries_install_info,
1369                 UnitFileChange *changes,
1370                 unsigned n_changes) {
1371
1372         _cleanup_bus_message_unref_ sd_bus_message *reply = NULL;
1373         unsigned i;
1374         int r;
1375
1376         if (n_changes > 0)
1377                 bus_manager_foreach_client(m, send_unit_files_changed, NULL);
1378
1379         r = sd_bus_message_new_method_return(message, &reply);
1380         if (r < 0)
1381                 goto fail;
1382
1383         if (carries_install_info >= 0) {
1384                 r = sd_bus_message_append(reply, "b", carries_install_info);
1385                 if (r < 0)
1386                         goto fail;
1387         }
1388
1389         r = sd_bus_message_open_container(reply, 'a', "(sss)");
1390         if (r < 0)
1391                 goto fail;
1392
1393         for (i = 0; i < n_changes; i++) {
1394                 r = sd_bus_message_append(
1395                                 reply, "(sss)",
1396                                 unit_file_change_type_to_string(changes[i].type),
1397                                 changes[i].path,
1398                                 changes[i].source);
1399                 if (r < 0)
1400                         goto fail;
1401         }
1402
1403         r = sd_bus_message_close_container(reply);
1404         if (r < 0)
1405                 goto fail;
1406
1407         return sd_bus_send(bus, reply, NULL);
1408
1409 fail:
1410         unit_file_changes_free(changes, n_changes);
1411         return r;
1412 }
1413
1414 static int method_enable_unit_files_generic(
1415                 sd_bus *bus,
1416                 sd_bus_message *message,
1417                 Manager *m, const
1418                 char *verb,
1419                 int (*call)(UnitFileScope scope, bool runtime, const char *root_dir, char *files[], bool force, UnitFileChange **changes, unsigned *n_changes),
1420                 bool carries_install_info,
1421                 sd_bus_error *error) {
1422
1423         _cleanup_strv_free_ char **l = NULL;
1424 #ifdef HAVE_SELINUX
1425         char **i;
1426 #endif
1427         UnitFileChange *changes = NULL;
1428         unsigned n_changes = 0;
1429         UnitFileScope scope;
1430         int runtime, force, r;
1431
1432         assert(bus);
1433         assert(message);
1434         assert(m);
1435
1436         r = sd_bus_message_read_strv(message, &l);
1437         if (r < 0)
1438                 return r;
1439
1440 #ifdef HAVE_SELINUX
1441         STRV_FOREACH(i, l) {
1442                 Unit *u;
1443
1444                 u = manager_get_unit(m, *i);
1445                 if (u) {
1446                         r = selinux_unit_access_check(u, bus, message, verb, error);
1447                         if (r < 0)
1448                                 return r;
1449                 }
1450         }
1451 #endif
1452
1453         r = sd_bus_message_read(message, "bb", &runtime, &force);
1454         if (r < 0)
1455                 return r;
1456
1457         scope = m->running_as == SYSTEMD_SYSTEM ? UNIT_FILE_SYSTEM : UNIT_FILE_USER;
1458
1459         r = call(scope, runtime, NULL, l, force, &changes, &n_changes);
1460         if (r < 0)
1461                 return r;
1462
1463         return reply_unit_file_changes_and_free(m, bus, message, carries_install_info ? r : -1, changes, n_changes);
1464 }
1465
1466 static int method_enable_unit_files(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1467         return method_enable_unit_files_generic(bus, message, userdata, "enable", unit_file_enable, true, error);
1468 }
1469
1470 static int method_reenable_unit_files(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1471         return method_enable_unit_files_generic(bus, message, userdata, "enable", unit_file_reenable, true, error);
1472 }
1473
1474 static int method_link_unit_files(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1475         return method_enable_unit_files_generic(bus, message, userdata, "enable", unit_file_link, false, error);
1476 }
1477
1478 static int method_preset_unit_files(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1479         return method_enable_unit_files_generic(bus, message, userdata, "enable", unit_file_preset, true, error);
1480 }
1481
1482 static int method_mask_unit_files(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1483         return method_enable_unit_files_generic(bus, message, userdata, "disable", unit_file_mask, false, error);
1484 }
1485
1486 static int method_disable_unit_files_generic(
1487                 sd_bus *bus,
1488                 sd_bus_message *message,
1489                 Manager *m, const
1490                 char *verb,
1491                 int (*call)(UnitFileScope scope, bool runtime, const char *root_dir, char *files[], UnitFileChange **changes, unsigned *n_changes),
1492                 sd_bus_error *error) {
1493
1494         _cleanup_strv_free_ char **l = NULL;
1495         UnitFileChange *changes = NULL;
1496         unsigned n_changes = 0;
1497         UnitFileScope scope;
1498         int r, runtime;
1499
1500         assert(bus);
1501         assert(message);
1502         assert(m);
1503
1504         r = selinux_access_check(bus, message, verb, error);
1505         if (r < 0)
1506                 return r;
1507
1508         r = sd_bus_message_read_strv(message, &l);
1509         if (r < 0)
1510                 return r;
1511
1512         r = sd_bus_message_read(message, "b", &runtime);
1513         if (r < 0)
1514                 return r;
1515
1516         scope = m->running_as == SYSTEMD_SYSTEM ? UNIT_FILE_SYSTEM : UNIT_FILE_USER;
1517
1518         r = call(scope, runtime, NULL, l, &changes, &n_changes);
1519         if (r < 0)
1520                 return r;
1521
1522         return reply_unit_file_changes_and_free(m, bus, message, -1, changes, n_changes);
1523 }
1524
1525 static int method_disable_unit_files(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1526         return method_disable_unit_files_generic(bus, message, userdata, "disable", unit_file_disable, error);
1527 }
1528
1529 static int method_unmask_unit_files(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1530         return method_disable_unit_files_generic(bus, message, userdata, "enable", unit_file_unmask, error);
1531 }
1532
1533 static int method_set_default_target(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1534         UnitFileChange *changes = NULL;
1535         unsigned n_changes = 0;
1536         Manager *m = userdata;
1537         UnitFileScope scope;
1538         const char *name;
1539         int force, r;
1540
1541         assert(bus);
1542         assert(message);
1543         assert(m);
1544
1545         r = selinux_access_check(bus, message, "enable", error);
1546         if (r < 0)
1547                 return r;
1548
1549         r = sd_bus_message_read(message, "sb", &name, &force);
1550         if (r < 0)
1551                 return r;
1552
1553         scope = m->running_as == SYSTEMD_SYSTEM ? UNIT_FILE_SYSTEM : UNIT_FILE_USER;
1554
1555         r = unit_file_set_default(scope, NULL, name, force, &changes, &n_changes);
1556         if (r < 0)
1557                 return r;
1558
1559         return reply_unit_file_changes_and_free(m, bus, message, -1, changes, n_changes);
1560 }
1561
1562 const sd_bus_vtable bus_manager_vtable[] = {
1563         SD_BUS_VTABLE_START(0),
1564
1565         SD_BUS_PROPERTY("Version", "s", property_get_version, 0, SD_BUS_VTABLE_PROPERTY_CONST),
1566         SD_BUS_PROPERTY("Features", "s", property_get_features, 0, SD_BUS_VTABLE_PROPERTY_CONST),
1567         SD_BUS_PROPERTY("Virtualization", "s", property_get_virtualization, 0, SD_BUS_VTABLE_PROPERTY_CONST),
1568         SD_BUS_PROPERTY("Architecture", "s", property_get_architecture, 0, SD_BUS_VTABLE_PROPERTY_CONST),
1569         SD_BUS_PROPERTY("Tainted", "s", property_get_tainted, 0, SD_BUS_VTABLE_PROPERTY_CONST),
1570         BUS_PROPERTY_DUAL_TIMESTAMP("FirmwareTimestamp", offsetof(Manager, firmware_timestamp), SD_BUS_VTABLE_PROPERTY_CONST),
1571         BUS_PROPERTY_DUAL_TIMESTAMP("LoaderTimestamp", offsetof(Manager, loader_timestamp), SD_BUS_VTABLE_PROPERTY_CONST),
1572         BUS_PROPERTY_DUAL_TIMESTAMP("KernelTimestamp", offsetof(Manager, kernel_timestamp), SD_BUS_VTABLE_PROPERTY_CONST),
1573         BUS_PROPERTY_DUAL_TIMESTAMP("InitRDTimestamp", offsetof(Manager, initrd_timestamp), SD_BUS_VTABLE_PROPERTY_CONST),
1574         BUS_PROPERTY_DUAL_TIMESTAMP("UserspaceTimestamp", offsetof(Manager, userspace_timestamp), SD_BUS_VTABLE_PROPERTY_CONST),
1575         BUS_PROPERTY_DUAL_TIMESTAMP("FinishTimestamp", offsetof(Manager, finish_timestamp), SD_BUS_VTABLE_PROPERTY_CONST),
1576         BUS_PROPERTY_DUAL_TIMESTAMP("SecurityStartTimestamp", offsetof(Manager, security_start_timestamp), SD_BUS_VTABLE_PROPERTY_CONST),
1577         BUS_PROPERTY_DUAL_TIMESTAMP("SecurityFinishTimestamp", offsetof(Manager, security_finish_timestamp), SD_BUS_VTABLE_PROPERTY_CONST),
1578         BUS_PROPERTY_DUAL_TIMESTAMP("GeneratorsStartTimestamp", offsetof(Manager, generators_start_timestamp), SD_BUS_VTABLE_PROPERTY_CONST),
1579         BUS_PROPERTY_DUAL_TIMESTAMP("GeneratorsFinishTimestamp", offsetof(Manager, generators_finish_timestamp), SD_BUS_VTABLE_PROPERTY_CONST),
1580         BUS_PROPERTY_DUAL_TIMESTAMP("UnitsLoadStartTimestamp", offsetof(Manager, units_load_start_timestamp), SD_BUS_VTABLE_PROPERTY_CONST),
1581         BUS_PROPERTY_DUAL_TIMESTAMP("UnitsLoadFinishTimestamp", offsetof(Manager, units_load_finish_timestamp), SD_BUS_VTABLE_PROPERTY_CONST),
1582         SD_BUS_WRITABLE_PROPERTY("LogLevel", "s", property_get_log_level, property_set_log_level, 0, 0),
1583         SD_BUS_WRITABLE_PROPERTY("LogTarget", "s", property_get_log_target, property_set_log_target, 0, 0),
1584         SD_BUS_PROPERTY("NNames", "u", property_get_n_names, 0, 0),
1585         SD_BUS_PROPERTY("NJobs", "u", property_get_n_jobs, 0, 0),
1586         SD_BUS_PROPERTY("NInstalledJobs", "u", bus_property_get_unsigned, offsetof(Manager, n_installed_jobs), 0),
1587         SD_BUS_PROPERTY("NFailedJobs", "u", bus_property_get_unsigned, offsetof(Manager, n_failed_jobs), 0),
1588         SD_BUS_PROPERTY("Progress", "d", property_get_progress, 0, 0),
1589         SD_BUS_PROPERTY("Environment", "as", NULL, offsetof(Manager, environment), 0),
1590         SD_BUS_PROPERTY("ConfirmSpawn", "b", bus_property_get_bool, offsetof(Manager, confirm_spawn), SD_BUS_VTABLE_PROPERTY_CONST),
1591         SD_BUS_PROPERTY("ShowStatus", "b", bus_property_get_bool, offsetof(Manager, show_status), SD_BUS_VTABLE_PROPERTY_CONST),
1592         SD_BUS_PROPERTY("UnitPath", "as", NULL, offsetof(Manager, lookup_paths.unit_path), SD_BUS_VTABLE_PROPERTY_CONST),
1593         SD_BUS_PROPERTY("DefaultStandardOutput", "s", bus_property_get_exec_output, offsetof(Manager, default_std_output), SD_BUS_VTABLE_PROPERTY_CONST),
1594         SD_BUS_PROPERTY("DefaultStandardError", "s", bus_property_get_exec_output, offsetof(Manager, default_std_output), SD_BUS_VTABLE_PROPERTY_CONST),
1595         SD_BUS_WRITABLE_PROPERTY("RuntimeWatchdogUSec", "t", bus_property_get_usec, property_set_runtime_watchdog, offsetof(Manager, runtime_watchdog), SD_BUS_VTABLE_PROPERTY_CONST),
1596         SD_BUS_WRITABLE_PROPERTY("ShutdownWatchdogUSec", "t", bus_property_get_usec, bus_property_set_usec, offsetof(Manager, shutdown_watchdog), SD_BUS_VTABLE_PROPERTY_CONST),
1597         SD_BUS_PROPERTY("ControlGroup", "s", NULL, offsetof(Manager, cgroup_root), 0),
1598
1599         SD_BUS_METHOD("GetUnit", "s", "o", method_get_unit, SD_BUS_VTABLE_UNPRIVILEGED),
1600         SD_BUS_METHOD("GetUnitByPID", "u", "o", method_get_unit_by_pid, SD_BUS_VTABLE_UNPRIVILEGED),
1601         SD_BUS_METHOD("LoadUnit", "s", "o", method_load_unit, SD_BUS_VTABLE_UNPRIVILEGED),
1602         SD_BUS_METHOD("StartUnit", "ss", "o", method_start_unit, 0),
1603         SD_BUS_METHOD("StartUnitReplace", "sss", "o", method_start_unit_replace, 0),
1604         SD_BUS_METHOD("StopUnit", "ss", "o", method_stop_unit, 0),
1605         SD_BUS_METHOD("ReloadUnit", "ss", "o", method_reload_unit, 0),
1606         SD_BUS_METHOD("RestartUnit", "ss", "o", method_restart_unit, 0),
1607         SD_BUS_METHOD("TryRestartUnit", "ss", "o", method_try_restart_unit, 0),
1608         SD_BUS_METHOD("ReloadOrRestartUnit", "ss", "o", method_reload_or_restart_unit, 0),
1609         SD_BUS_METHOD("ReloadOrTryRestartUnit", "ss", "o", method_reload_or_try_restart_unit, 0),
1610         SD_BUS_METHOD("KillUnit", "ssi", NULL, method_kill_unit, SD_BUS_VTABLE_CAPABILITY(CAP_KILL)),
1611         SD_BUS_METHOD("ResetFailedUnit", "s", NULL, method_reset_failed_unit, 0),
1612         SD_BUS_METHOD("SetUnitProperties", "sba(sv)", NULL, method_set_unit_properties, 0),
1613         SD_BUS_METHOD("StartTransientUnit", "ssa(sv)a(sa(sv))", "o", method_start_transient_unit, 0),
1614         SD_BUS_METHOD("GetJob", "u", "o", method_get_job, SD_BUS_VTABLE_UNPRIVILEGED),
1615         SD_BUS_METHOD("CancelJob", "u", NULL, method_cancel_job, 0),
1616         SD_BUS_METHOD("ClearJobs", NULL, NULL, method_clear_jobs, 0),
1617         SD_BUS_METHOD("ResetFailed", NULL, NULL, method_reset_failed, 0),
1618         SD_BUS_METHOD("ListUnits", NULL, "a(ssssssouso)", method_list_units, SD_BUS_VTABLE_UNPRIVILEGED),
1619         SD_BUS_METHOD("ListJobs", NULL, "a(usssoo)", method_list_jobs, SD_BUS_VTABLE_UNPRIVILEGED),
1620         SD_BUS_METHOD("Subscribe", NULL, NULL, method_subscribe, SD_BUS_VTABLE_UNPRIVILEGED),
1621         SD_BUS_METHOD("Unsubscribe", NULL, NULL, method_unsubscribe, SD_BUS_VTABLE_UNPRIVILEGED),
1622         SD_BUS_METHOD("Dump", NULL, "s", method_dump, SD_BUS_VTABLE_UNPRIVILEGED),
1623         SD_BUS_METHOD("CreateSnapshot", "sb", "o", method_create_snapshot, 0),
1624         SD_BUS_METHOD("RemoveSnapshot", "s", NULL, method_remove_snapshot, 0),
1625         SD_BUS_METHOD("Reload", NULL, NULL, method_reload, 0),
1626         SD_BUS_METHOD("Reexecute", NULL, NULL, method_reexecute, 0),
1627         SD_BUS_METHOD("Exit", NULL, NULL, method_exit, 0),
1628         SD_BUS_METHOD("Reboot", NULL, NULL, method_reboot, SD_BUS_VTABLE_CAPABILITY(CAP_SYS_BOOT)),
1629         SD_BUS_METHOD("PowerOff", NULL, NULL, method_poweroff, SD_BUS_VTABLE_CAPABILITY(CAP_SYS_BOOT)),
1630         SD_BUS_METHOD("Halt", NULL, NULL, method_halt, SD_BUS_VTABLE_CAPABILITY(CAP_SYS_BOOT)),
1631         SD_BUS_METHOD("KExec", NULL, NULL, method_kexec, SD_BUS_VTABLE_CAPABILITY(CAP_SYS_BOOT)),
1632         SD_BUS_METHOD("SwitchRoot", "ss", NULL, method_switch_root, SD_BUS_VTABLE_CAPABILITY(CAP_SYS_BOOT)),
1633         SD_BUS_METHOD("SetEnvironment", "as", NULL, method_set_environment, 0),
1634         SD_BUS_METHOD("UnsetEnvironment", "as", NULL, method_unset_environment, 0),
1635         SD_BUS_METHOD("UnsetAndSetEnvironment", "asas", NULL, method_unset_and_set_environment, 0),
1636         SD_BUS_METHOD("ListUnitFiles", NULL, "a(ss)", method_list_unit_files, SD_BUS_VTABLE_UNPRIVILEGED),
1637         SD_BUS_METHOD("GetUnitFileState", "s", "s", method_get_unit_file_state, SD_BUS_VTABLE_UNPRIVILEGED),
1638         SD_BUS_METHOD("EnableUnitFiles", "asbb", "ba(sss)", method_enable_unit_files, 0),
1639         SD_BUS_METHOD("DisableUnitFiles", "asb", "a(sss)", method_disable_unit_files, 0),
1640         SD_BUS_METHOD("ReenableUnitFiles", "asbb", "ba(sss)", method_reenable_unit_files, 0),
1641         SD_BUS_METHOD("LinkUnitFiles", "asbb", "a(sss)", method_link_unit_files, 0),
1642         SD_BUS_METHOD("PresetUnitFiles", "asbb", "ba(sss)", method_preset_unit_files, 0),
1643         SD_BUS_METHOD("MaskUnitFiles", "asbb", "a(sss)", method_mask_unit_files, 0),
1644         SD_BUS_METHOD("UnmaskUnitFiles", "asb", "a(sss)", method_unmask_unit_files, 0),
1645         SD_BUS_METHOD("SetDefaultTarget", "sb", "a(sss)", method_set_default_target, 0),
1646         SD_BUS_METHOD("GetDefaultTarget", NULL, "s", method_get_default_target, SD_BUS_VTABLE_UNPRIVILEGED),
1647
1648         SD_BUS_SIGNAL("UnitNew", "so", 0),
1649         SD_BUS_SIGNAL("UnitRemoved", "so", 0),
1650         SD_BUS_SIGNAL("JobNew", "uos", 0),
1651         SD_BUS_SIGNAL("JobRemoved", "uoss", 0),
1652         SD_BUS_SIGNAL("StartupFinished", "tttttt", 0),
1653         SD_BUS_SIGNAL("UnitFilesChanged", NULL, 0),
1654         SD_BUS_SIGNAL("Reloading", "b", 0),
1655
1656         SD_BUS_VTABLE_END
1657 };
1658
1659 int bus_manager_foreach_client(Manager *m, int (*send_message)(sd_bus *bus, const char *destination, void *userdata), void *userdata) {
1660         Iterator i;
1661         sd_bus *b;
1662         unsigned n;
1663         int r, ret;
1664
1665         n = set_size(m->subscribed);
1666         if (n <= 0)
1667                 return 0;
1668         if (n == 1) {
1669                 BusTrackedClient *d;
1670
1671                 assert_se(d = set_first(m->subscribed));
1672                 return send_message(d->bus, isempty(d->name) ? NULL : d->name, userdata);
1673         }
1674
1675         ret = 0;
1676
1677         /* Send to everybody */
1678         SET_FOREACH(b, m->private_buses, i) {
1679                 r = send_message(b, NULL, userdata);
1680                 if (r < 0)
1681                         ret = r;
1682         }
1683
1684         if (m->api_bus) {
1685                 r = send_message(m->api_bus, NULL, userdata);
1686                 if (r < 0)
1687                         ret = r;
1688         }
1689
1690         return ret;
1691 }
1692
1693 static int send_finished(sd_bus *bus, const char *destination, void *userdata) {
1694         _cleanup_bus_message_unref_ sd_bus_message *message = NULL;
1695         usec_t *times = userdata;
1696         int r;
1697
1698         assert(bus);
1699         assert(times);
1700
1701         r = sd_bus_message_new_signal(bus, &message, "/org/freedesktop/systemd1", "org.freedesktop.systemd1.Manager", "StartupFinished");
1702         if (r < 0)
1703                 return r;
1704
1705         r = sd_bus_message_append(message, "tttttt", times[0], times[1], times[2], times[3], times[4], times[5]);
1706         if (r < 0)
1707                 return r;
1708
1709         return sd_bus_send_to(bus, message, destination, NULL);
1710 }
1711
1712 void bus_manager_send_finished(
1713                 Manager *m,
1714                 usec_t firmware_usec,
1715                 usec_t loader_usec,
1716                 usec_t kernel_usec,
1717                 usec_t initrd_usec,
1718                 usec_t userspace_usec,
1719                 usec_t total_usec) {
1720
1721         int r;
1722
1723         assert(m);
1724
1725         r = bus_manager_foreach_client(m, send_finished,
1726                                    (usec_t[6]) { firmware_usec, loader_usec, kernel_usec, initrd_usec, userspace_usec, total_usec });
1727         if (r < 0)
1728                 log_debug("Failed to send finished signal: %s", strerror(-r));
1729 }
1730
1731 static int send_reloading(sd_bus *bus, const char *destination, void *userdata) {
1732         _cleanup_bus_message_unref_ sd_bus_message *message = NULL;
1733         int r;
1734
1735         assert(bus);
1736
1737         r = sd_bus_message_new_signal(bus, &message, "/org/freedesktop/systemd1", "org.freedesktop.systemd1.Manager", "Reloading");
1738         if (r < 0)
1739                 return r;
1740
1741         r = sd_bus_message_append(message, "b", PTR_TO_INT(userdata));
1742         if (r < 0)
1743                 return r;
1744
1745         return sd_bus_send_to(bus, message, destination, NULL);
1746 }
1747
1748 void bus_manager_send_reloading(Manager *m, bool active) {
1749         int r;
1750
1751         assert(m);
1752
1753         r = bus_manager_foreach_client(m, send_reloading, INT_TO_PTR(active));
1754         if (r < 0)
1755                 log_debug("Failed to send reloading signal: %s", strerror(-r));
1756
1757 }