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