1 /* SPDX-License-Identifier: LGPL-2.1-or-later */
2 
3 #include <errno.h>
4 #include <sys/stat.h>
5 #include <unistd.h>
6 
7 #include "sd-device.h"
8 #include "sd-messages.h"
9 
10 #include "alloc-util.h"
11 #include "audit-util.h"
12 #include "bootspec.h"
13 #include "bus-common-errors.h"
14 #include "bus-error.h"
15 #include "bus-get-properties.h"
16 #include "bus-locator.h"
17 #include "bus-polkit.h"
18 #include "bus-unit-util.h"
19 #include "bus-util.h"
20 #include "cgroup-util.h"
21 #include "device-util.h"
22 #include "dirent-util.h"
23 #include "efi-api.h"
24 #include "efi-loader.h"
25 #include "efivars.h"
26 #include "env-file.h"
27 #include "env-util.h"
28 #include "escape.h"
29 #include "event-util.h"
30 #include "fd-util.h"
31 #include "fileio-label.h"
32 #include "fileio.h"
33 #include "format-util.h"
34 #include "fs-util.h"
35 #include "logind-action.h"
36 #include "logind-dbus.h"
37 #include "logind-polkit.h"
38 #include "logind-seat-dbus.h"
39 #include "logind-session-dbus.h"
40 #include "logind-user-dbus.h"
41 #include "logind.h"
42 #include "missing_capability.h"
43 #include "mkdir-label.h"
44 #include "parse-util.h"
45 #include "path-util.h"
46 #include "process-util.h"
47 #include "reboot-util.h"
48 #include "selinux-util.h"
49 #include "sleep-config.h"
50 #include "special.h"
51 #include "serialize.h"
52 #include "stdio-util.h"
53 #include "strv.h"
54 #include "terminal-util.h"
55 #include "tmpfile-util.h"
56 #include "unit-name.h"
57 #include "user-util.h"
58 #include "utmp-wtmp.h"
59 #include "virt.h"
60 
61 /* As a random fun fact sysvinit had a 252 (256-(strlen(" \r\n")+1))
62  * character limit for the wall message.
63  * https://git.savannah.nongnu.org/cgit/sysvinit.git/tree/src/shutdown.c#n72
64  * There is no real technical need for that but doesn't make sense
65  * to store arbitrary amounts either. As we are not stingy here, we
66  * allow 4k.
67  */
68 #define WALL_MESSAGE_MAX 4096
69 
70 #define SHUTDOWN_SCHEDULE_FILE "/run/systemd/shutdown/scheduled"
71 
72 static int update_schedule_file(Manager *m);
73 static void reset_scheduled_shutdown(Manager *m);
74 static int manager_setup_shutdown_timers(Manager* m);
75 
get_sender_session(Manager * m,sd_bus_message * message,bool consult_display,sd_bus_error * error,Session ** ret)76 static int get_sender_session(
77                 Manager *m,
78                 sd_bus_message *message,
79                 bool consult_display,
80                 sd_bus_error *error,
81                 Session **ret) {
82 
83         _cleanup_(sd_bus_creds_unrefp) sd_bus_creds *creds = NULL;
84         Session *session = NULL;
85         const char *name;
86         int r;
87 
88         /* Acquire the sender's session. This first checks if the sending process is inside a session itself,
89          * and returns that. If not and 'consult_display' is true, this returns the display session of the
90          * owning user of the caller. */
91 
92         r = sd_bus_query_sender_creds(message,
93                                       SD_BUS_CREDS_SESSION|SD_BUS_CREDS_AUGMENT|
94                                       (consult_display ? SD_BUS_CREDS_OWNER_UID : 0), &creds);
95         if (r < 0)
96                 return r;
97 
98         r = sd_bus_creds_get_session(creds, &name);
99         if (r < 0) {
100                 if (r != -ENXIO)
101                         return r;
102 
103                 if (consult_display) {
104                         uid_t uid;
105 
106                         r = sd_bus_creds_get_owner_uid(creds, &uid);
107                         if (r < 0) {
108                                 if (r != -ENXIO)
109                                         return r;
110                         } else {
111                                 User *user;
112 
113                                 user = hashmap_get(m->users, UID_TO_PTR(uid));
114                                 if (user)
115                                         session = user->display;
116                         }
117                 }
118         } else
119                 session = hashmap_get(m->sessions, name);
120 
121         if (!session)
122                 return sd_bus_error_setf(error, BUS_ERROR_NO_SESSION_FOR_PID,
123                                          consult_display ?
124                                          "Caller does not belong to any known session and doesn't own any suitable session." :
125                                          "Caller does not belong to any known session.");
126 
127         *ret = session;
128         return 0;
129 }
130 
manager_get_session_from_creds(Manager * m,sd_bus_message * message,const char * name,sd_bus_error * error,Session ** ret)131 int manager_get_session_from_creds(
132                 Manager *m,
133                 sd_bus_message *message,
134                 const char *name,
135                 sd_bus_error *error,
136                 Session **ret) {
137 
138         Session *session;
139 
140         assert(m);
141         assert(ret);
142 
143         if (SEAT_IS_SELF(name)) /* the caller's own session */
144                 return get_sender_session(m, message, false, error, ret);
145         if (SEAT_IS_AUTO(name)) /* The caller's own session if they have one, otherwise their user's display session */
146                 return get_sender_session(m, message, true, error, ret);
147 
148         session = hashmap_get(m->sessions, name);
149         if (!session)
150                 return sd_bus_error_setf(error, BUS_ERROR_NO_SUCH_SESSION, "No session '%s' known", name);
151 
152         *ret = session;
153         return 0;
154 }
155 
get_sender_user(Manager * m,sd_bus_message * message,sd_bus_error * error,User ** ret)156 static int get_sender_user(Manager *m, sd_bus_message *message, sd_bus_error *error, User **ret) {
157         _cleanup_(sd_bus_creds_unrefp) sd_bus_creds *creds = NULL;
158         uid_t uid;
159         User *user;
160         int r;
161 
162         /* Note that we get the owner UID of the session, not the actual client UID here! */
163         r = sd_bus_query_sender_creds(message, SD_BUS_CREDS_OWNER_UID|SD_BUS_CREDS_AUGMENT, &creds);
164         if (r < 0)
165                 return r;
166 
167         r = sd_bus_creds_get_owner_uid(creds, &uid);
168         if (r < 0) {
169                 if (r != -ENXIO)
170                         return r;
171 
172                 user = NULL;
173         } else
174                 user = hashmap_get(m->users, UID_TO_PTR(uid));
175 
176         if (!user)
177                 return sd_bus_error_setf(error, BUS_ERROR_NO_USER_FOR_PID,
178                                          "Caller does not belong to any logged in or lingering user");
179 
180         *ret = user;
181         return 0;
182 }
183 
manager_get_user_from_creds(Manager * m,sd_bus_message * message,uid_t uid,sd_bus_error * error,User ** ret)184 int manager_get_user_from_creds(Manager *m, sd_bus_message *message, uid_t uid, sd_bus_error *error, User **ret) {
185         User *user;
186 
187         assert(m);
188         assert(ret);
189 
190         if (!uid_is_valid(uid))
191                 return get_sender_user(m, message, error, ret);
192 
193         user = hashmap_get(m->users, UID_TO_PTR(uid));
194         if (!user)
195                 return sd_bus_error_setf(error, BUS_ERROR_NO_SUCH_USER,
196                                          "User ID "UID_FMT" is not logged in or lingering", uid);
197 
198         *ret = user;
199         return 0;
200 }
201 
manager_get_seat_from_creds(Manager * m,sd_bus_message * message,const char * name,sd_bus_error * error,Seat ** ret)202 int manager_get_seat_from_creds(
203                 Manager *m,
204                 sd_bus_message *message,
205                 const char *name,
206                 sd_bus_error *error,
207                 Seat **ret) {
208 
209         Seat *seat;
210         int r;
211 
212         assert(m);
213         assert(ret);
214 
215         if (SEAT_IS_SELF(name) || SEAT_IS_AUTO(name)) {
216                 Session *session;
217 
218                 /* Use these special seat names as session names */
219                 r = manager_get_session_from_creds(m, message, name, error, &session);
220                 if (r < 0)
221                         return r;
222 
223                 seat = session->seat;
224                 if (!seat)
225                         return sd_bus_error_setf(error, BUS_ERROR_NO_SUCH_SEAT, "Session '%s' has no seat.", session->id);
226         } else {
227                 seat = hashmap_get(m->seats, name);
228                 if (!seat)
229                         return sd_bus_error_setf(error, BUS_ERROR_NO_SUCH_SEAT, "No seat '%s' known", name);
230         }
231 
232         *ret = seat;
233         return 0;
234 }
235 
return_test_polkit(sd_bus_message * message,int capability,const char * action,const char ** details,uid_t good_user,sd_bus_error * e)236 static int return_test_polkit(
237                 sd_bus_message *message,
238                 int capability,
239                 const char *action,
240                 const char **details,
241                 uid_t good_user,
242                 sd_bus_error *e) {
243 
244         const char *result;
245         bool challenge;
246         int r;
247 
248         r = bus_test_polkit(message, capability, action, details, good_user, &challenge, e);
249         if (r < 0)
250                 return r;
251 
252         if (r > 0)
253                 result = "yes";
254         else if (challenge)
255                 result = "challenge";
256         else
257                 result = "no";
258 
259         return sd_bus_reply_method_return(message, "s", result);
260 }
261 
property_get_idle_hint(sd_bus * bus,const char * path,const char * interface,const char * property,sd_bus_message * reply,void * userdata,sd_bus_error * error)262 static int property_get_idle_hint(
263                 sd_bus *bus,
264                 const char *path,
265                 const char *interface,
266                 const char *property,
267                 sd_bus_message *reply,
268                 void *userdata,
269                 sd_bus_error *error) {
270 
271         Manager *m = userdata;
272 
273         assert(bus);
274         assert(reply);
275         assert(m);
276 
277         return sd_bus_message_append(reply, "b", manager_get_idle_hint(m, NULL) > 0);
278 }
279 
property_get_idle_since_hint(sd_bus * bus,const char * path,const char * interface,const char * property,sd_bus_message * reply,void * userdata,sd_bus_error * error)280 static int property_get_idle_since_hint(
281                 sd_bus *bus,
282                 const char *path,
283                 const char *interface,
284                 const char *property,
285                 sd_bus_message *reply,
286                 void *userdata,
287                 sd_bus_error *error) {
288 
289         Manager *m = userdata;
290         dual_timestamp t = DUAL_TIMESTAMP_NULL;
291 
292         assert(bus);
293         assert(reply);
294         assert(m);
295 
296         manager_get_idle_hint(m, &t);
297 
298         return sd_bus_message_append(reply, "t", streq(property, "IdleSinceHint") ? t.realtime : t.monotonic);
299 }
300 
property_get_inhibited(sd_bus * bus,const char * path,const char * interface,const char * property,sd_bus_message * reply,void * userdata,sd_bus_error * error)301 static int property_get_inhibited(
302                 sd_bus *bus,
303                 const char *path,
304                 const char *interface,
305                 const char *property,
306                 sd_bus_message *reply,
307                 void *userdata,
308                 sd_bus_error *error) {
309 
310         Manager *m = userdata;
311         InhibitWhat w;
312 
313         assert(bus);
314         assert(reply);
315         assert(m);
316 
317         w = manager_inhibit_what(m, streq(property, "BlockInhibited") ? INHIBIT_BLOCK : INHIBIT_DELAY);
318 
319         return sd_bus_message_append(reply, "s", inhibit_what_to_string(w));
320 }
321 
property_get_preparing(sd_bus * bus,const char * path,const char * interface,const char * property,sd_bus_message * reply,void * userdata,sd_bus_error * error)322 static int property_get_preparing(
323                 sd_bus *bus,
324                 const char *path,
325                 const char *interface,
326                 const char *property,
327                 sd_bus_message *reply,
328                 void *userdata,
329                 sd_bus_error *error) {
330 
331         Manager *m = userdata;
332         bool b = false;
333 
334         assert(bus);
335         assert(reply);
336         assert(m);
337 
338         if (m->delayed_action) {
339                 if (streq(property, "PreparingForShutdown"))
340                         b = m->delayed_action->inhibit_what & INHIBIT_SHUTDOWN;
341                 else
342                         b = m->delayed_action->inhibit_what & INHIBIT_SLEEP;
343         }
344 
345         return sd_bus_message_append(reply, "b", b);
346 }
347 
property_get_scheduled_shutdown(sd_bus * bus,const char * path,const char * interface,const char * property,sd_bus_message * reply,void * userdata,sd_bus_error * error)348 static int property_get_scheduled_shutdown(
349                 sd_bus *bus,
350                 const char *path,
351                 const char *interface,
352                 const char *property,
353                 sd_bus_message *reply,
354                 void *userdata,
355                 sd_bus_error *error) {
356 
357         Manager *m = userdata;
358         int r;
359 
360         assert(bus);
361         assert(reply);
362         assert(m);
363 
364         r = sd_bus_message_open_container(reply, 'r', "st");
365         if (r < 0)
366                 return r;
367 
368         r = sd_bus_message_append(reply, "st",
369                 m->scheduled_shutdown_action ? handle_action_to_string(m->scheduled_shutdown_action->handle) : NULL,
370                 m->scheduled_shutdown_timeout);
371         if (r < 0)
372                 return r;
373 
374         return sd_bus_message_close_container(reply);
375 }
376 
377 static BUS_DEFINE_PROPERTY_GET_ENUM(property_get_handle_action, handle_action, HandleAction);
378 static BUS_DEFINE_PROPERTY_GET(property_get_docked, "b", Manager, manager_is_docked_or_external_displays);
379 static BUS_DEFINE_PROPERTY_GET(property_get_lid_closed, "b", Manager, manager_is_lid_closed);
380 static BUS_DEFINE_PROPERTY_GET_GLOBAL(property_get_on_external_power, "b", manager_is_on_external_power);
381 static BUS_DEFINE_PROPERTY_GET_GLOBAL(property_get_compat_user_tasks_max, "t", CGROUP_LIMIT_MAX);
382 static BUS_DEFINE_PROPERTY_GET_REF(property_get_hashmap_size, "t", Hashmap *, (uint64_t) hashmap_size);
383 
method_get_session(sd_bus_message * message,void * userdata,sd_bus_error * error)384 static int method_get_session(sd_bus_message *message, void *userdata, sd_bus_error *error) {
385         _cleanup_free_ char *p = NULL;
386         Manager *m = userdata;
387         const char *name;
388         Session *session;
389         int r;
390 
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_get_session_from_creds(m, message, name, error, &session);
399         if (r < 0)
400                 return r;
401 
402         p = session_bus_path(session);
403         if (!p)
404                 return -ENOMEM;
405 
406         return sd_bus_reply_method_return(message, "o", p);
407 }
408 
409 /* Get login session of a process.  This is not what you are looking for these days,
410  * as apps may instead belong to a user service unit.  This includes terminal
411  * emulators and hence command-line apps. */
method_get_session_by_pid(sd_bus_message * message,void * userdata,sd_bus_error * error)412 static int method_get_session_by_pid(sd_bus_message *message, void *userdata, sd_bus_error *error) {
413         _cleanup_free_ char *p = NULL;
414         Session *session = NULL;
415         Manager *m = userdata;
416         pid_t pid;
417         int r;
418 
419         assert(message);
420         assert(m);
421 
422         assert_cc(sizeof(pid_t) == sizeof(uint32_t));
423 
424         r = sd_bus_message_read(message, "u", &pid);
425         if (r < 0)
426                 return r;
427         if (pid < 0)
428                 return -EINVAL;
429 
430         if (pid == 0) {
431                 r = manager_get_session_from_creds(m, message, NULL, error, &session);
432                 if (r < 0)
433                         return r;
434         } else {
435                 r = manager_get_session_by_pid(m, pid, &session);
436                 if (r < 0)
437                         return r;
438 
439                 if (!session)
440                         return sd_bus_error_setf(error, BUS_ERROR_NO_SESSION_FOR_PID,
441                                                  "PID "PID_FMT" does not belong to any known session", pid);
442         }
443 
444         p = session_bus_path(session);
445         if (!p)
446                 return -ENOMEM;
447 
448         return sd_bus_reply_method_return(message, "o", p);
449 }
450 
method_get_user(sd_bus_message * message,void * userdata,sd_bus_error * error)451 static int method_get_user(sd_bus_message *message, void *userdata, sd_bus_error *error) {
452         _cleanup_free_ char *p = NULL;
453         Manager *m = userdata;
454         uint32_t uid;
455         User *user;
456         int r;
457 
458         assert(message);
459         assert(m);
460 
461         r = sd_bus_message_read(message, "u", &uid);
462         if (r < 0)
463                 return r;
464 
465         r = manager_get_user_from_creds(m, message, uid, error, &user);
466         if (r < 0)
467                 return r;
468 
469         p = user_bus_path(user);
470         if (!p)
471                 return -ENOMEM;
472 
473         return sd_bus_reply_method_return(message, "o", p);
474 }
475 
method_get_user_by_pid(sd_bus_message * message,void * userdata,sd_bus_error * error)476 static int method_get_user_by_pid(sd_bus_message *message, void *userdata, sd_bus_error *error) {
477         _cleanup_free_ char *p = NULL;
478         Manager *m = userdata;
479         User *user = NULL;
480         pid_t pid;
481         int r;
482 
483         assert(message);
484         assert(m);
485 
486         assert_cc(sizeof(pid_t) == sizeof(uint32_t));
487 
488         r = sd_bus_message_read(message, "u", &pid);
489         if (r < 0)
490                 return r;
491         if (pid < 0)
492                 return -EINVAL;
493 
494         if (pid == 0) {
495                 r = manager_get_user_from_creds(m, message, UID_INVALID, error, &user);
496                 if (r < 0)
497                         return r;
498         } else {
499                 r = manager_get_user_by_pid(m, pid, &user);
500                 if (r < 0)
501                         return r;
502                 if (!user)
503                         return sd_bus_error_setf(error, BUS_ERROR_NO_USER_FOR_PID,
504                                                  "PID "PID_FMT" does not belong to any logged in user or lingering user",
505                                                  pid);
506         }
507 
508         p = user_bus_path(user);
509         if (!p)
510                 return -ENOMEM;
511 
512         return sd_bus_reply_method_return(message, "o", p);
513 }
514 
method_get_seat(sd_bus_message * message,void * userdata,sd_bus_error * error)515 static int method_get_seat(sd_bus_message *message, void *userdata, sd_bus_error *error) {
516         _cleanup_free_ char *p = NULL;
517         Manager *m = userdata;
518         const char *name;
519         Seat *seat;
520         int r;
521 
522         assert(message);
523         assert(m);
524 
525         r = sd_bus_message_read(message, "s", &name);
526         if (r < 0)
527                 return r;
528 
529         r = manager_get_seat_from_creds(m, message, name, error, &seat);
530         if (r < 0)
531                 return r;
532 
533         p = seat_bus_path(seat);
534         if (!p)
535                 return -ENOMEM;
536 
537         return sd_bus_reply_method_return(message, "o", p);
538 }
539 
method_list_sessions(sd_bus_message * message,void * userdata,sd_bus_error * error)540 static int method_list_sessions(sd_bus_message *message, void *userdata, sd_bus_error *error) {
541         _cleanup_(sd_bus_message_unrefp) sd_bus_message *reply = NULL;
542         Manager *m = userdata;
543         Session *session;
544         int r;
545 
546         assert(message);
547         assert(m);
548 
549         r = sd_bus_message_new_method_return(message, &reply);
550         if (r < 0)
551                 return r;
552 
553         r = sd_bus_message_open_container(reply, 'a', "(susso)");
554         if (r < 0)
555                 return r;
556 
557         HASHMAP_FOREACH(session, m->sessions) {
558                 _cleanup_free_ char *p = NULL;
559 
560                 p = session_bus_path(session);
561                 if (!p)
562                         return -ENOMEM;
563 
564                 r = sd_bus_message_append(reply, "(susso)",
565                                           session->id,
566                                           (uint32_t) session->user->user_record->uid,
567                                           session->user->user_record->user_name,
568                                           session->seat ? session->seat->id : "",
569                                           p);
570                 if (r < 0)
571                         return r;
572         }
573 
574         r = sd_bus_message_close_container(reply);
575         if (r < 0)
576                 return r;
577 
578         return sd_bus_send(NULL, reply, NULL);
579 }
580 
method_list_users(sd_bus_message * message,void * userdata,sd_bus_error * error)581 static int method_list_users(sd_bus_message *message, void *userdata, sd_bus_error *error) {
582         _cleanup_(sd_bus_message_unrefp) sd_bus_message *reply = NULL;
583         Manager *m = userdata;
584         User *user;
585         int r;
586 
587         assert(message);
588         assert(m);
589 
590         r = sd_bus_message_new_method_return(message, &reply);
591         if (r < 0)
592                 return r;
593 
594         r = sd_bus_message_open_container(reply, 'a', "(uso)");
595         if (r < 0)
596                 return r;
597 
598         HASHMAP_FOREACH(user, m->users) {
599                 _cleanup_free_ char *p = NULL;
600 
601                 p = user_bus_path(user);
602                 if (!p)
603                         return -ENOMEM;
604 
605                 r = sd_bus_message_append(reply, "(uso)",
606                                           (uint32_t) user->user_record->uid,
607                                           user->user_record->user_name,
608                                           p);
609                 if (r < 0)
610                         return r;
611         }
612 
613         r = sd_bus_message_close_container(reply);
614         if (r < 0)
615                 return r;
616 
617         return sd_bus_send(NULL, reply, NULL);
618 }
619 
method_list_seats(sd_bus_message * message,void * userdata,sd_bus_error * error)620 static int method_list_seats(sd_bus_message *message, void *userdata, sd_bus_error *error) {
621         _cleanup_(sd_bus_message_unrefp) sd_bus_message *reply = NULL;
622         Manager *m = userdata;
623         Seat *seat;
624         int r;
625 
626         assert(message);
627         assert(m);
628 
629         r = sd_bus_message_new_method_return(message, &reply);
630         if (r < 0)
631                 return r;
632 
633         r = sd_bus_message_open_container(reply, 'a', "(so)");
634         if (r < 0)
635                 return r;
636 
637         HASHMAP_FOREACH(seat, m->seats) {
638                 _cleanup_free_ char *p = NULL;
639 
640                 p = seat_bus_path(seat);
641                 if (!p)
642                         return -ENOMEM;
643 
644                 r = sd_bus_message_append(reply, "(so)", seat->id, p);
645                 if (r < 0)
646                         return r;
647         }
648 
649         r = sd_bus_message_close_container(reply);
650         if (r < 0)
651                 return r;
652 
653         return sd_bus_send(NULL, reply, NULL);
654 }
655 
method_list_inhibitors(sd_bus_message * message,void * userdata,sd_bus_error * error)656 static int method_list_inhibitors(sd_bus_message *message, void *userdata, sd_bus_error *error) {
657         _cleanup_(sd_bus_message_unrefp) sd_bus_message *reply = NULL;
658         Manager *m = userdata;
659         Inhibitor *inhibitor;
660         int r;
661 
662         assert(message);
663         assert(m);
664 
665         r = sd_bus_message_new_method_return(message, &reply);
666         if (r < 0)
667                 return r;
668 
669         r = sd_bus_message_open_container(reply, 'a', "(ssssuu)");
670         if (r < 0)
671                 return r;
672 
673         HASHMAP_FOREACH(inhibitor, m->inhibitors) {
674 
675                 r = sd_bus_message_append(reply, "(ssssuu)",
676                                           strempty(inhibit_what_to_string(inhibitor->what)),
677                                           strempty(inhibitor->who),
678                                           strempty(inhibitor->why),
679                                           strempty(inhibit_mode_to_string(inhibitor->mode)),
680                                           (uint32_t) inhibitor->uid,
681                                           (uint32_t) inhibitor->pid);
682                 if (r < 0)
683                         return r;
684         }
685 
686         r = sd_bus_message_close_container(reply);
687         if (r < 0)
688                 return r;
689 
690         return sd_bus_send(NULL, reply, NULL);
691 }
692 
method_create_session(sd_bus_message * message,void * userdata,sd_bus_error * error)693 static int method_create_session(sd_bus_message *message, void *userdata, sd_bus_error *error) {
694         const char *service, *type, *class, *cseat, *tty, *display, *remote_user, *remote_host, *desktop;
695         _cleanup_free_ char *id = NULL;
696         Session *session = NULL;
697         uint32_t audit_id = 0;
698         Manager *m = userdata;
699         User *user = NULL;
700         Seat *seat = NULL;
701         pid_t leader;
702         uid_t uid;
703         int remote;
704         uint32_t vtnr = 0;
705         SessionType t;
706         SessionClass c;
707         int r;
708 
709         assert(message);
710         assert(m);
711 
712         assert_cc(sizeof(pid_t) == sizeof(uint32_t));
713         assert_cc(sizeof(uid_t) == sizeof(uint32_t));
714 
715         r = sd_bus_message_read(message, "uusssssussbss",
716                                 &uid, &leader, &service, &type, &class, &desktop, &cseat,
717                                 &vtnr, &tty, &display, &remote, &remote_user, &remote_host);
718         if (r < 0)
719                 return r;
720 
721         if (!uid_is_valid(uid))
722                 return sd_bus_error_set(error, SD_BUS_ERROR_INVALID_ARGS, "Invalid UID");
723         if (leader < 0 || leader == 1 || leader == getpid_cached())
724                 return sd_bus_error_set(error, SD_BUS_ERROR_INVALID_ARGS, "Invalid leader PID");
725 
726         if (isempty(type))
727                 t = _SESSION_TYPE_INVALID;
728         else {
729                 t = session_type_from_string(type);
730                 if (t < 0)
731                         return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS,
732                                                  "Invalid session type %s", type);
733         }
734 
735         if (isempty(class))
736                 c = _SESSION_CLASS_INVALID;
737         else {
738                 c = session_class_from_string(class);
739                 if (c < 0)
740                         return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS,
741                                                  "Invalid session class %s", class);
742         }
743 
744         if (isempty(desktop))
745                 desktop = NULL;
746         else {
747                 if (!string_is_safe(desktop))
748                         return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS,
749                                                  "Invalid desktop string %s", desktop);
750         }
751 
752         if (isempty(cseat))
753                 seat = NULL;
754         else {
755                 seat = hashmap_get(m->seats, cseat);
756                 if (!seat)
757                         return sd_bus_error_setf(error, BUS_ERROR_NO_SUCH_SEAT,
758                                                  "No seat '%s' known", cseat);
759         }
760 
761         if (tty_is_vc(tty)) {
762                 int v;
763 
764                 if (!seat)
765                         seat = m->seat0;
766                 else if (seat != m->seat0)
767                         return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS,
768                                                  "TTY %s is virtual console but seat %s is not seat0", tty, seat->id);
769 
770                 v = vtnr_from_tty(tty);
771                 if (v <= 0)
772                         return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS,
773                                                  "Cannot determine VT number from virtual console TTY %s", tty);
774 
775                 if (vtnr == 0)
776                         vtnr = (uint32_t) v;
777                 else if (vtnr != (uint32_t) v)
778                         return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS,
779                                                  "Specified TTY and VT number do not match");
780 
781         } else if (tty_is_console(tty)) {
782 
783                 if (!seat)
784                         seat = m->seat0;
785                 else if (seat != m->seat0)
786                         return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS,
787                                                  "Console TTY specified but seat is not seat0");
788 
789                 if (vtnr != 0)
790                         return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS,
791                                                  "Console TTY specified but VT number is not 0");
792         }
793 
794         if (seat) {
795                 if (seat_has_vts(seat)) {
796                         if (vtnr <= 0 || vtnr > 63)
797                                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS,
798                                                          "VT number out of range");
799                 } else {
800                         if (vtnr != 0)
801                                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS,
802                                                          "Seat has no VTs but VT number not 0");
803                 }
804         }
805 
806         if (t == _SESSION_TYPE_INVALID) {
807                 if (!isempty(display))
808                         t = SESSION_X11;
809                 else if (!isempty(tty))
810                         t = SESSION_TTY;
811                 else
812                         t = SESSION_UNSPECIFIED;
813         }
814 
815         if (c == _SESSION_CLASS_INVALID) {
816                 if (t == SESSION_UNSPECIFIED)
817                         c = SESSION_BACKGROUND;
818                 else
819                         c = SESSION_USER;
820         }
821 
822         if (leader == 0) {
823                 _cleanup_(sd_bus_creds_unrefp) sd_bus_creds *creds = NULL;
824 
825                 r = sd_bus_query_sender_creds(message, SD_BUS_CREDS_PID, &creds);
826                 if (r < 0)
827                         return r;
828 
829                 r = sd_bus_creds_get_pid(creds, (pid_t*) &leader);
830                 if (r < 0)
831                         return r;
832         }
833 
834         /* Check if we are already in a logind session. Or if we are in user@.service
835          * which is a special PAM session that avoids creating a logind session. */
836         r = manager_get_user_by_pid(m, leader, NULL);
837         if (r < 0)
838                 return r;
839         if (r > 0)
840                 return sd_bus_error_setf(error, BUS_ERROR_SESSION_BUSY,
841                                          "Already running in a session or user slice");
842 
843         /*
844          * Old gdm and lightdm start the user-session on the same VT as
845          * the greeter session. But they destroy the greeter session
846          * after the user-session and want the user-session to take
847          * over the VT. We need to support this for
848          * backwards-compatibility, so make sure we allow new sessions
849          * on a VT that a greeter is running on. Furthermore, to allow
850          * re-logins, we have to allow a greeter to take over a used VT for
851          * the exact same reasons.
852          */
853         if (c != SESSION_GREETER &&
854             vtnr > 0 &&
855             vtnr < MALLOC_ELEMENTSOF(m->seat0->positions) &&
856             m->seat0->positions[vtnr] &&
857             m->seat0->positions[vtnr]->class != SESSION_GREETER)
858                 return sd_bus_error_set(error, BUS_ERROR_SESSION_BUSY, "Already occupied by a session");
859 
860         if (hashmap_size(m->sessions) >= m->sessions_max)
861                 return sd_bus_error_setf(error, SD_BUS_ERROR_LIMITS_EXCEEDED,
862                                          "Maximum number of sessions (%" PRIu64 ") reached, refusing further sessions.",
863                                          m->sessions_max);
864 
865         (void) audit_session_from_pid(leader, &audit_id);
866         if (audit_session_is_valid(audit_id)) {
867                 /* Keep our session IDs and the audit session IDs in sync */
868 
869                 if (asprintf(&id, "%"PRIu32, audit_id) < 0)
870                         return -ENOMEM;
871 
872                 /* Wut? There's already a session by this name and we didn't find it above? Weird, then let's
873                  * not trust the audit data and let's better register a new ID */
874                 if (hashmap_contains(m->sessions, id)) {
875                         log_warning("Existing logind session ID %s used by new audit session, ignoring.", id);
876                         audit_id = AUDIT_SESSION_INVALID;
877                         id = mfree(id);
878                 }
879         }
880 
881         if (!id) {
882                 do {
883                         id = mfree(id);
884 
885                         if (asprintf(&id, "c%lu", ++m->session_counter) < 0)
886                                 return -ENOMEM;
887 
888                 } while (hashmap_contains(m->sessions, id));
889         }
890 
891         /* The generated names should not clash with 'auto' or 'self' */
892         assert(!SESSION_IS_SELF(id));
893         assert(!SESSION_IS_AUTO(id));
894 
895         /* If we are not watching utmp already, try again */
896         manager_reconnect_utmp(m);
897 
898         r = manager_add_user_by_uid(m, uid, &user);
899         if (r < 0)
900                 goto fail;
901 
902         r = manager_add_session(m, id, &session);
903         if (r < 0)
904                 goto fail;
905 
906         session_set_user(session, user);
907         r = session_set_leader(session, leader);
908         if (r < 0)
909                 goto fail;
910 
911         session->original_type = session->type = t;
912         session->class = c;
913         session->remote = remote;
914         session->vtnr = vtnr;
915 
916         if (!isempty(tty)) {
917                 session->tty = strdup(tty);
918                 if (!session->tty) {
919                         r = -ENOMEM;
920                         goto fail;
921                 }
922 
923                 session->tty_validity = TTY_FROM_PAM;
924         }
925 
926         if (!isempty(display)) {
927                 session->display = strdup(display);
928                 if (!session->display) {
929                         r = -ENOMEM;
930                         goto fail;
931                 }
932         }
933 
934         if (!isempty(remote_user)) {
935                 session->remote_user = strdup(remote_user);
936                 if (!session->remote_user) {
937                         r = -ENOMEM;
938                         goto fail;
939                 }
940         }
941 
942         if (!isempty(remote_host)) {
943                 session->remote_host = strdup(remote_host);
944                 if (!session->remote_host) {
945                         r = -ENOMEM;
946                         goto fail;
947                 }
948         }
949 
950         if (!isempty(service)) {
951                 session->service = strdup(service);
952                 if (!session->service) {
953                         r = -ENOMEM;
954                         goto fail;
955                 }
956         }
957 
958         if (!isempty(desktop)) {
959                 session->desktop = strdup(desktop);
960                 if (!session->desktop) {
961                         r = -ENOMEM;
962                         goto fail;
963                 }
964         }
965 
966         if (seat) {
967                 r = seat_attach_session(seat, session);
968                 if (r < 0)
969                         goto fail;
970         }
971 
972         r = sd_bus_message_enter_container(message, 'a', "(sv)");
973         if (r < 0)
974                 goto fail;
975 
976         r = session_start(session, message, error);
977         if (r < 0)
978                 goto fail;
979 
980         r = sd_bus_message_exit_container(message);
981         if (r < 0)
982                 goto fail;
983 
984         session->create_message = sd_bus_message_ref(message);
985 
986         /* Now, let's wait until the slice unit and stuff got created. We send the reply back from
987          * session_send_create_reply(). */
988 
989         return 1;
990 
991 fail:
992         if (session)
993                 session_add_to_gc_queue(session);
994 
995         if (user)
996                 user_add_to_gc_queue(user);
997 
998         return r;
999 }
1000 
method_release_session(sd_bus_message * message,void * userdata,sd_bus_error * error)1001 static int method_release_session(sd_bus_message *message, void *userdata, sd_bus_error *error) {
1002         Manager *m = userdata;
1003         Session *session;
1004         const char *name;
1005         int r;
1006 
1007         assert(message);
1008         assert(m);
1009 
1010         r = sd_bus_message_read(message, "s", &name);
1011         if (r < 0)
1012                 return r;
1013 
1014         r = manager_get_session_from_creds(m, message, name, error, &session);
1015         if (r < 0)
1016                 return r;
1017 
1018         r = session_release(session);
1019         if (r < 0)
1020                 return r;
1021 
1022         return sd_bus_reply_method_return(message, NULL);
1023 }
1024 
method_activate_session(sd_bus_message * message,void * userdata,sd_bus_error * error)1025 static int method_activate_session(sd_bus_message *message, void *userdata, sd_bus_error *error) {
1026         Manager *m = userdata;
1027         Session *session;
1028         const char *name;
1029         int r;
1030 
1031         assert(message);
1032         assert(m);
1033 
1034         r = sd_bus_message_read(message, "s", &name);
1035         if (r < 0)
1036                 return r;
1037 
1038         r = manager_get_session_from_creds(m, message, name, error, &session);
1039         if (r < 0)
1040                 return r;
1041 
1042         /* PolicyKit is done by bus_session_method_activate() */
1043 
1044         return bus_session_method_activate(message, session, error);
1045 }
1046 
method_activate_session_on_seat(sd_bus_message * message,void * userdata,sd_bus_error * error)1047 static int method_activate_session_on_seat(sd_bus_message *message, void *userdata, sd_bus_error *error) {
1048         const char *session_name, *seat_name;
1049         Manager *m = userdata;
1050         Session *session;
1051         Seat *seat;
1052         int r;
1053 
1054         assert(message);
1055         assert(m);
1056 
1057         /* Same as ActivateSession() but refuses to work if the seat doesn't match */
1058 
1059         r = sd_bus_message_read(message, "ss", &session_name, &seat_name);
1060         if (r < 0)
1061                 return r;
1062 
1063         r = manager_get_session_from_creds(m, message, session_name, error, &session);
1064         if (r < 0)
1065                 return r;
1066 
1067         r = manager_get_seat_from_creds(m, message, seat_name, error, &seat);
1068         if (r < 0)
1069                 return r;
1070 
1071         if (session->seat != seat)
1072                 return sd_bus_error_setf(error, BUS_ERROR_SESSION_NOT_ON_SEAT,
1073                                          "Session %s not on seat %s", session_name, seat_name);
1074 
1075         r = check_polkit_chvt(message, m, error);
1076         if (r < 0)
1077                 return r;
1078         if (r == 0)
1079                 return 1; /* Will call us back */
1080 
1081         r = session_activate(session);
1082         if (r < 0)
1083                 return r;
1084 
1085         return sd_bus_reply_method_return(message, NULL);
1086 }
1087 
method_lock_session(sd_bus_message * message,void * userdata,sd_bus_error * error)1088 static int method_lock_session(sd_bus_message *message, void *userdata, sd_bus_error *error) {
1089         Manager *m = userdata;
1090         Session *session;
1091         const char *name;
1092         int r;
1093 
1094         assert(message);
1095         assert(m);
1096 
1097         r = sd_bus_message_read(message, "s", &name);
1098         if (r < 0)
1099                 return r;
1100 
1101         r = manager_get_session_from_creds(m, message, name, error, &session);
1102         if (r < 0)
1103                 return r;
1104 
1105         return bus_session_method_lock(message, session, error);
1106 }
1107 
method_lock_sessions(sd_bus_message * message,void * userdata,sd_bus_error * error)1108 static int method_lock_sessions(sd_bus_message *message, void *userdata, sd_bus_error *error) {
1109         Manager *m = userdata;
1110         int r;
1111 
1112         assert(message);
1113         assert(m);
1114 
1115         r = bus_verify_polkit_async(
1116                         message,
1117                         CAP_SYS_ADMIN,
1118                         "org.freedesktop.login1.lock-sessions",
1119                         NULL,
1120                         false,
1121                         UID_INVALID,
1122                         &m->polkit_registry,
1123                         error);
1124         if (r < 0)
1125                 return r;
1126         if (r == 0)
1127                 return 1; /* Will call us back */
1128 
1129         r = session_send_lock_all(m, streq(sd_bus_message_get_member(message), "LockSessions"));
1130         if (r < 0)
1131                 return r;
1132 
1133         return sd_bus_reply_method_return(message, NULL);
1134 }
1135 
method_kill_session(sd_bus_message * message,void * userdata,sd_bus_error * error)1136 static int method_kill_session(sd_bus_message *message, void *userdata, sd_bus_error *error) {
1137         const char *name;
1138         Manager *m = userdata;
1139         Session *session;
1140         int r;
1141 
1142         assert(message);
1143         assert(m);
1144 
1145         r = sd_bus_message_read(message, "s", &name);
1146         if (r < 0)
1147                 return r;
1148 
1149         r = manager_get_session_from_creds(m, message, name, error, &session);
1150         if (r < 0)
1151                 return r;
1152 
1153         return bus_session_method_kill(message, session, error);
1154 }
1155 
method_kill_user(sd_bus_message * message,void * userdata,sd_bus_error * error)1156 static int method_kill_user(sd_bus_message *message, void *userdata, sd_bus_error *error) {
1157         Manager *m = userdata;
1158         uint32_t uid;
1159         User *user;
1160         int r;
1161 
1162         assert(message);
1163         assert(m);
1164 
1165         r = sd_bus_message_read(message, "u", &uid);
1166         if (r < 0)
1167                 return r;
1168 
1169         r = manager_get_user_from_creds(m, message, uid, error, &user);
1170         if (r < 0)
1171                 return r;
1172 
1173         return bus_user_method_kill(message, user, error);
1174 }
1175 
method_terminate_session(sd_bus_message * message,void * userdata,sd_bus_error * error)1176 static int method_terminate_session(sd_bus_message *message, void *userdata, sd_bus_error *error) {
1177         Manager *m = userdata;
1178         const char *name;
1179         Session *session;
1180         int r;
1181 
1182         assert(message);
1183         assert(m);
1184 
1185         r = sd_bus_message_read(message, "s", &name);
1186         if (r < 0)
1187                 return r;
1188 
1189         r = manager_get_session_from_creds(m, message, name, error, &session);
1190         if (r < 0)
1191                 return r;
1192 
1193         return bus_session_method_terminate(message, session, error);
1194 }
1195 
method_terminate_user(sd_bus_message * message,void * userdata,sd_bus_error * error)1196 static int method_terminate_user(sd_bus_message *message, void *userdata, sd_bus_error *error) {
1197         Manager *m = userdata;
1198         uint32_t uid;
1199         User *user;
1200         int r;
1201 
1202         assert(message);
1203         assert(m);
1204 
1205         r = sd_bus_message_read(message, "u", &uid);
1206         if (r < 0)
1207                 return r;
1208 
1209         r = manager_get_user_from_creds(m, message, uid, error, &user);
1210         if (r < 0)
1211                 return r;
1212 
1213         return bus_user_method_terminate(message, user, error);
1214 }
1215 
method_terminate_seat(sd_bus_message * message,void * userdata,sd_bus_error * error)1216 static int method_terminate_seat(sd_bus_message *message, void *userdata, sd_bus_error *error) {
1217         Manager *m = userdata;
1218         const char *name;
1219         Seat *seat;
1220         int r;
1221 
1222         assert(message);
1223         assert(m);
1224 
1225         r = sd_bus_message_read(message, "s", &name);
1226         if (r < 0)
1227                 return r;
1228 
1229         r = manager_get_seat_from_creds(m, message, name, error, &seat);
1230         if (r < 0)
1231                 return r;
1232 
1233         return bus_seat_method_terminate(message, seat, error);
1234 }
1235 
method_set_user_linger(sd_bus_message * message,void * userdata,sd_bus_error * error)1236 static int method_set_user_linger(sd_bus_message *message, void *userdata, sd_bus_error *error) {
1237         _cleanup_(sd_bus_creds_unrefp) sd_bus_creds *creds = NULL;
1238         _cleanup_free_ char *cc = NULL;
1239         Manager *m = userdata;
1240         int r, b, interactive;
1241         struct passwd *pw;
1242         const char *path;
1243         uint32_t uid, auth_uid;
1244 
1245         assert(message);
1246         assert(m);
1247 
1248         r = sd_bus_message_read(message, "ubb", &uid, &b, &interactive);
1249         if (r < 0)
1250                 return r;
1251 
1252         r = sd_bus_query_sender_creds(message, SD_BUS_CREDS_EUID |
1253                                                SD_BUS_CREDS_OWNER_UID|SD_BUS_CREDS_AUGMENT, &creds);
1254         if (r < 0)
1255                 return r;
1256 
1257         if (!uid_is_valid(uid)) {
1258                 /* Note that we get the owner UID of the session or user unit,
1259                  * not the actual client UID here! */
1260                 r = sd_bus_creds_get_owner_uid(creds, &uid);
1261                 if (r < 0)
1262                         return r;
1263         }
1264 
1265         /* owner_uid is racy, so for authorization we must use euid */
1266         r = sd_bus_creds_get_euid(creds, &auth_uid);
1267         if (r < 0)
1268                 return r;
1269 
1270         errno = 0;
1271         pw = getpwuid(uid);
1272         if (!pw)
1273                 return errno_or_else(ENOENT);
1274 
1275         r = bus_verify_polkit_async(
1276                         message,
1277                         CAP_SYS_ADMIN,
1278                         uid == auth_uid ? "org.freedesktop.login1.set-self-linger" :
1279                                           "org.freedesktop.login1.set-user-linger",
1280                         NULL,
1281                         interactive,
1282                         UID_INVALID,
1283                         &m->polkit_registry,
1284                         error);
1285         if (r < 0)
1286                 return r;
1287         if (r == 0)
1288                 return 1; /* No authorization for now, but the async polkit stuff will call us again when it has it */
1289 
1290         (void) mkdir_p_label("/var/lib/systemd", 0755);
1291         r = mkdir_safe_label("/var/lib/systemd/linger", 0755, 0, 0, MKDIR_WARN_MODE);
1292         if (r < 0)
1293                 return r;
1294 
1295         cc = cescape(pw->pw_name);
1296         if (!cc)
1297                 return -ENOMEM;
1298 
1299         path = strjoina("/var/lib/systemd/linger/", cc);
1300         if (b) {
1301                 User *u;
1302 
1303                 r = touch(path);
1304                 if (r < 0)
1305                         return r;
1306 
1307                 if (manager_add_user_by_uid(m, uid, &u) >= 0)
1308                         user_start(u);
1309 
1310         } else {
1311                 User *u;
1312 
1313                 r = unlink(path);
1314                 if (r < 0 && errno != ENOENT)
1315                         return -errno;
1316 
1317                 u = hashmap_get(m->users, UID_TO_PTR(uid));
1318                 if (u)
1319                         user_add_to_gc_queue(u);
1320         }
1321 
1322         return sd_bus_reply_method_return(message, NULL);
1323 }
1324 
trigger_device(Manager * m,sd_device * d)1325 static int trigger_device(Manager *m, sd_device *d) {
1326         _cleanup_(sd_device_enumerator_unrefp) sd_device_enumerator *e = NULL;
1327         int r;
1328 
1329         assert(m);
1330 
1331         r = sd_device_enumerator_new(&e);
1332         if (r < 0)
1333                 return r;
1334 
1335         r = sd_device_enumerator_allow_uninitialized(e);
1336         if (r < 0)
1337                 return r;
1338 
1339         if (d) {
1340                 r = sd_device_enumerator_add_match_parent(e, d);
1341                 if (r < 0)
1342                         return r;
1343         }
1344 
1345         FOREACH_DEVICE(e, d) {
1346                 r = sd_device_trigger(d, SD_DEVICE_CHANGE);
1347                 if (r < 0)
1348                         log_device_debug_errno(d, r, "Failed to trigger device, ignoring: %m");
1349         }
1350 
1351         return 0;
1352 }
1353 
attach_device(Manager * m,const char * seat,const char * sysfs)1354 static int attach_device(Manager *m, const char *seat, const char *sysfs) {
1355         _cleanup_(sd_device_unrefp) sd_device *d = NULL;
1356         _cleanup_free_ char *rule = NULL, *file = NULL;
1357         const char *id_for_seat;
1358         int r;
1359 
1360         assert(m);
1361         assert(seat);
1362         assert(sysfs);
1363 
1364         r = sd_device_new_from_syspath(&d, sysfs);
1365         if (r < 0)
1366                 return r;
1367 
1368         if (sd_device_has_current_tag(d, "seat") <= 0)
1369                 return -ENODEV;
1370 
1371         if (sd_device_get_property_value(d, "ID_FOR_SEAT", &id_for_seat) < 0)
1372                 return -ENODEV;
1373 
1374         if (asprintf(&file, "/etc/udev/rules.d/72-seat-%s.rules", id_for_seat) < 0)
1375                 return -ENOMEM;
1376 
1377         if (asprintf(&rule, "TAG==\"seat\", ENV{ID_FOR_SEAT}==\"%s\", ENV{ID_SEAT}=\"%s\"", id_for_seat, seat) < 0)
1378                 return -ENOMEM;
1379 
1380         (void) mkdir_p_label("/etc/udev/rules.d", 0755);
1381         r = write_string_file_atomic_label(file, rule);
1382         if (r < 0)
1383                 return r;
1384 
1385         return trigger_device(m, d);
1386 }
1387 
flush_devices(Manager * m)1388 static int flush_devices(Manager *m) {
1389         _cleanup_closedir_ DIR *d = NULL;
1390 
1391         assert(m);
1392 
1393         d = opendir("/etc/udev/rules.d");
1394         if (!d) {
1395                 if (errno != ENOENT)
1396                         log_warning_errno(errno, "Failed to open /etc/udev/rules.d: %m");
1397         } else
1398                 FOREACH_DIRENT_ALL(de, d, break) {
1399                         if (!dirent_is_file(de))
1400                                 continue;
1401 
1402                         if (!startswith(de->d_name, "72-seat-"))
1403                                 continue;
1404 
1405                         if (!endswith(de->d_name, ".rules"))
1406                                 continue;
1407 
1408                         if (unlinkat(dirfd(d), de->d_name, 0) < 0)
1409                                 log_warning_errno(errno, "Failed to unlink %s: %m", de->d_name);
1410                 }
1411 
1412         return trigger_device(m, NULL);
1413 }
1414 
method_attach_device(sd_bus_message * message,void * userdata,sd_bus_error * error)1415 static int method_attach_device(sd_bus_message *message, void *userdata, sd_bus_error *error) {
1416         const char *sysfs, *seat;
1417         Manager *m = userdata;
1418         int interactive, r;
1419 
1420         assert(message);
1421         assert(m);
1422 
1423         r = sd_bus_message_read(message, "ssb", &seat, &sysfs, &interactive);
1424         if (r < 0)
1425                 return r;
1426 
1427         if (!path_is_normalized(sysfs))
1428                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Path %s is not normalized", sysfs);
1429         if (!path_startswith(sysfs, "/sys"))
1430                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Path %s is not in /sys", sysfs);
1431 
1432         if (SEAT_IS_SELF(seat) || SEAT_IS_AUTO(seat)) {
1433                 Seat *found;
1434 
1435                 r = manager_get_seat_from_creds(m, message, seat, error, &found);
1436                 if (r < 0)
1437                         return r;
1438 
1439                 seat = found->id;
1440 
1441         } else if (!seat_name_is_valid(seat)) /* Note that a seat does not have to exist yet for this operation to succeed */
1442                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Seat name %s is not valid", seat);
1443 
1444         r = bus_verify_polkit_async(
1445                         message,
1446                         CAP_SYS_ADMIN,
1447                         "org.freedesktop.login1.attach-device",
1448                         NULL,
1449                         interactive,
1450                         UID_INVALID,
1451                         &m->polkit_registry,
1452                         error);
1453         if (r < 0)
1454                 return r;
1455         if (r == 0)
1456                 return 1; /* No authorization for now, but the async polkit stuff will call us again when it has it */
1457 
1458         r = attach_device(m, seat, sysfs);
1459         if (r < 0)
1460                 return r;
1461 
1462         return sd_bus_reply_method_return(message, NULL);
1463 }
1464 
method_flush_devices(sd_bus_message * message,void * userdata,sd_bus_error * error)1465 static int method_flush_devices(sd_bus_message *message, void *userdata, sd_bus_error *error) {
1466         Manager *m = userdata;
1467         int interactive, r;
1468 
1469         assert(message);
1470         assert(m);
1471 
1472         r = sd_bus_message_read(message, "b", &interactive);
1473         if (r < 0)
1474                 return r;
1475 
1476         r = bus_verify_polkit_async(
1477                         message,
1478                         CAP_SYS_ADMIN,
1479                         "org.freedesktop.login1.flush-devices",
1480                         NULL,
1481                         interactive,
1482                         UID_INVALID,
1483                         &m->polkit_registry,
1484                         error);
1485         if (r < 0)
1486                 return r;
1487         if (r == 0)
1488                 return 1; /* No authorization for now, but the async polkit stuff will call us again when it has it */
1489 
1490         r = flush_devices(m);
1491         if (r < 0)
1492                 return r;
1493 
1494         return sd_bus_reply_method_return(message, NULL);
1495 }
1496 
have_multiple_sessions(Manager * m,uid_t uid)1497 static int have_multiple_sessions(
1498                 Manager *m,
1499                 uid_t uid) {
1500 
1501         Session *session;
1502 
1503         assert(m);
1504 
1505         /* Check for other users' sessions. Greeter sessions do not
1506          * count, and non-login sessions do not count either. */
1507         HASHMAP_FOREACH(session, m->sessions)
1508                 if (session->class == SESSION_USER &&
1509                     session->user->user_record->uid != uid)
1510                         return true;
1511 
1512         return false;
1513 }
1514 
bus_manager_log_shutdown(Manager * m,const HandleActionData * a)1515 static int bus_manager_log_shutdown(
1516                 Manager *m,
1517                 const HandleActionData *a) {
1518         assert(m);
1519         assert(a);
1520 
1521         const char *message = a->message ?: "System is shutting down";
1522         const char *log_verb = a->log_verb ? strjoina("SHUTDOWN=", a->log_verb) : NULL;
1523 
1524         return log_struct(LOG_NOTICE,
1525                           "MESSAGE_ID=%s", a->message_id ?: SD_MESSAGE_SHUTDOWN_STR,
1526                           LOG_MESSAGE("%s%s%s%s.",
1527                                       message,
1528                                       m->wall_message ? " (" : "",
1529                                       strempty(m->wall_message),
1530                                       m->wall_message ? ")" : ""),
1531                           log_verb);
1532 }
1533 
lid_switch_ignore_handler(sd_event_source * e,uint64_t usec,void * userdata)1534 static int lid_switch_ignore_handler(sd_event_source *e, uint64_t usec, void *userdata) {
1535         Manager *m = userdata;
1536 
1537         assert(e);
1538         assert(m);
1539 
1540         m->lid_switch_ignore_event_source = sd_event_source_unref(m->lid_switch_ignore_event_source);
1541         return 0;
1542 }
1543 
manager_set_lid_switch_ignore(Manager * m,usec_t until)1544 int manager_set_lid_switch_ignore(Manager *m, usec_t until) {
1545         int r;
1546 
1547         assert(m);
1548 
1549         if (until <= now(CLOCK_MONOTONIC))
1550                 return 0;
1551 
1552         /* We want to ignore the lid switch for a while after each
1553          * suspend, and after boot-up. Hence let's install a timer for
1554          * this. As long as the event source exists we ignore the lid
1555          * switch. */
1556 
1557         if (m->lid_switch_ignore_event_source) {
1558                 usec_t u;
1559 
1560                 r = sd_event_source_get_time(m->lid_switch_ignore_event_source, &u);
1561                 if (r < 0)
1562                         return r;
1563 
1564                 if (until <= u)
1565                         return 0;
1566 
1567                 r = sd_event_source_set_time(m->lid_switch_ignore_event_source, until);
1568         } else
1569                 r = sd_event_add_time(
1570                                 m->event,
1571                                 &m->lid_switch_ignore_event_source,
1572                                 CLOCK_MONOTONIC,
1573                                 until, 0,
1574                                 lid_switch_ignore_handler, m);
1575 
1576         return r;
1577 }
1578 
send_prepare_for(Manager * m,InhibitWhat w,bool _active)1579 static int send_prepare_for(Manager *m, InhibitWhat w, bool _active) {
1580         int active = _active;
1581 
1582         assert(m);
1583         assert(IN_SET(w, INHIBIT_SHUTDOWN, INHIBIT_SLEEP));
1584 
1585         return sd_bus_emit_signal(m->bus,
1586                                   "/org/freedesktop/login1",
1587                                   "org.freedesktop.login1.Manager",
1588                                   w == INHIBIT_SHUTDOWN ? "PrepareForShutdown" : "PrepareForSleep",
1589                                   "b",
1590                                   active);
1591 }
1592 
execute_shutdown_or_sleep(Manager * m,const HandleActionData * a,sd_bus_error * error)1593 static int execute_shutdown_or_sleep(
1594                 Manager *m,
1595                 const HandleActionData *a,
1596                 sd_bus_error *error) {
1597 
1598         _cleanup_(sd_bus_message_unrefp) sd_bus_message *reply = NULL;
1599         const char *p;
1600         int r;
1601 
1602         assert(m);
1603         assert(a);
1604 
1605         if (a->inhibit_what == INHIBIT_SHUTDOWN)
1606                 bus_manager_log_shutdown(m, a);
1607 
1608         r = bus_call_method(
1609                         m->bus,
1610                         bus_systemd_mgr,
1611                         "StartUnit",
1612                         error,
1613                         &reply,
1614                         "ss", a->target, "replace-irreversibly");
1615         if (r < 0)
1616                 goto error;
1617 
1618         r = sd_bus_message_read(reply, "o", &p);
1619         if (r < 0)
1620                 goto error;
1621 
1622         r = free_and_strdup(&m->action_job, p);
1623         if (r < 0)
1624                 goto error;
1625 
1626         m->delayed_action = a;
1627 
1628         /* Make sure the lid switch is ignored for a while */
1629         manager_set_lid_switch_ignore(m, usec_add(now(CLOCK_MONOTONIC), m->holdoff_timeout_usec));
1630 
1631         return 0;
1632 
1633 error:
1634         /* Tell people that they now may take a lock again */
1635         (void) send_prepare_for(m, a->inhibit_what, false);
1636 
1637         return r;
1638 }
1639 
manager_dispatch_delayed(Manager * manager,bool timeout)1640 int manager_dispatch_delayed(Manager *manager, bool timeout) {
1641         _cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
1642         Inhibitor *offending = NULL;
1643         int r;
1644 
1645         assert(manager);
1646 
1647         if (!manager->delayed_action || manager->action_job)
1648                 return 0;
1649 
1650         if (manager_is_inhibited(manager, manager->delayed_action->inhibit_what, INHIBIT_DELAY, NULL, false, false, 0, &offending)) {
1651                 _cleanup_free_ char *comm = NULL, *u = NULL;
1652 
1653                 if (!timeout)
1654                         return 0;
1655 
1656                 (void) get_process_comm(offending->pid, &comm);
1657                 u = uid_to_name(offending->uid);
1658 
1659                 log_notice("Delay lock is active (UID "UID_FMT"/%s, PID "PID_FMT"/%s) but inhibitor timeout is reached.",
1660                            offending->uid, strna(u),
1661                            offending->pid, strna(comm));
1662         }
1663 
1664         /* Actually do the operation */
1665         r = execute_shutdown_or_sleep(manager, manager->delayed_action, &error);
1666         if (r < 0) {
1667                 log_warning("Error during inhibitor-delayed operation (already returned success to client): %s",
1668                             bus_error_message(&error, r));
1669 
1670                 manager->delayed_action = NULL;
1671         }
1672 
1673         return 1; /* We did some work. */
1674 }
1675 
manager_inhibit_timeout_handler(sd_event_source * s,uint64_t usec,void * userdata)1676 static int manager_inhibit_timeout_handler(
1677                         sd_event_source *s,
1678                         uint64_t usec,
1679                         void *userdata) {
1680 
1681         Manager *manager = userdata;
1682 
1683         assert(manager);
1684         assert(manager->inhibit_timeout_source == s);
1685 
1686         return manager_dispatch_delayed(manager, true);
1687 }
1688 
delay_shutdown_or_sleep(Manager * m,const HandleActionData * a)1689 static int delay_shutdown_or_sleep(
1690                 Manager *m,
1691                 const HandleActionData *a) {
1692 
1693         int r;
1694 
1695         assert(m);
1696         assert(a);
1697 
1698         if (m->inhibit_timeout_source) {
1699                 r = sd_event_source_set_time_relative(m->inhibit_timeout_source, m->inhibit_delay_max);
1700                 if (r < 0)
1701                         return log_error_errno(r, "sd_event_source_set_time_relative() failed: %m");
1702 
1703                 r = sd_event_source_set_enabled(m->inhibit_timeout_source, SD_EVENT_ONESHOT);
1704                 if (r < 0)
1705                         return log_error_errno(r, "sd_event_source_set_enabled() failed: %m");
1706         } else {
1707                 r = sd_event_add_time_relative(
1708                                 m->event,
1709                                 &m->inhibit_timeout_source,
1710                                 CLOCK_MONOTONIC, m->inhibit_delay_max, 0,
1711                                 manager_inhibit_timeout_handler, m);
1712                 if (r < 0)
1713                         return r;
1714         }
1715 
1716         m->delayed_action = a;
1717 
1718         return 0;
1719 }
1720 
bus_manager_shutdown_or_sleep_now_or_later(Manager * m,const HandleActionData * a,sd_bus_error * error)1721 int bus_manager_shutdown_or_sleep_now_or_later(
1722                 Manager *m,
1723                 const HandleActionData *a,
1724                 sd_bus_error *error) {
1725 
1726         _cleanup_free_ char *load_state = NULL;
1727         bool delayed;
1728         int r;
1729 
1730         assert(m);
1731         assert(a);
1732         assert(!m->action_job);
1733 
1734         r = unit_load_state(m->bus, a->target, &load_state);
1735         if (r < 0)
1736                 return r;
1737 
1738         if (!streq(load_state, "loaded"))
1739                 return log_notice_errno(SYNTHETIC_ERRNO(EACCES),
1740                                         "Unit %s is %s, refusing operation.",
1741                                         a->target, load_state);
1742 
1743         /* Tell everybody to prepare for shutdown/sleep */
1744         (void) send_prepare_for(m, a->inhibit_what, true);
1745 
1746         delayed =
1747                 m->inhibit_delay_max > 0 &&
1748                 manager_is_inhibited(m, a->inhibit_what, INHIBIT_DELAY, NULL, false, false, 0, NULL);
1749 
1750         if (delayed)
1751                 /* Shutdown is delayed, keep in mind what we
1752                  * want to do, and start a timeout */
1753                 r = delay_shutdown_or_sleep(m, a);
1754         else
1755                 /* Shutdown is not delayed, execute it
1756                  * immediately */
1757                 r = execute_shutdown_or_sleep(m, a, error);
1758 
1759         return r;
1760 }
1761 
verify_shutdown_creds(Manager * m,sd_bus_message * message,const HandleActionData * a,uint64_t flags,sd_bus_error * error)1762 static int verify_shutdown_creds(
1763                 Manager *m,
1764                 sd_bus_message *message,
1765                 const HandleActionData *a,
1766                 uint64_t flags,
1767                 sd_bus_error *error) {
1768 
1769         _cleanup_(sd_bus_creds_unrefp) sd_bus_creds *creds = NULL;
1770         bool multiple_sessions, blocked, interactive;
1771         uid_t uid;
1772         int r;
1773 
1774         assert(m);
1775         assert(a);
1776         assert(message);
1777 
1778         r = sd_bus_query_sender_creds(message, SD_BUS_CREDS_EUID, &creds);
1779         if (r < 0)
1780                 return r;
1781 
1782         r = sd_bus_creds_get_euid(creds, &uid);
1783         if (r < 0)
1784                 return r;
1785 
1786         r = have_multiple_sessions(m, uid);
1787         if (r < 0)
1788                 return r;
1789 
1790         multiple_sessions = r > 0;
1791         blocked = manager_is_inhibited(m, a->inhibit_what, INHIBIT_BLOCK, NULL, false, true, uid, NULL);
1792         interactive = flags & SD_LOGIND_INTERACTIVE;
1793 
1794         if (multiple_sessions) {
1795                 r = bus_verify_polkit_async(
1796                                 message,
1797                                 CAP_SYS_BOOT,
1798                                 a->polkit_action_multiple_sessions,
1799                                 NULL,
1800                                 interactive,
1801                                 UID_INVALID,
1802                                 &m->polkit_registry,
1803                                 error);
1804                 if (r < 0)
1805                         return r;
1806                 if (r == 0)
1807                         return 1; /* No authorization for now, but the async polkit stuff will call us again when it has it */
1808         }
1809 
1810         if (blocked) {
1811                 /* We don't check polkit for root here, because you can't be more privileged than root */
1812                 if (uid == 0 && (flags & SD_LOGIND_ROOT_CHECK_INHIBITORS))
1813                         return sd_bus_error_setf(error, SD_BUS_ERROR_ACCESS_DENIED,
1814                                                  "Access denied to root due to active block inhibitor");
1815 
1816                 r = bus_verify_polkit_async(message,
1817                                 CAP_SYS_BOOT,
1818                                 a->polkit_action_ignore_inhibit,
1819                                 NULL,
1820                                 interactive,
1821                                 UID_INVALID,
1822                                 &m->polkit_registry,
1823                                 error);
1824                 if (r < 0)
1825                         return r;
1826                 if (r == 0)
1827                         return 1; /* No authorization for now, but the async polkit stuff will call us again when it has it */
1828         }
1829 
1830         if (!multiple_sessions && !blocked) {
1831                 r = bus_verify_polkit_async(message,
1832                                 CAP_SYS_BOOT,
1833                                 a->polkit_action,
1834                                 NULL,
1835                                 interactive,
1836                                 UID_INVALID,
1837                                 &m->polkit_registry,
1838                                 error);
1839                 if (r < 0)
1840                         return r;
1841                 if (r == 0)
1842                         return 1; /* No authorization for now, but the async polkit stuff will call us again when it has it */
1843         }
1844 
1845         return 0;
1846 }
1847 
setup_wall_message_timer(Manager * m,sd_bus_message * message)1848 static int setup_wall_message_timer(Manager *m, sd_bus_message* message) {
1849         _cleanup_(sd_bus_creds_unrefp) sd_bus_creds *creds = NULL;
1850         int r;
1851 
1852         r = sd_bus_query_sender_creds(message, SD_BUS_CREDS_AUGMENT|SD_BUS_CREDS_TTY|SD_BUS_CREDS_UID, &creds);
1853         if (r >= 0) {
1854                 const char *tty = NULL;
1855 
1856                 (void) sd_bus_creds_get_uid(creds, &m->scheduled_shutdown_uid);
1857                 (void) sd_bus_creds_get_tty(creds, &tty);
1858 
1859                 r = free_and_strdup(&m->scheduled_shutdown_tty, tty);
1860                 if (r < 0)
1861                         return log_oom();
1862         }
1863 
1864         r = manager_setup_wall_message_timer(m);
1865         if (r < 0)
1866                 return r;
1867 
1868         return 0;
1869 }
1870 
method_do_shutdown_or_sleep(Manager * m,sd_bus_message * message,const HandleActionData * a,bool with_flags,sd_bus_error * error)1871 static int method_do_shutdown_or_sleep(
1872                 Manager *m,
1873                 sd_bus_message *message,
1874                 const HandleActionData *a,
1875                 bool with_flags,
1876                 sd_bus_error *error) {
1877 
1878         uint64_t flags;
1879         int r;
1880 
1881         assert(m);
1882         assert(message);
1883         assert(a);
1884 
1885         if (with_flags) {
1886                 /* New style method: with flags parameter (and interactive bool in the bus message header) */
1887                 r = sd_bus_message_read(message, "t", &flags);
1888                 if (r < 0)
1889                         return r;
1890                 if ((flags & ~SD_LOGIND_SHUTDOWN_AND_SLEEP_FLAGS_PUBLIC) != 0)
1891                         return sd_bus_error_set(error, SD_BUS_ERROR_INVALID_ARGS, "Invalid flags parameter");
1892                 if (a->handle != HANDLE_REBOOT && (flags & SD_LOGIND_REBOOT_VIA_KEXEC))
1893                         return sd_bus_error_set(error, SD_BUS_ERROR_INVALID_ARGS, "Reboot via kexec is only applicable with reboot operations");
1894         } else {
1895                 /* Old style method: no flags parameter, but interactive bool passed as boolean in
1896                  * payload. Let's convert this argument to the new-style flags parameter for our internal
1897                  * use. */
1898                 int interactive;
1899 
1900                 r = sd_bus_message_read(message, "b", &interactive);
1901                 if (r < 0)
1902                         return r;
1903 
1904                 flags = interactive ? SD_LOGIND_INTERACTIVE : 0;
1905         }
1906 
1907         if ((flags & SD_LOGIND_REBOOT_VIA_KEXEC) && kexec_loaded())
1908                 a = handle_action_lookup(HANDLE_KEXEC);
1909 
1910         /* Don't allow multiple jobs being executed at the same time */
1911         if (m->delayed_action)
1912                 return sd_bus_error_setf(error, BUS_ERROR_OPERATION_IN_PROGRESS,
1913                                          "There's already a shutdown or sleep operation in progress");
1914 
1915         if (a->sleep_operation >= 0) {
1916                 r = can_sleep(a->sleep_operation);
1917                 if (r == -ENOSPC)
1918                         return sd_bus_error_set(error, BUS_ERROR_SLEEP_VERB_NOT_SUPPORTED,
1919                                                 "Not enough swap space for hibernation");
1920                 if (r == 0)
1921                         return sd_bus_error_setf(error, BUS_ERROR_SLEEP_VERB_NOT_SUPPORTED,
1922                                                  "Sleep verb \"%s\" not supported", sleep_operation_to_string(a->sleep_operation));
1923                 if (r < 0)
1924                         return r;
1925         }
1926 
1927         r = verify_shutdown_creds(m, message, a, flags, error);
1928         if (r != 0)
1929                 return r;
1930 
1931         /* reset case we're shorting a scheduled shutdown */
1932         m->unlink_nologin = false;
1933         reset_scheduled_shutdown(m);
1934 
1935         m->scheduled_shutdown_timeout = 0;
1936         m->scheduled_shutdown_action = a;
1937 
1938         (void) setup_wall_message_timer(m, message);
1939 
1940         r = bus_manager_shutdown_or_sleep_now_or_later(m, a, error);
1941         if (r < 0)
1942                 return r;
1943 
1944         return sd_bus_reply_method_return(message, NULL);
1945 }
1946 
method_poweroff(sd_bus_message * message,void * userdata,sd_bus_error * error)1947 static int method_poweroff(sd_bus_message *message, void *userdata, sd_bus_error *error) {
1948         Manager *m = userdata;
1949 
1950         return method_do_shutdown_or_sleep(
1951                         m, message,
1952                         handle_action_lookup(HANDLE_POWEROFF),
1953                         sd_bus_message_is_method_call(message, NULL, "PowerOffWithFlags"),
1954                         error);
1955 }
1956 
method_reboot(sd_bus_message * message,void * userdata,sd_bus_error * error)1957 static int method_reboot(sd_bus_message *message, void *userdata, sd_bus_error *error) {
1958         Manager *m = userdata;
1959 
1960         return method_do_shutdown_or_sleep(
1961                         m, message,
1962                         handle_action_lookup(HANDLE_REBOOT),
1963                         sd_bus_message_is_method_call(message, NULL, "RebootWithFlags"),
1964                         error);
1965 }
1966 
method_halt(sd_bus_message * message,void * userdata,sd_bus_error * error)1967 static int method_halt(sd_bus_message *message, void *userdata, sd_bus_error *error) {
1968         Manager *m = userdata;
1969 
1970         return method_do_shutdown_or_sleep(
1971                         m, message,
1972                         handle_action_lookup(HANDLE_HALT),
1973                         sd_bus_message_is_method_call(message, NULL, "HaltWithFlags"),
1974                         error);
1975 }
1976 
method_suspend(sd_bus_message * message,void * userdata,sd_bus_error * error)1977 static int method_suspend(sd_bus_message *message, void *userdata, sd_bus_error *error) {
1978         Manager *m = userdata;
1979 
1980         return method_do_shutdown_or_sleep(
1981                         m, message,
1982                         handle_action_lookup(HANDLE_SUSPEND),
1983                         sd_bus_message_is_method_call(message, NULL, "SuspendWithFlags"),
1984                         error);
1985 }
1986 
method_hibernate(sd_bus_message * message,void * userdata,sd_bus_error * error)1987 static int method_hibernate(sd_bus_message *message, void *userdata, sd_bus_error *error) {
1988         Manager *m = userdata;
1989 
1990         return method_do_shutdown_or_sleep(
1991                         m, message,
1992                         handle_action_lookup(HANDLE_HIBERNATE),
1993                         sd_bus_message_is_method_call(message, NULL, "HibernateWithFlags"),
1994                         error);
1995 }
1996 
method_hybrid_sleep(sd_bus_message * message,void * userdata,sd_bus_error * error)1997 static int method_hybrid_sleep(sd_bus_message *message, void *userdata, sd_bus_error *error) {
1998         Manager *m = userdata;
1999 
2000         return method_do_shutdown_or_sleep(
2001                         m, message,
2002                         handle_action_lookup(HANDLE_HYBRID_SLEEP),
2003                         sd_bus_message_is_method_call(message, NULL, "HybridSleepWithFlags"),
2004                         error);
2005 }
2006 
method_suspend_then_hibernate(sd_bus_message * message,void * userdata,sd_bus_error * error)2007 static int method_suspend_then_hibernate(sd_bus_message *message, void *userdata, sd_bus_error *error) {
2008         Manager *m = userdata;
2009 
2010         return method_do_shutdown_or_sleep(
2011                         m, message,
2012                         handle_action_lookup(HANDLE_SUSPEND_THEN_HIBERNATE),
2013                         sd_bus_message_is_method_call(message, NULL, "SuspendThenHibernateWithFlags"),
2014                         error);
2015 }
2016 
nologin_timeout_handler(sd_event_source * s,uint64_t usec,void * userdata)2017 static int nologin_timeout_handler(
2018                         sd_event_source *s,
2019                         uint64_t usec,
2020                         void *userdata) {
2021 
2022         Manager *m = userdata;
2023 
2024         log_info("Creating /run/nologin, blocking further logins...");
2025 
2026         m->unlink_nologin =
2027                 create_shutdown_run_nologin_or_warn() >= 0;
2028 
2029         return 0;
2030 }
2031 
nologin_timeout_usec(usec_t elapse)2032 static usec_t nologin_timeout_usec(usec_t elapse) {
2033         /* Issue /run/nologin five minutes before shutdown */
2034         return LESS_BY(elapse, 5 * USEC_PER_MINUTE);
2035 }
2036 
manager_load_scheduled_shutdown(Manager * m)2037 void manager_load_scheduled_shutdown(Manager *m) {
2038         _cleanup_fclose_ FILE *f = NULL;
2039         _cleanup_free_ char *usec = NULL,
2040                *warn_wall = NULL,
2041                *mode = NULL,
2042                *wall_message = NULL,
2043                *uid = NULL,
2044                *tty = NULL;
2045         int r;
2046 
2047         assert(m);
2048 
2049         r = parse_env_file(f, SHUTDOWN_SCHEDULE_FILE,
2050                         "USEC", &usec,
2051                         "WARN_WALL", &warn_wall,
2052                         "MODE", &mode,
2053                         "WALL_MESSAGE", &wall_message,
2054                         "UID", &uid,
2055                         "TTY", &tty);
2056 
2057         /* reset will delete the file */
2058         reset_scheduled_shutdown(m);
2059 
2060         if (r == -ENOENT)
2061                 return;
2062         if (r < 0)
2063                 return (void) log_debug_errno(r, "Failed to parse " SHUTDOWN_SCHEDULE_FILE ": %m");
2064 
2065         HandleAction handle = handle_action_from_string(mode);
2066         if (handle < 0)
2067                 return (void) log_debug_errno(SYNTHETIC_ERRNO(EINVAL), "Failed to parse scheduled shutdown type: %s", mode);
2068 
2069         if (!usec)
2070                 return (void) log_debug_errno(SYNTHETIC_ERRNO(EINVAL), "USEC is required");
2071         if (deserialize_usec(usec, &m->scheduled_shutdown_timeout) < 0)
2072                 return;
2073 
2074         /* assign parsed type only after we know usec is also valid */
2075         m->scheduled_shutdown_action = handle_action_lookup(handle);
2076 
2077         if (warn_wall) {
2078                 r = parse_boolean(warn_wall);
2079                 if (r < 0)
2080                         log_debug_errno(r, "Failed to parse enabling wall messages");
2081                 else
2082                         m->enable_wall_messages = r;
2083         }
2084 
2085         if (wall_message) {
2086                 _cleanup_free_ char *unescaped = NULL;
2087                 r = cunescape(wall_message, 0, &unescaped);
2088                 if (r < 0)
2089                         log_debug_errno(r, "Failed to parse wall message: %s", wall_message);
2090                 else
2091                         free_and_replace(m->wall_message, unescaped);
2092         }
2093 
2094         if (uid) {
2095                 r = parse_uid(uid, &m->scheduled_shutdown_uid);
2096                 if (r < 0)
2097                         log_debug_errno(r, "Failed to parse wall uid: %s", uid);
2098         }
2099 
2100         free_and_replace(m->scheduled_shutdown_tty, tty);
2101 
2102         r = manager_setup_shutdown_timers(m);
2103         if (r < 0)
2104                 return reset_scheduled_shutdown(m);
2105 
2106         (void) manager_setup_wall_message_timer(m);
2107         (void) update_schedule_file(m);
2108 
2109         return;
2110 }
2111 
update_schedule_file(Manager * m)2112 static int update_schedule_file(Manager *m) {
2113         _cleanup_free_ char *temp_path = NULL;
2114         _cleanup_fclose_ FILE *f = NULL;
2115         int r;
2116 
2117         assert(m);
2118         assert(m->scheduled_shutdown_action);
2119 
2120         r = mkdir_parents_label(SHUTDOWN_SCHEDULE_FILE, 0755);
2121         if (r < 0)
2122                 return log_error_errno(r, "Failed to create shutdown subdirectory: %m");
2123 
2124         r = fopen_temporary(SHUTDOWN_SCHEDULE_FILE, &f, &temp_path);
2125         if (r < 0)
2126                 return log_error_errno(r, "Failed to save information about scheduled shutdowns: %m");
2127 
2128         (void) fchmod(fileno(f), 0644);
2129 
2130         serialize_usec(f, "USEC", m->scheduled_shutdown_timeout);
2131         serialize_item_format(f, "WARN_WALL", "%s", one_zero(m->enable_wall_messages));
2132         serialize_item_format(f, "MODE", "%s", handle_action_to_string(m->scheduled_shutdown_action->handle));
2133         serialize_item_format(f, "UID", UID_FMT, m->scheduled_shutdown_uid);
2134 
2135         if (m->scheduled_shutdown_tty)
2136                 serialize_item_format(f, "TTY", "%s", m->scheduled_shutdown_tty);
2137 
2138         if (!isempty(m->wall_message)) {
2139                 r = serialize_item_escaped(f, "WALL_MESSAGE", m->wall_message);
2140                 if (r < 0)
2141                         goto fail;
2142         }
2143 
2144         r = fflush_and_check(f);
2145         if (r < 0)
2146                 goto fail;
2147 
2148         if (rename(temp_path, SHUTDOWN_SCHEDULE_FILE) < 0) {
2149                 r = -errno;
2150                 goto fail;
2151         }
2152 
2153         return 0;
2154 
2155 fail:
2156         (void) unlink(temp_path);
2157         (void) unlink(SHUTDOWN_SCHEDULE_FILE);
2158 
2159         return log_error_errno(r, "Failed to write information about scheduled shutdowns: %m");
2160 }
2161 
reset_scheduled_shutdown(Manager * m)2162 static void reset_scheduled_shutdown(Manager *m) {
2163         assert(m);
2164 
2165         m->scheduled_shutdown_timeout_source = sd_event_source_unref(m->scheduled_shutdown_timeout_source);
2166         m->wall_message_timeout_source = sd_event_source_unref(m->wall_message_timeout_source);
2167         m->nologin_timeout_source = sd_event_source_unref(m->nologin_timeout_source);
2168 
2169         m->scheduled_shutdown_action = NULL;
2170         m->scheduled_shutdown_timeout = USEC_INFINITY;
2171         m->scheduled_shutdown_uid = UID_INVALID;
2172         m->scheduled_shutdown_tty = mfree(m->scheduled_shutdown_tty);
2173         m->wall_message = mfree(m->wall_message);
2174         m->shutdown_dry_run = false;
2175 
2176         if (m->unlink_nologin) {
2177                 (void) unlink_or_warn("/run/nologin");
2178                 m->unlink_nologin = false;
2179         }
2180 
2181         (void) unlink(SHUTDOWN_SCHEDULE_FILE);
2182 }
2183 
manager_scheduled_shutdown_handler(sd_event_source * s,uint64_t usec,void * userdata)2184 static int manager_scheduled_shutdown_handler(
2185                         sd_event_source *s,
2186                         uint64_t usec,
2187                         void *userdata) {
2188 
2189         const HandleActionData *a = NULL;
2190         _cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
2191         Manager *m = userdata;
2192         int r;
2193 
2194         assert(m);
2195 
2196         a = m->scheduled_shutdown_action;
2197         assert(a);
2198 
2199         /* Don't allow multiple jobs being executed at the same time */
2200         if (m->delayed_action) {
2201                 r = -EALREADY;
2202                 log_error("Scheduled shutdown to %s failed: shutdown or sleep operation already in progress", a->target);
2203                 goto error;
2204         }
2205 
2206         if (m->shutdown_dry_run) {
2207                 /* We do not process delay inhibitors here.  Otherwise, we
2208                  * would have to be considered "in progress" (like the check
2209                  * above) for some seconds after our admin has seen the final
2210                  * wall message. */
2211 
2212                 bus_manager_log_shutdown(m, a);
2213                 log_info("Running in dry run, suppressing action.");
2214                 reset_scheduled_shutdown(m);
2215 
2216                 return 0;
2217         }
2218 
2219         r = bus_manager_shutdown_or_sleep_now_or_later(m, m->scheduled_shutdown_action, &error);
2220         if (r < 0) {
2221                 log_error_errno(r, "Scheduled shutdown to %s failed: %m", a->target);
2222                 goto error;
2223         }
2224 
2225         return 0;
2226 
2227 error:
2228         reset_scheduled_shutdown(m);
2229         return r;
2230 }
2231 
method_schedule_shutdown(sd_bus_message * message,void * userdata,sd_bus_error * error)2232 static int method_schedule_shutdown(sd_bus_message *message, void *userdata, sd_bus_error *error) {
2233         Manager *m = userdata;
2234         HandleAction handle;
2235         const HandleActionData *a;
2236         uint64_t elapse;
2237         char *type;
2238         int r;
2239         bool dry_run = false;
2240 
2241         assert(m);
2242         assert(message);
2243 
2244         r = sd_bus_message_read(message, "st", &type, &elapse);
2245         if (r < 0)
2246                 return r;
2247 
2248         if (startswith(type, "dry-")) {
2249                 type += 4;
2250                 dry_run = true;
2251         }
2252 
2253         handle = handle_action_from_string(type);
2254         if (!IN_SET(handle, HANDLE_POWEROFF, HANDLE_REBOOT, HANDLE_HALT, HANDLE_KEXEC))
2255                 return sd_bus_error_set(error, SD_BUS_ERROR_INVALID_ARGS, "Unsupported shutdown type");
2256 
2257         a = handle_action_lookup(handle);
2258         assert(a);
2259         assert(a->polkit_action);
2260 
2261         r = verify_shutdown_creds(m, message, a, 0, error);
2262         if (r != 0)
2263                 return r;
2264 
2265         m->scheduled_shutdown_action = a;
2266         m->shutdown_dry_run = dry_run;
2267         m->scheduled_shutdown_timeout = elapse;
2268 
2269         r = manager_setup_shutdown_timers(m);
2270         if (r < 0)
2271                 return r;
2272 
2273         r = setup_wall_message_timer(m, message);
2274         if (r >= 0)
2275                 r = update_schedule_file(m);
2276 
2277         if (r < 0) {
2278                 reset_scheduled_shutdown(m);
2279                 return r;
2280         }
2281 
2282         return sd_bus_reply_method_return(message, NULL);
2283 }
2284 
manager_setup_shutdown_timers(Manager * m)2285 static int manager_setup_shutdown_timers(Manager* m) {
2286         int r;
2287 
2288         r = event_reset_time(m->event, &m->scheduled_shutdown_timeout_source,
2289                              CLOCK_REALTIME,
2290                              m->scheduled_shutdown_timeout, 0,
2291                              manager_scheduled_shutdown_handler, m,
2292                              0, "scheduled-shutdown-timeout", true);
2293         if (r < 0)
2294                 goto fail;
2295 
2296         r = event_reset_time(m->event, &m->nologin_timeout_source,
2297                              CLOCK_REALTIME,
2298                              nologin_timeout_usec(m->scheduled_shutdown_timeout), 0,
2299                              nologin_timeout_handler, m,
2300                              0, "nologin-timeout", true);
2301         if (r < 0)
2302                 goto fail;
2303 
2304         return 0;
2305 
2306 fail:
2307         m->scheduled_shutdown_timeout_source = sd_event_source_unref(m->scheduled_shutdown_timeout_source);
2308         m->nologin_timeout_source = sd_event_source_unref(m->nologin_timeout_source);
2309 
2310         return r;
2311 }
2312 
method_cancel_scheduled_shutdown(sd_bus_message * message,void * userdata,sd_bus_error * error)2313 static int method_cancel_scheduled_shutdown(sd_bus_message *message, void *userdata, sd_bus_error *error) {
2314         Manager *m = userdata;
2315         const HandleActionData *a;
2316         bool cancelled;
2317         int r;
2318 
2319         assert(m);
2320         assert(message);
2321 
2322         cancelled = m->scheduled_shutdown_action
2323                 && !IN_SET(m->scheduled_shutdown_action->handle, HANDLE_IGNORE, _HANDLE_ACTION_INVALID);
2324         if (!cancelled)
2325                 return sd_bus_reply_method_return(message, "b", false);
2326 
2327         a = m->scheduled_shutdown_action;
2328         if (!a->polkit_action)
2329                 return sd_bus_error_set(error, SD_BUS_ERROR_AUTH_FAILED, "Unsupported shutdown type");
2330 
2331         r = bus_verify_polkit_async(
2332                         message,
2333                         CAP_SYS_BOOT,
2334                         a->polkit_action,
2335                         NULL,
2336                         false,
2337                         UID_INVALID,
2338                         &m->polkit_registry,
2339                         error);
2340         if (r < 0)
2341                 return r;
2342         if (r == 0)
2343                 return 1; /* No authorization for now, but the async polkit stuff will call us again when it has it */
2344 
2345         reset_scheduled_shutdown(m);
2346 
2347         if (m->enable_wall_messages) {
2348                 _cleanup_(sd_bus_creds_unrefp) sd_bus_creds *creds = NULL;
2349                 _cleanup_free_ char *username = NULL;
2350                 const char *tty = NULL;
2351                 uid_t uid = 0;
2352 
2353                 r = sd_bus_query_sender_creds(message, SD_BUS_CREDS_AUGMENT|SD_BUS_CREDS_TTY|SD_BUS_CREDS_UID, &creds);
2354                 if (r >= 0) {
2355                         (void) sd_bus_creds_get_uid(creds, &uid);
2356                         (void) sd_bus_creds_get_tty(creds, &tty);
2357                 }
2358 
2359                 username = uid_to_name(uid);
2360                 utmp_wall("The system shutdown has been cancelled",
2361                           username, tty, logind_wall_tty_filter, m);
2362         }
2363 
2364         return sd_bus_reply_method_return(message, "b", true);
2365 }
2366 
method_can_shutdown_or_sleep(Manager * m,sd_bus_message * message,const HandleActionData * a,sd_bus_error * error)2367 static int method_can_shutdown_or_sleep(
2368                 Manager *m,
2369                 sd_bus_message *message,
2370                 const HandleActionData *a,
2371                 sd_bus_error *error) {
2372 
2373         _cleanup_(sd_bus_creds_unrefp) sd_bus_creds *creds = NULL;
2374         bool multiple_sessions, challenge, blocked;
2375         const char *result = NULL;
2376         uid_t uid;
2377         int r;
2378 
2379         assert(m);
2380         assert(message);
2381         assert(a);
2382 
2383         if (a->sleep_operation >= 0) {
2384                 r = can_sleep(a->sleep_operation);
2385                 if (IN_SET(r,  0, -ENOSPC))
2386                         return sd_bus_reply_method_return(message, "s", "na");
2387                 if (r < 0)
2388                         return r;
2389         }
2390 
2391         r = sd_bus_query_sender_creds(message, SD_BUS_CREDS_EUID, &creds);
2392         if (r < 0)
2393                 return r;
2394 
2395         r = sd_bus_creds_get_euid(creds, &uid);
2396         if (r < 0)
2397                 return r;
2398 
2399         r = have_multiple_sessions(m, uid);
2400         if (r < 0)
2401                 return r;
2402 
2403         multiple_sessions = r > 0;
2404         blocked = manager_is_inhibited(m, a->inhibit_what, INHIBIT_BLOCK, NULL, false, true, uid, NULL);
2405 
2406         HandleAction handle = handle_action_from_string(sleep_operation_to_string(a->sleep_operation));
2407         if (handle >= 0) {
2408                 const char *target;
2409 
2410                 target = handle_action_lookup(handle)->target;
2411                 if (target) {
2412                         _cleanup_free_ char *load_state = NULL;
2413 
2414                         r = unit_load_state(m->bus, target, &load_state);
2415                         if (r < 0)
2416                                 return r;
2417 
2418                         if (!streq(load_state, "loaded")) {
2419                                 result = "no";
2420                                 goto finish;
2421                         }
2422                 }
2423         }
2424 
2425         if (multiple_sessions) {
2426                 r = bus_test_polkit(message, CAP_SYS_BOOT, a->polkit_action_multiple_sessions, NULL, UID_INVALID, &challenge, error);
2427                 if (r < 0)
2428                         return r;
2429 
2430                 if (r > 0)
2431                         result = "yes";
2432                 else if (challenge)
2433                         result = "challenge";
2434                 else
2435                         result = "no";
2436         }
2437 
2438         if (blocked) {
2439                 r = bus_test_polkit(message, CAP_SYS_BOOT, a->polkit_action_ignore_inhibit, NULL, UID_INVALID, &challenge, error);
2440                 if (r < 0)
2441                         return r;
2442 
2443                 if (r > 0) {
2444                         if (!result)
2445                                 result = "yes";
2446                 } else if (challenge) {
2447                         if (!result || streq(result, "yes"))
2448                                 result = "challenge";
2449                 } else
2450                         result = "no";
2451         }
2452 
2453         if (!multiple_sessions && !blocked) {
2454                 /* If neither inhibit nor multiple sessions
2455                  * apply then just check the normal policy */
2456 
2457                 r = bus_test_polkit(message, CAP_SYS_BOOT, a->polkit_action, NULL, UID_INVALID, &challenge, error);
2458                 if (r < 0)
2459                         return r;
2460 
2461                 if (r > 0)
2462                         result = "yes";
2463                 else if (challenge)
2464                         result = "challenge";
2465                 else
2466                         result = "no";
2467         }
2468 
2469  finish:
2470         return sd_bus_reply_method_return(message, "s", result);
2471 }
2472 
method_can_poweroff(sd_bus_message * message,void * userdata,sd_bus_error * error)2473 static int method_can_poweroff(sd_bus_message *message, void *userdata, sd_bus_error *error) {
2474         Manager *m = userdata;
2475 
2476         return method_can_shutdown_or_sleep(
2477                         m, message, handle_action_lookup(HANDLE_POWEROFF),
2478                         error);
2479 }
2480 
method_can_reboot(sd_bus_message * message,void * userdata,sd_bus_error * error)2481 static int method_can_reboot(sd_bus_message *message, void *userdata, sd_bus_error *error) {
2482         Manager *m = userdata;
2483 
2484         return method_can_shutdown_or_sleep(
2485                         m, message, handle_action_lookup(HANDLE_REBOOT),
2486                         error);
2487 }
2488 
method_can_halt(sd_bus_message * message,void * userdata,sd_bus_error * error)2489 static int method_can_halt(sd_bus_message *message, void *userdata, sd_bus_error *error) {
2490         Manager *m = userdata;
2491 
2492         return method_can_shutdown_or_sleep(
2493                         m, message, handle_action_lookup(HANDLE_HALT),
2494                         error);
2495 }
2496 
method_can_suspend(sd_bus_message * message,void * userdata,sd_bus_error * error)2497 static int method_can_suspend(sd_bus_message *message, void *userdata, sd_bus_error *error) {
2498         Manager *m = userdata;
2499 
2500         return method_can_shutdown_or_sleep(
2501                         m, message, handle_action_lookup(HANDLE_SUSPEND),
2502                         error);
2503 }
2504 
method_can_hibernate(sd_bus_message * message,void * userdata,sd_bus_error * error)2505 static int method_can_hibernate(sd_bus_message *message, void *userdata, sd_bus_error *error) {
2506         Manager *m = userdata;
2507 
2508         return method_can_shutdown_or_sleep(
2509                         m, message, handle_action_lookup(HANDLE_HIBERNATE),
2510                         error);
2511 }
2512 
method_can_hybrid_sleep(sd_bus_message * message,void * userdata,sd_bus_error * error)2513 static int method_can_hybrid_sleep(sd_bus_message *message, void *userdata, sd_bus_error *error) {
2514         Manager *m = userdata;
2515 
2516         return method_can_shutdown_or_sleep(
2517                         m, message, handle_action_lookup(HANDLE_HYBRID_SLEEP),
2518                         error);
2519 }
2520 
method_can_suspend_then_hibernate(sd_bus_message * message,void * userdata,sd_bus_error * error)2521 static int method_can_suspend_then_hibernate(sd_bus_message *message, void *userdata, sd_bus_error *error) {
2522         Manager *m = userdata;
2523 
2524         return method_can_shutdown_or_sleep(
2525                         m, message, handle_action_lookup(HANDLE_SUSPEND_THEN_HIBERNATE),
2526                         error);
2527 }
2528 
property_get_reboot_parameter(sd_bus * bus,const char * path,const char * interface,const char * property,sd_bus_message * reply,void * userdata,sd_bus_error * error)2529 static int property_get_reboot_parameter(
2530                 sd_bus *bus,
2531                 const char *path,
2532                 const char *interface,
2533                 const char *property,
2534                 sd_bus_message *reply,
2535                 void *userdata,
2536                 sd_bus_error *error) {
2537         _cleanup_free_ char *parameter = NULL;
2538         int r;
2539 
2540         assert(bus);
2541         assert(reply);
2542         assert(userdata);
2543 
2544         r = read_reboot_parameter(&parameter);
2545         if (r < 0)
2546                 return r;
2547 
2548         return sd_bus_message_append(reply, "s", parameter);
2549 }
2550 
method_set_reboot_parameter(sd_bus_message * message,void * userdata,sd_bus_error * error)2551 static int method_set_reboot_parameter(
2552                 sd_bus_message *message,
2553                 void *userdata,
2554                 sd_bus_error *error) {
2555 
2556         Manager *m = userdata;
2557         const char *arg;
2558         int r;
2559 
2560         assert(message);
2561         assert(m);
2562 
2563         r = sd_bus_message_read(message, "s", &arg);
2564         if (r < 0)
2565                 return r;
2566 
2567         r = detect_container();
2568         if (r < 0)
2569                 return r;
2570         if (r > 0)
2571                 return sd_bus_error_setf(error, SD_BUS_ERROR_NOT_SUPPORTED,
2572                                          "Reboot parameter not supported in containers, refusing.");
2573 
2574         r = bus_verify_polkit_async(message,
2575                                     CAP_SYS_ADMIN,
2576                                     "org.freedesktop.login1.set-reboot-parameter",
2577                                     NULL,
2578                                     false,
2579                                     UID_INVALID,
2580                                     &m->polkit_registry,
2581                                     error);
2582         if (r < 0)
2583                 return r;
2584         if (r == 0)
2585                 return 1; /* No authorization for now, but the async polkit stuff will call us again when it has it */
2586 
2587         r = update_reboot_parameter_and_warn(arg, false);
2588         if (r < 0)
2589                 return r;
2590 
2591         return sd_bus_reply_method_return(message, NULL);
2592 }
2593 
method_can_reboot_parameter(sd_bus_message * message,void * userdata,sd_bus_error * error)2594 static int method_can_reboot_parameter(
2595                 sd_bus_message *message,
2596                 void *userdata,
2597                 sd_bus_error *error) {
2598 
2599         _unused_ Manager *m = userdata;
2600         int r;
2601 
2602         assert(message);
2603         assert(m);
2604 
2605         r = detect_container();
2606         if (r < 0)
2607                 return r;
2608         if (r > 0) /* Inside containers, specifying a reboot parameter, doesn't make much sense */
2609                 return sd_bus_reply_method_return(message, "s", "na");
2610 
2611         return return_test_polkit(
2612                         message,
2613                         CAP_SYS_ADMIN,
2614                         "org.freedesktop.login1.set-reboot-parameter",
2615                         NULL,
2616                         UID_INVALID,
2617                         error);
2618 }
2619 
property_get_reboot_to_firmware_setup(sd_bus * bus,const char * path,const char * interface,const char * property,sd_bus_message * reply,void * userdata,sd_bus_error * error)2620 static int property_get_reboot_to_firmware_setup(
2621                 sd_bus *bus,
2622                 const char *path,
2623                 const char *interface,
2624                 const char *property,
2625                 sd_bus_message *reply,
2626                 void *userdata,
2627                 sd_bus_error *error) {
2628         int r;
2629 
2630         assert(bus);
2631         assert(reply);
2632         assert(userdata);
2633 
2634         r = getenv_bool("SYSTEMD_REBOOT_TO_FIRMWARE_SETUP");
2635         if (r == -ENXIO) {
2636                 /* EFI case: let's see what is currently configured in the EFI variables */
2637                 r = efi_get_reboot_to_firmware();
2638                 if (r < 0 && r != -EOPNOTSUPP)
2639                         log_warning_errno(r, "Failed to determine reboot-to-firmware-setup state: %m");
2640         } else if (r < 0)
2641                 log_warning_errno(r, "Failed to parse $SYSTEMD_REBOOT_TO_FIRMWARE_SETUP: %m");
2642         else if (r > 0) {
2643                 /* Non-EFI case: let's see whether /run/systemd/reboot-to-firmware-setup exists. */
2644                 if (access("/run/systemd/reboot-to-firmware-setup", F_OK) < 0) {
2645                         if (errno != ENOENT)
2646                                 log_warning_errno(errno, "Failed to check whether /run/systemd/reboot-to-firmware-setup exists: %m");
2647 
2648                         r = false;
2649                 } else
2650                         r = true;
2651         }
2652 
2653         return sd_bus_message_append(reply, "b", r > 0);
2654 }
2655 
method_set_reboot_to_firmware_setup(sd_bus_message * message,void * userdata,sd_bus_error * error)2656 static int method_set_reboot_to_firmware_setup(
2657                 sd_bus_message *message,
2658                 void *userdata,
2659                 sd_bus_error *error) {
2660 
2661         Manager *m = userdata;
2662         bool use_efi;
2663         int b, r;
2664 
2665         assert(message);
2666         assert(m);
2667 
2668         r = sd_bus_message_read(message, "b", &b);
2669         if (r < 0)
2670                 return r;
2671 
2672         r = getenv_bool("SYSTEMD_REBOOT_TO_FIRMWARE_SETUP");
2673         if (r == -ENXIO) {
2674                 /* EFI case: let's see what the firmware supports */
2675 
2676                 r = efi_reboot_to_firmware_supported();
2677                 if (r == -EOPNOTSUPP)
2678                         return sd_bus_error_set(error, SD_BUS_ERROR_NOT_SUPPORTED, "Firmware does not support boot into firmware.");
2679                 if (r < 0)
2680                         return r;
2681 
2682                 use_efi = true;
2683 
2684         } else if (r <= 0) {
2685                 /* non-EFI case: $SYSTEMD_REBOOT_TO_FIRMWARE_SETUP is set to off */
2686 
2687                 if (r < 0)
2688                         log_warning_errno(r, "Failed to parse $SYSTEMD_REBOOT_TO_FIRMWARE_SETUP: %m");
2689 
2690                 return sd_bus_error_set(error, SD_BUS_ERROR_NOT_SUPPORTED, "Firmware does not support boot into firmware.");
2691         } else
2692                 /* non-EFI case: $SYSTEMD_REBOOT_TO_FIRMWARE_SETUP is set to on */
2693                 use_efi = false;
2694 
2695         r = bus_verify_polkit_async(message,
2696                                     CAP_SYS_ADMIN,
2697                                     "org.freedesktop.login1.set-reboot-to-firmware-setup",
2698                                     NULL,
2699                                     false,
2700                                     UID_INVALID,
2701                                     &m->polkit_registry,
2702                                     error);
2703         if (r < 0)
2704                 return r;
2705         if (r == 0)
2706                 return 1; /* No authorization for now, but the async polkit stuff will call us again when it has it */
2707 
2708         if (use_efi) {
2709                 r = efi_set_reboot_to_firmware(b);
2710                 if (r < 0)
2711                         return r;
2712         } else {
2713                 if (b) {
2714                         r = touch("/run/systemd/reboot-to-firmware-setup");
2715                         if (r < 0)
2716                                 return r;
2717                 } else {
2718                         if (unlink("/run/systemd/reboot-to-firmware-setup") < 0 && errno != ENOENT)
2719                                 return -errno;
2720                 }
2721         }
2722 
2723         return sd_bus_reply_method_return(message, NULL);
2724 }
2725 
method_can_reboot_to_firmware_setup(sd_bus_message * message,void * userdata,sd_bus_error * error)2726 static int method_can_reboot_to_firmware_setup(
2727                 sd_bus_message *message,
2728                 void *userdata,
2729                 sd_bus_error *error) {
2730 
2731         _unused_ Manager *m = userdata;
2732         int r;
2733 
2734         assert(message);
2735         assert(m);
2736 
2737         r = getenv_bool("SYSTEMD_REBOOT_TO_FIRMWARE_SETUP");
2738         if (r == -ENXIO) {
2739                 /* EFI case: let's see what the firmware supports */
2740 
2741                 r = efi_reboot_to_firmware_supported();
2742                 if (r < 0) {
2743                         if (r != -EOPNOTSUPP)
2744                                 log_warning_errno(r, "Failed to determine whether reboot to firmware is supported: %m");
2745 
2746                         return sd_bus_reply_method_return(message, "s", "na");
2747                 }
2748 
2749         } else if (r <= 0) {
2750                 /* Non-EFI case: let's trust $SYSTEMD_REBOOT_TO_FIRMWARE_SETUP */
2751 
2752                 if (r < 0)
2753                         log_warning_errno(r, "Failed to parse $SYSTEMD_REBOOT_TO_FIRMWARE_SETUP: %m");
2754 
2755                 return sd_bus_reply_method_return(message, "s", "na");
2756         }
2757 
2758         return return_test_polkit(
2759                         message,
2760                         CAP_SYS_ADMIN,
2761                         "org.freedesktop.login1.set-reboot-to-firmware-setup",
2762                         NULL,
2763                         UID_INVALID,
2764                         error);
2765 }
2766 
property_get_reboot_to_boot_loader_menu(sd_bus * bus,const char * path,const char * interface,const char * property,sd_bus_message * reply,void * userdata,sd_bus_error * error)2767 static int property_get_reboot_to_boot_loader_menu(
2768                 sd_bus *bus,
2769                 const char *path,
2770                 const char *interface,
2771                 const char *property,
2772                 sd_bus_message *reply,
2773                 void *userdata,
2774                 sd_bus_error *error) {
2775 
2776         uint64_t x = UINT64_MAX;
2777         int r;
2778 
2779         assert(bus);
2780         assert(reply);
2781         assert(userdata);
2782 
2783         r = getenv_bool("SYSTEMD_REBOOT_TO_BOOT_LOADER_MENU");
2784         if (r == -ENXIO) {
2785                 /* EFI case: returns the current value of LoaderConfigTimeoutOneShot. Three cases are distinguished:
2786                  *
2787                  *     1. Variable not set, boot into boot loader menu is not enabled (we return UINT64_MAX to the user)
2788                  *     2. Variable set to "0", boot into boot loader menu is enabled with no timeout (we return 0 to the user)
2789                  *     3. Variable set to numeric value formatted in ASCII, boot into boot loader menu with the specified timeout in seconds
2790                  */
2791 
2792                 r = efi_loader_get_config_timeout_one_shot(&x);
2793                 if (r < 0) {
2794                         if (r != -ENOENT)
2795                                 log_warning_errno(r, "Failed to read LoaderConfigTimeoutOneShot variable, ignoring: %m");
2796                 }
2797 
2798         } else if (r < 0)
2799                 log_warning_errno(r, "Failed to parse $SYSTEMD_REBOOT_TO_BOOT_LOADER_MENU: %m");
2800         else if (r > 0) {
2801                 _cleanup_free_ char *v = NULL;
2802 
2803                 /* Non-EFI case, let's process /run/systemd/reboot-to-boot-loader-menu. */
2804 
2805                 r = read_one_line_file("/run/systemd/reboot-to-boot-loader-menu", &v);
2806                 if (r < 0) {
2807                         if (r != -ENOENT)
2808                                 log_warning_errno(r, "Failed to read /run/systemd/reboot-to-boot-loader-menu: %m");
2809                 } else {
2810                         r = safe_atou64(v, &x);
2811                         if (r < 0)
2812                                 log_warning_errno(r, "Failed to parse /run/systemd/reboot-to-boot-loader-menu: %m");
2813                 }
2814         }
2815 
2816         return sd_bus_message_append(reply, "t", x);
2817 }
2818 
method_set_reboot_to_boot_loader_menu(sd_bus_message * message,void * userdata,sd_bus_error * error)2819 static int method_set_reboot_to_boot_loader_menu(
2820                 sd_bus_message *message,
2821                 void *userdata,
2822                 sd_bus_error *error) {
2823 
2824         Manager *m = userdata;
2825         bool use_efi;
2826         uint64_t x;
2827         int r;
2828 
2829         assert(message);
2830         assert(m);
2831 
2832         r = sd_bus_message_read(message, "t", &x);
2833         if (r < 0)
2834                 return r;
2835 
2836         r = getenv_bool("SYSTEMD_REBOOT_TO_BOOT_LOADER_MENU");
2837         if (r == -ENXIO) {
2838                 uint64_t features;
2839 
2840                 /* EFI case: let's see if booting into boot loader menu is supported. */
2841 
2842                 r = efi_loader_get_features(&features);
2843                 if (r < 0)
2844                         log_warning_errno(r, "Failed to determine whether reboot to boot loader menu is supported: %m");
2845                 if (r < 0 || !FLAGS_SET(features, EFI_LOADER_FEATURE_CONFIG_TIMEOUT_ONE_SHOT))
2846                         return sd_bus_error_set(error, SD_BUS_ERROR_NOT_SUPPORTED, "Boot loader does not support boot into boot loader menu.");
2847 
2848                 use_efi = true;
2849 
2850         } else if (r <= 0) {
2851                 /* non-EFI case: $SYSTEMD_REBOOT_TO_BOOT_LOADER_MENU is set to off */
2852 
2853                 if (r < 0)
2854                         log_warning_errno(r, "Failed to parse $SYSTEMD_REBOOT_TO_BOOT_LOADER_MENU: %m");
2855 
2856                 return sd_bus_error_set(error, SD_BUS_ERROR_NOT_SUPPORTED, "Boot loader does not support boot into boot loader menu.");
2857         } else
2858                 /* non-EFI case: $SYSTEMD_REBOOT_TO_BOOT_LOADER_MENU is set to on */
2859                 use_efi = false;
2860 
2861         r = bus_verify_polkit_async(message,
2862                                     CAP_SYS_ADMIN,
2863                                     "org.freedesktop.login1.set-reboot-to-boot-loader-menu",
2864                                     NULL,
2865                                     false,
2866                                     UID_INVALID,
2867                                     &m->polkit_registry,
2868                                     error);
2869         if (r < 0)
2870                 return r;
2871         if (r == 0)
2872                 return 1; /* No authorization for now, but the async polkit stuff will call us again when it has it */
2873 
2874         if (use_efi) {
2875                 if (x == UINT64_MAX)
2876                         r = efi_set_variable(EFI_LOADER_VARIABLE(LoaderConfigTimeoutOneShot), NULL, 0);
2877                 else {
2878                         char buf[DECIMAL_STR_MAX(uint64_t) + 1];
2879                         xsprintf(buf, "%" PRIu64, DIV_ROUND_UP(x, USEC_PER_SEC)); /* second granularity */
2880 
2881                         r = efi_set_variable_string(EFI_LOADER_VARIABLE(LoaderConfigTimeoutOneShot), buf);
2882                 }
2883                 if (r < 0)
2884                         return r;
2885         } else {
2886                 if (x == UINT64_MAX) {
2887                         if (unlink("/run/systemd/reboot-to-boot-loader-menu") < 0 && errno != ENOENT)
2888                                 return -errno;
2889                 } else {
2890                         char buf[DECIMAL_STR_MAX(uint64_t) + 1];
2891 
2892                         xsprintf(buf, "%" PRIu64, x); /* µs granularity */
2893 
2894                         r = write_string_file_atomic_label("/run/systemd/reboot-to-boot-loader-menu", buf);
2895                         if (r < 0)
2896                                 return r;
2897                 }
2898         }
2899 
2900         return sd_bus_reply_method_return(message, NULL);
2901 }
2902 
method_can_reboot_to_boot_loader_menu(sd_bus_message * message,void * userdata,sd_bus_error * error)2903 static int method_can_reboot_to_boot_loader_menu(
2904                 sd_bus_message *message,
2905                 void *userdata,
2906                 sd_bus_error *error) {
2907 
2908         _unused_ Manager *m = userdata;
2909         int r;
2910 
2911         assert(message);
2912         assert(m);
2913 
2914         r = getenv_bool("SYSTEMD_REBOOT_TO_BOOT_LOADER_MENU");
2915         if (r == -ENXIO) {
2916                 uint64_t features = 0;
2917 
2918                 /* EFI case, let's see if booting into boot loader menu is supported. */
2919 
2920                 r = efi_loader_get_features(&features);
2921                 if (r < 0)
2922                         log_warning_errno(r, "Failed to determine whether reboot to boot loader menu is supported: %m");
2923                 if (r < 0 || !FLAGS_SET(features, EFI_LOADER_FEATURE_CONFIG_TIMEOUT_ONE_SHOT))
2924                         return sd_bus_reply_method_return(message, "s", "na");
2925 
2926         } else if (r <= 0) {
2927                 /* Non-EFI case: let's trust $SYSTEMD_REBOOT_TO_BOOT_LOADER_MENU */
2928 
2929                 if (r < 0)
2930                         log_warning_errno(r, "Failed to parse $SYSTEMD_REBOOT_TO_BOOT_LOADER_MENU: %m");
2931 
2932                 return sd_bus_reply_method_return(message, "s", "na");
2933         }
2934 
2935         return return_test_polkit(
2936                         message,
2937                         CAP_SYS_ADMIN,
2938                         "org.freedesktop.login1.set-reboot-to-boot-loader-menu",
2939                         NULL,
2940                         UID_INVALID,
2941                         error);
2942 }
2943 
property_get_reboot_to_boot_loader_entry(sd_bus * bus,const char * path,const char * interface,const char * property,sd_bus_message * reply,void * userdata,sd_bus_error * error)2944 static int property_get_reboot_to_boot_loader_entry(
2945                 sd_bus *bus,
2946                 const char *path,
2947                 const char *interface,
2948                 const char *property,
2949                 sd_bus_message *reply,
2950                 void *userdata,
2951                 sd_bus_error *error) {
2952 
2953         _cleanup_free_ char *v = NULL;
2954         Manager *m = userdata;
2955         const char *x = NULL;
2956         int r;
2957 
2958         assert(bus);
2959         assert(reply);
2960         assert(m);
2961 
2962         r = getenv_bool("SYSTEMD_REBOOT_TO_BOOT_LOADER_ENTRY");
2963         if (r == -ENXIO) {
2964                 /* EFI case: let's read the LoaderEntryOneShot variable */
2965 
2966                 r = efi_loader_update_entry_one_shot_cache(&m->efi_loader_entry_one_shot, &m->efi_loader_entry_one_shot_stat);
2967                 if (r < 0) {
2968                         if (r != -ENOENT)
2969                                 log_warning_errno(r, "Failed to read LoaderEntryOneShot variable, ignoring: %m");
2970                 } else
2971                         x = m->efi_loader_entry_one_shot;
2972 
2973         } else if (r < 0)
2974                 log_warning_errno(r, "Failed to parse $SYSTEMD_REBOOT_TO_BOOT_LOADER_ENTRY: %m");
2975         else if (r > 0) {
2976 
2977                 /* Non-EFI case, let's process /run/systemd/reboot-to-boot-loader-entry. */
2978 
2979                 r = read_one_line_file("/run/systemd/reboot-to-boot-loader-entry", &v);
2980                 if (r < 0) {
2981                         if (r != -ENOENT)
2982                                 log_warning_errno(r, "Failed to read /run/systemd/reboot-to-boot-loader-entry, ignoring: %m");
2983                 } else if (!efi_loader_entry_name_valid(v))
2984                         log_warning("/run/systemd/reboot-to-boot-loader-entry is not valid, ignoring.");
2985                 else
2986                         x = v;
2987         }
2988 
2989         return sd_bus_message_append(reply, "s", x);
2990 }
2991 
boot_loader_entry_exists(Manager * m,const char * id)2992 static int boot_loader_entry_exists(Manager *m, const char *id) {
2993         _cleanup_(boot_config_free) BootConfig config = BOOT_CONFIG_NULL;
2994         int r;
2995 
2996         assert(m);
2997         assert(id);
2998 
2999         r = boot_config_load_auto(&config, NULL, NULL);
3000         if (r < 0 && r != -ENOKEY) /* don't complain if no GPT is found, hence skip ENOKEY */
3001                 return r;
3002 
3003         r = manager_read_efi_boot_loader_entries(m);
3004         if (r >= 0)
3005                 (void) boot_config_augment_from_loader(&config, m->efi_boot_loader_entries, /* auto_only= */ true);
3006 
3007         return !!boot_config_find_entry(&config, id);
3008 }
3009 
method_set_reboot_to_boot_loader_entry(sd_bus_message * message,void * userdata,sd_bus_error * error)3010 static int method_set_reboot_to_boot_loader_entry(
3011                 sd_bus_message *message,
3012                 void *userdata,
3013                 sd_bus_error *error) {
3014 
3015         Manager *m = userdata;
3016         bool use_efi;
3017         const char *v;
3018         int r;
3019 
3020         assert(message);
3021         assert(m);
3022 
3023         r = sd_bus_message_read(message, "s", &v);
3024         if (r < 0)
3025                 return r;
3026 
3027         if (isempty(v))
3028                 v = NULL;
3029         else if (efi_loader_entry_name_valid(v)) {
3030                 r = boot_loader_entry_exists(m, v);
3031                 if (r < 0)
3032                         return r;
3033                 if (r == 0)
3034                         return sd_bus_error_setf(error, SD_BUS_ERROR_NOT_SUPPORTED, "Boot loader entry '%s' is not known.", v);
3035         } else
3036                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Boot loader entry name '%s' is not valid, refusing.", v);
3037 
3038         r = getenv_bool("SYSTEMD_REBOOT_TO_BOOT_LOADER_ENTRY");
3039         if (r == -ENXIO) {
3040                 uint64_t features;
3041 
3042                 /* EFI case: let's see if booting into boot loader entry is supported. */
3043 
3044                 r = efi_loader_get_features(&features);
3045                 if (r < 0)
3046                         log_warning_errno(r, "Failed to determine whether reboot into boot loader entry is supported: %m");
3047                 if (r < 0 || !FLAGS_SET(features, EFI_LOADER_FEATURE_ENTRY_ONESHOT))
3048                         return sd_bus_error_set(error, SD_BUS_ERROR_NOT_SUPPORTED, "Loader does not support boot into boot loader entry.");
3049 
3050                 use_efi = true;
3051 
3052         } else if (r <= 0) {
3053                 /* non-EFI case: $SYSTEMD_REBOOT_TO_BOOT_LOADER_ENTRY is set to off */
3054 
3055                 if (r < 0)
3056                         log_warning_errno(r, "Failed to parse $SYSTEMD_REBOOT_TO_BOOT_LOADER_ENTRY: %m");
3057 
3058                 return sd_bus_error_set(error, SD_BUS_ERROR_NOT_SUPPORTED, "Loader does not support boot into boot loader entry.");
3059         } else
3060                 /* non-EFI case: $SYSTEMD_REBOOT_TO_BOOT_LOADER_ENTRY is set to on */
3061                 use_efi = false;
3062 
3063         r = bus_verify_polkit_async(message,
3064                                     CAP_SYS_ADMIN,
3065                                     "org.freedesktop.login1.set-reboot-to-boot-loader-entry",
3066                                     NULL,
3067                                     false,
3068                                     UID_INVALID,
3069                                     &m->polkit_registry,
3070                                     error);
3071         if (r < 0)
3072                 return r;
3073         if (r == 0)
3074                 return 1; /* No authorization for now, but the async polkit stuff will call us again when it has it */
3075 
3076         if (use_efi) {
3077                 if (isempty(v))
3078                         /* Delete item */
3079                         r = efi_set_variable(EFI_LOADER_VARIABLE(LoaderEntryOneShot), NULL, 0);
3080                 else
3081                         r = efi_set_variable_string(EFI_LOADER_VARIABLE(LoaderEntryOneShot), v);
3082                 if (r < 0)
3083                         return r;
3084         } else {
3085                 if (isempty(v)) {
3086                         if (unlink("/run/systemd/reboot-to-boot-loader-entry") < 0 && errno != ENOENT)
3087                                 return -errno;
3088                 } else {
3089                         r = write_string_file_atomic_label("/run/systemd/reboot-boot-to-loader-entry", v);
3090                         if (r < 0)
3091                                 return r;
3092                 }
3093         }
3094 
3095         return sd_bus_reply_method_return(message, NULL);
3096 }
3097 
method_can_reboot_to_boot_loader_entry(sd_bus_message * message,void * userdata,sd_bus_error * error)3098 static int method_can_reboot_to_boot_loader_entry(
3099                 sd_bus_message *message,
3100                 void *userdata,
3101                 sd_bus_error *error) {
3102 
3103         _unused_ Manager *m = userdata;
3104         int r;
3105 
3106         assert(message);
3107         assert(m);
3108 
3109         r = getenv_bool("SYSTEMD_REBOOT_TO_BOOT_LOADER_ENTRY");
3110         if (r == -ENXIO) {
3111                 uint64_t features = 0;
3112 
3113                 /* EFI case, let's see if booting into boot loader entry is supported. */
3114 
3115                 r = efi_loader_get_features(&features);
3116                 if (r < 0)
3117                         log_warning_errno(r, "Failed to determine whether reboot to boot loader entry is supported: %m");
3118                 if (r < 0 || !FLAGS_SET(features, EFI_LOADER_FEATURE_ENTRY_ONESHOT))
3119                         return sd_bus_reply_method_return(message, "s", "na");
3120 
3121         } else if (r <= 0) {
3122                 /* Non-EFI case: let's trust $SYSTEMD_REBOOT_TO_BOOT_LOADER_ENTRY */
3123 
3124                 if (r < 0)
3125                         log_warning_errno(r, "Failed to parse $SYSTEMD_REBOOT_TO_BOOT_LOADER_ENTRY: %m");
3126 
3127                 return sd_bus_reply_method_return(message, "s", "na");
3128         }
3129 
3130         return return_test_polkit(
3131                         message,
3132                         CAP_SYS_ADMIN,
3133                         "org.freedesktop.login1.set-reboot-to-boot-loader-entry",
3134                         NULL,
3135                         UID_INVALID,
3136                         error);
3137 }
3138 
property_get_boot_loader_entries(sd_bus * bus,const char * path,const char * interface,const char * property,sd_bus_message * reply,void * userdata,sd_bus_error * error)3139 static int property_get_boot_loader_entries(
3140                 sd_bus *bus,
3141                 const char *path,
3142                 const char *interface,
3143                 const char *property,
3144                 sd_bus_message *reply,
3145                 void *userdata,
3146                 sd_bus_error *error) {
3147 
3148         _cleanup_(boot_config_free) BootConfig config = BOOT_CONFIG_NULL;
3149         Manager *m = userdata;
3150         size_t i;
3151         int r;
3152 
3153         assert(bus);
3154         assert(reply);
3155         assert(m);
3156 
3157         r = boot_config_load_auto(&config, NULL, NULL);
3158         if (r < 0 && r != -ENOKEY) /* don't complain if there's no GPT found */
3159                 return r;
3160 
3161         r = manager_read_efi_boot_loader_entries(m);
3162         if (r >= 0)
3163                 (void) boot_config_augment_from_loader(&config, m->efi_boot_loader_entries, /* auto_only= */ true);
3164 
3165         r = sd_bus_message_open_container(reply, 'a', "s");
3166         if (r < 0)
3167                 return r;
3168 
3169         for (i = 0; i < config.n_entries; i++) {
3170                 BootEntry *e = config.entries + i;
3171 
3172                 r = sd_bus_message_append(reply, "s", e->id);
3173                 if (r < 0)
3174                         return r;
3175         }
3176 
3177         return sd_bus_message_close_container(reply);
3178 }
3179 
method_set_wall_message(sd_bus_message * message,void * userdata,sd_bus_error * error)3180 static int method_set_wall_message(
3181                 sd_bus_message *message,
3182                 void *userdata,
3183                 sd_bus_error *error) {
3184 
3185         int r;
3186         Manager *m = userdata;
3187         char *wall_message;
3188         int enable_wall_messages;
3189 
3190         assert(message);
3191         assert(m);
3192 
3193         r = sd_bus_message_read(message, "sb", &wall_message, &enable_wall_messages);
3194         if (r < 0)
3195                 return r;
3196 
3197         if (strlen(wall_message) > WALL_MESSAGE_MAX)
3198                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS,
3199                         "Wall message too long, maximum permitted length is %u characters.",
3200                         WALL_MESSAGE_MAX);
3201 
3202         /* Short-circuit the operation if the desired state is already in place, to
3203          * avoid an unnecessary polkit permission check. */
3204         if (streq_ptr(m->wall_message, empty_to_null(wall_message)) &&
3205             m->enable_wall_messages == enable_wall_messages)
3206                 goto done;
3207 
3208         r = bus_verify_polkit_async(message,
3209                                     CAP_SYS_ADMIN,
3210                                     "org.freedesktop.login1.set-wall-message",
3211                                     NULL,
3212                                     false,
3213                                     UID_INVALID,
3214                                     &m->polkit_registry,
3215                                     error);
3216         if (r < 0)
3217                 return r;
3218         if (r == 0)
3219                 return 1; /* Will call us back */
3220 
3221         r = free_and_strdup(&m->wall_message, empty_to_null(wall_message));
3222         if (r < 0)
3223                 return log_oom();
3224 
3225         m->enable_wall_messages = enable_wall_messages;
3226 
3227  done:
3228         return sd_bus_reply_method_return(message, NULL);
3229 }
3230 
method_inhibit(sd_bus_message * message,void * userdata,sd_bus_error * error)3231 static int method_inhibit(sd_bus_message *message, void *userdata, sd_bus_error *error) {
3232         _cleanup_(sd_bus_creds_unrefp) sd_bus_creds *creds = NULL;
3233         const char *who, *why, *what, *mode;
3234         _cleanup_free_ char *id = NULL;
3235         _cleanup_close_ int fifo_fd = -1;
3236         Manager *m = userdata;
3237         InhibitMode mm;
3238         InhibitWhat w;
3239         pid_t pid;
3240         uid_t uid;
3241         int r;
3242 
3243         assert(message);
3244         assert(m);
3245 
3246         r = sd_bus_message_read(message, "ssss", &what, &who, &why, &mode);
3247         if (r < 0)
3248                 return r;
3249 
3250         w = inhibit_what_from_string(what);
3251         if (w <= 0)
3252                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS,
3253                                          "Invalid what specification %s", what);
3254 
3255         mm = inhibit_mode_from_string(mode);
3256         if (mm < 0)
3257                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS,
3258                                          "Invalid mode specification %s", mode);
3259 
3260         /* Delay is only supported for shutdown/sleep */
3261         if (mm == INHIBIT_DELAY && (w & ~(INHIBIT_SHUTDOWN|INHIBIT_SLEEP)))
3262                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS,
3263                                          "Delay inhibitors only supported for shutdown and sleep");
3264 
3265         /* Don't allow taking delay locks while we are already
3266          * executing the operation. We shouldn't create the impression
3267          * that the lock was successful if the machine is about to go
3268          * down/suspend any moment. */
3269         if (m->delayed_action && m->delayed_action->inhibit_what & w)
3270                 return sd_bus_error_setf(error, BUS_ERROR_OPERATION_IN_PROGRESS,
3271                                          "The operation inhibition has been requested for is already running");
3272 
3273         r = bus_verify_polkit_async(
3274                         message,
3275                         CAP_SYS_BOOT,
3276                         w == INHIBIT_SHUTDOWN             ? (mm == INHIBIT_BLOCK ? "org.freedesktop.login1.inhibit-block-shutdown" : "org.freedesktop.login1.inhibit-delay-shutdown") :
3277                         w == INHIBIT_SLEEP                ? (mm == INHIBIT_BLOCK ? "org.freedesktop.login1.inhibit-block-sleep"    : "org.freedesktop.login1.inhibit-delay-sleep") :
3278                         w == INHIBIT_IDLE                 ? "org.freedesktop.login1.inhibit-block-idle" :
3279                         w == INHIBIT_HANDLE_POWER_KEY     ? "org.freedesktop.login1.inhibit-handle-power-key" :
3280                         w == INHIBIT_HANDLE_SUSPEND_KEY   ? "org.freedesktop.login1.inhibit-handle-suspend-key" :
3281                         w == INHIBIT_HANDLE_REBOOT_KEY    ? "org.freedesktop.login1.inhibit-handle-reboot-key" :
3282                         w == INHIBIT_HANDLE_HIBERNATE_KEY ? "org.freedesktop.login1.inhibit-handle-hibernate-key" :
3283                                                             "org.freedesktop.login1.inhibit-handle-lid-switch",
3284                         NULL,
3285                         false,
3286                         UID_INVALID,
3287                         &m->polkit_registry,
3288                         error);
3289         if (r < 0)
3290                 return r;
3291         if (r == 0)
3292                 return 1; /* No authorization for now, but the async polkit stuff will call us again when it has it */
3293 
3294         r = sd_bus_query_sender_creds(message, SD_BUS_CREDS_EUID|SD_BUS_CREDS_PID, &creds);
3295         if (r < 0)
3296                 return r;
3297 
3298         r = sd_bus_creds_get_euid(creds, &uid);
3299         if (r < 0)
3300                 return r;
3301 
3302         r = sd_bus_creds_get_pid(creds, &pid);
3303         if (r < 0)
3304                 return r;
3305 
3306         if (hashmap_size(m->inhibitors) >= m->inhibitors_max)
3307                 return sd_bus_error_setf(error, SD_BUS_ERROR_LIMITS_EXCEEDED,
3308                                          "Maximum number of inhibitors (%" PRIu64 ") reached, refusing further inhibitors.",
3309                                          m->inhibitors_max);
3310 
3311         do {
3312                 id = mfree(id);
3313 
3314                 if (asprintf(&id, "%lu", ++m->inhibit_counter) < 0)
3315                         return -ENOMEM;
3316 
3317         } while (hashmap_get(m->inhibitors, id));
3318 
3319         _cleanup_(inhibitor_freep) Inhibitor *i = NULL;
3320         r = manager_add_inhibitor(m, id, &i);
3321         if (r < 0)
3322                 return r;
3323 
3324         i->what = w;
3325         i->mode = mm;
3326         i->pid = pid;
3327         i->uid = uid;
3328         i->why = strdup(why);
3329         i->who = strdup(who);
3330 
3331         if (!i->why || !i->who)
3332                 return -ENOMEM;
3333 
3334         fifo_fd = inhibitor_create_fifo(i);
3335         if (fifo_fd < 0)
3336                 return fifo_fd;
3337 
3338         r = inhibitor_start(i);
3339         if (r < 0)
3340                 return r;
3341         TAKE_PTR(i);
3342 
3343         return sd_bus_reply_method_return(message, "h", fifo_fd);
3344 }
3345 
3346 static const sd_bus_vtable manager_vtable[] = {
3347         SD_BUS_VTABLE_START(0),
3348 
3349         SD_BUS_WRITABLE_PROPERTY("EnableWallMessages", "b", bus_property_get_bool, bus_property_set_bool, offsetof(Manager, enable_wall_messages), 0),
3350         SD_BUS_WRITABLE_PROPERTY("WallMessage", "s", NULL, NULL, offsetof(Manager, wall_message), 0),
3351 
3352         SD_BUS_PROPERTY("NAutoVTs", "u", NULL, offsetof(Manager, n_autovts), SD_BUS_VTABLE_PROPERTY_CONST),
3353         SD_BUS_PROPERTY("KillOnlyUsers", "as", NULL, offsetof(Manager, kill_only_users), SD_BUS_VTABLE_PROPERTY_CONST),
3354         SD_BUS_PROPERTY("KillExcludeUsers", "as", NULL, offsetof(Manager, kill_exclude_users), SD_BUS_VTABLE_PROPERTY_CONST),
3355         SD_BUS_PROPERTY("KillUserProcesses", "b", bus_property_get_bool, offsetof(Manager, kill_user_processes), SD_BUS_VTABLE_PROPERTY_CONST),
3356         SD_BUS_PROPERTY("RebootParameter", "s", property_get_reboot_parameter, 0, 0),
3357         SD_BUS_PROPERTY("RebootToFirmwareSetup", "b", property_get_reboot_to_firmware_setup, 0, 0),
3358         SD_BUS_PROPERTY("RebootToBootLoaderMenu", "t", property_get_reboot_to_boot_loader_menu, 0, 0),
3359         SD_BUS_PROPERTY("RebootToBootLoaderEntry", "s", property_get_reboot_to_boot_loader_entry, 0, 0),
3360         SD_BUS_PROPERTY("BootLoaderEntries", "as", property_get_boot_loader_entries, 0, SD_BUS_VTABLE_PROPERTY_CONST),
3361         SD_BUS_PROPERTY("IdleHint", "b", property_get_idle_hint, 0, SD_BUS_VTABLE_PROPERTY_EMITS_CHANGE),
3362         SD_BUS_PROPERTY("IdleSinceHint", "t", property_get_idle_since_hint, 0, SD_BUS_VTABLE_PROPERTY_EMITS_CHANGE),
3363         SD_BUS_PROPERTY("IdleSinceHintMonotonic", "t", property_get_idle_since_hint, 0, SD_BUS_VTABLE_PROPERTY_EMITS_CHANGE),
3364         SD_BUS_PROPERTY("BlockInhibited", "s", property_get_inhibited, 0, SD_BUS_VTABLE_PROPERTY_EMITS_CHANGE),
3365         SD_BUS_PROPERTY("DelayInhibited", "s", property_get_inhibited, 0, SD_BUS_VTABLE_PROPERTY_EMITS_CHANGE),
3366         SD_BUS_PROPERTY("InhibitDelayMaxUSec", "t", NULL, offsetof(Manager, inhibit_delay_max), SD_BUS_VTABLE_PROPERTY_CONST),
3367         SD_BUS_PROPERTY("UserStopDelayUSec", "t", NULL, offsetof(Manager, user_stop_delay), SD_BUS_VTABLE_PROPERTY_CONST),
3368         SD_BUS_PROPERTY("HandlePowerKey", "s", property_get_handle_action, offsetof(Manager, handle_power_key), SD_BUS_VTABLE_PROPERTY_CONST),
3369         SD_BUS_PROPERTY("HandlePowerKeyLongPress", "s", property_get_handle_action, offsetof(Manager, handle_power_key_long_press), SD_BUS_VTABLE_PROPERTY_CONST),
3370         SD_BUS_PROPERTY("HandleRebootKey", "s", property_get_handle_action, offsetof(Manager, handle_reboot_key), SD_BUS_VTABLE_PROPERTY_CONST),
3371         SD_BUS_PROPERTY("HandleRebootKeyLongPress", "s", property_get_handle_action, offsetof(Manager, handle_reboot_key_long_press), SD_BUS_VTABLE_PROPERTY_CONST),
3372         SD_BUS_PROPERTY("HandleSuspendKey", "s", property_get_handle_action, offsetof(Manager, handle_suspend_key), SD_BUS_VTABLE_PROPERTY_CONST),
3373         SD_BUS_PROPERTY("HandleSuspendKeyLongPress", "s", property_get_handle_action, offsetof(Manager, handle_suspend_key_long_press), SD_BUS_VTABLE_PROPERTY_CONST),
3374         SD_BUS_PROPERTY("HandleHibernateKey", "s", property_get_handle_action, offsetof(Manager, handle_hibernate_key), SD_BUS_VTABLE_PROPERTY_CONST),
3375         SD_BUS_PROPERTY("HandleHibernateKeyLongPress", "s", property_get_handle_action, offsetof(Manager, handle_hibernate_key_long_press), SD_BUS_VTABLE_PROPERTY_CONST),
3376         SD_BUS_PROPERTY("HandleLidSwitch", "s", property_get_handle_action, offsetof(Manager, handle_lid_switch), SD_BUS_VTABLE_PROPERTY_CONST),
3377         SD_BUS_PROPERTY("HandleLidSwitchExternalPower", "s", property_get_handle_action, offsetof(Manager, handle_lid_switch_ep), SD_BUS_VTABLE_PROPERTY_CONST),
3378         SD_BUS_PROPERTY("HandleLidSwitchDocked", "s", property_get_handle_action, offsetof(Manager, handle_lid_switch_docked), SD_BUS_VTABLE_PROPERTY_CONST),
3379         SD_BUS_PROPERTY("HoldoffTimeoutUSec", "t", NULL, offsetof(Manager, holdoff_timeout_usec), SD_BUS_VTABLE_PROPERTY_CONST),
3380         SD_BUS_PROPERTY("IdleAction", "s", property_get_handle_action, offsetof(Manager, idle_action), SD_BUS_VTABLE_PROPERTY_CONST),
3381         SD_BUS_PROPERTY("IdleActionUSec", "t", NULL, offsetof(Manager, idle_action_usec), SD_BUS_VTABLE_PROPERTY_CONST),
3382         SD_BUS_PROPERTY("PreparingForShutdown", "b", property_get_preparing, 0, 0),
3383         SD_BUS_PROPERTY("PreparingForSleep", "b", property_get_preparing, 0, 0),
3384         SD_BUS_PROPERTY("ScheduledShutdown", "(st)", property_get_scheduled_shutdown, 0, 0),
3385         SD_BUS_PROPERTY("Docked", "b", property_get_docked, 0, 0),
3386         SD_BUS_PROPERTY("LidClosed", "b", property_get_lid_closed, 0, 0),
3387         SD_BUS_PROPERTY("OnExternalPower", "b", property_get_on_external_power, 0, 0),
3388         SD_BUS_PROPERTY("RemoveIPC", "b", bus_property_get_bool, offsetof(Manager, remove_ipc), SD_BUS_VTABLE_PROPERTY_CONST),
3389         SD_BUS_PROPERTY("RuntimeDirectorySize", "t", NULL, offsetof(Manager, runtime_dir_size), SD_BUS_VTABLE_PROPERTY_CONST),
3390         SD_BUS_PROPERTY("RuntimeDirectoryInodesMax", "t", NULL, offsetof(Manager, runtime_dir_inodes), SD_BUS_VTABLE_PROPERTY_CONST),
3391         SD_BUS_PROPERTY("InhibitorsMax", "t", NULL, offsetof(Manager, inhibitors_max), SD_BUS_VTABLE_PROPERTY_CONST),
3392         SD_BUS_PROPERTY("NCurrentInhibitors", "t", property_get_hashmap_size, offsetof(Manager, inhibitors), 0),
3393         SD_BUS_PROPERTY("SessionsMax", "t", NULL, offsetof(Manager, sessions_max), SD_BUS_VTABLE_PROPERTY_CONST),
3394         SD_BUS_PROPERTY("NCurrentSessions", "t", property_get_hashmap_size, offsetof(Manager, sessions), 0),
3395         SD_BUS_PROPERTY("UserTasksMax", "t", property_get_compat_user_tasks_max, 0, SD_BUS_VTABLE_PROPERTY_CONST|SD_BUS_VTABLE_HIDDEN),
3396 
3397         SD_BUS_METHOD_WITH_ARGS("GetSession",
3398                                 SD_BUS_ARGS("s", session_id),
3399                                 SD_BUS_RESULT("o", object_path),
3400                                 method_get_session,
3401                                 SD_BUS_VTABLE_UNPRIVILEGED),
3402         SD_BUS_METHOD_WITH_ARGS("GetSessionByPID",
3403                                 SD_BUS_ARGS("u", pid),
3404                                 SD_BUS_RESULT("o", object_path),
3405                                 method_get_session_by_pid,
3406                                 SD_BUS_VTABLE_UNPRIVILEGED),
3407         SD_BUS_METHOD_WITH_ARGS("GetUser",
3408                                 SD_BUS_ARGS("u", uid),
3409                                 SD_BUS_RESULT("o", object_path),
3410                                 method_get_user,
3411                                 SD_BUS_VTABLE_UNPRIVILEGED),
3412         SD_BUS_METHOD_WITH_ARGS("GetUserByPID",
3413                                 SD_BUS_ARGS("u", pid),
3414                                 SD_BUS_RESULT("o", object_path),
3415                                 method_get_user_by_pid,
3416                                 SD_BUS_VTABLE_UNPRIVILEGED),
3417         SD_BUS_METHOD_WITH_ARGS("GetSeat",
3418                                 SD_BUS_ARGS("s", seat_id),
3419                                 SD_BUS_RESULT("o", object_path),
3420                                 method_get_seat,
3421                                 SD_BUS_VTABLE_UNPRIVILEGED),
3422         SD_BUS_METHOD_WITH_ARGS("ListSessions",
3423                                 SD_BUS_NO_ARGS,
3424                                 SD_BUS_RESULT("a(susso)", sessions),
3425                                 method_list_sessions,
3426                                 SD_BUS_VTABLE_UNPRIVILEGED),
3427         SD_BUS_METHOD_WITH_ARGS("ListUsers",
3428                                 SD_BUS_NO_ARGS,
3429                                 SD_BUS_RESULT("a(uso)", users),
3430                                 method_list_users,
3431                                 SD_BUS_VTABLE_UNPRIVILEGED),
3432         SD_BUS_METHOD_WITH_ARGS("ListSeats",
3433                                 SD_BUS_NO_ARGS,
3434                                 SD_BUS_RESULT("a(so)", seats),
3435                                 method_list_seats,
3436                                 SD_BUS_VTABLE_UNPRIVILEGED),
3437         SD_BUS_METHOD_WITH_ARGS("ListInhibitors",
3438                                 SD_BUS_NO_ARGS,
3439                                 SD_BUS_RESULT("a(ssssuu)", inhibitors),
3440                                 method_list_inhibitors,
3441                                 SD_BUS_VTABLE_UNPRIVILEGED),
3442         SD_BUS_METHOD_WITH_ARGS("CreateSession",
3443                                 SD_BUS_ARGS("u", uid,
3444                                             "u", pid,
3445                                             "s", service,
3446                                             "s", type,
3447                                             "s", class,
3448                                             "s", desktop,
3449                                             "s", seat_id,
3450                                             "u", vtnr,
3451                                             "s", tty,
3452                                             "s", display,
3453                                             "b", remote,
3454                                             "s", remote_user,
3455                                             "s", remote_host,
3456                                             "a(sv)", properties),
3457                                 SD_BUS_RESULT("s", session_id,
3458                                               "o", object_path,
3459                                               "s", runtime_path,
3460                                               "h", fifo_fd,
3461                                               "u", uid,
3462                                               "s", seat_id,
3463                                               "u", vtnr,
3464                                               "b", existing),
3465                                 method_create_session,
3466                                 0),
3467         SD_BUS_METHOD_WITH_ARGS("ReleaseSession",
3468                                 SD_BUS_ARGS("s", session_id),
3469                                 SD_BUS_NO_RESULT,
3470                                 method_release_session,
3471                                 0),
3472         SD_BUS_METHOD_WITH_ARGS("ActivateSession",
3473                                 SD_BUS_ARGS("s", session_id),
3474                                 SD_BUS_NO_RESULT,
3475                                 method_activate_session,
3476                                 SD_BUS_VTABLE_UNPRIVILEGED),
3477         SD_BUS_METHOD_WITH_ARGS("ActivateSessionOnSeat",
3478                                 SD_BUS_ARGS("s", session_id, "s", seat_id),
3479                                 SD_BUS_NO_RESULT,
3480                                 method_activate_session_on_seat,
3481                                 SD_BUS_VTABLE_UNPRIVILEGED),
3482         SD_BUS_METHOD_WITH_ARGS("LockSession",
3483                                 SD_BUS_ARGS("s", session_id),
3484                                 SD_BUS_NO_RESULT,
3485                                 method_lock_session,
3486                                 SD_BUS_VTABLE_UNPRIVILEGED),
3487         SD_BUS_METHOD_WITH_ARGS("UnlockSession",
3488                                 SD_BUS_ARGS("s", session_id),
3489                                 SD_BUS_NO_RESULT,
3490                                 method_lock_session,
3491                                 SD_BUS_VTABLE_UNPRIVILEGED),
3492         SD_BUS_METHOD("LockSessions",
3493                       NULL,
3494                       NULL,
3495                       method_lock_sessions,
3496                       SD_BUS_VTABLE_UNPRIVILEGED),
3497         SD_BUS_METHOD("UnlockSessions",
3498                       NULL,
3499                       NULL,
3500                       method_lock_sessions,
3501                       SD_BUS_VTABLE_UNPRIVILEGED),
3502         SD_BUS_METHOD_WITH_ARGS("KillSession",
3503                                 SD_BUS_ARGS("s", session_id, "s", who, "i", signal_number),
3504                                 SD_BUS_NO_RESULT,
3505                                 method_kill_session,
3506                                 SD_BUS_VTABLE_UNPRIVILEGED),
3507         SD_BUS_METHOD_WITH_ARGS("KillUser",
3508                                 SD_BUS_ARGS("u", uid, "i", signal_number),
3509                                 SD_BUS_NO_RESULT,
3510                                 method_kill_user,
3511                                 SD_BUS_VTABLE_UNPRIVILEGED),
3512         SD_BUS_METHOD_WITH_ARGS("TerminateSession",
3513                                 SD_BUS_ARGS("s", session_id),
3514                                 SD_BUS_NO_RESULT,
3515                                 method_terminate_session,
3516                                 SD_BUS_VTABLE_UNPRIVILEGED),
3517         SD_BUS_METHOD_WITH_ARGS("TerminateUser",
3518                                 SD_BUS_ARGS("u", uid),
3519                                 SD_BUS_NO_RESULT,
3520                                 method_terminate_user,
3521                                 SD_BUS_VTABLE_UNPRIVILEGED),
3522         SD_BUS_METHOD_WITH_ARGS("TerminateSeat",
3523                                 SD_BUS_ARGS("s", seat_id),
3524                                 SD_BUS_NO_RESULT,
3525                                 method_terminate_seat,
3526                                 SD_BUS_VTABLE_UNPRIVILEGED),
3527         SD_BUS_METHOD_WITH_ARGS("SetUserLinger",
3528                                 SD_BUS_ARGS("u", uid, "b", enable, "b", interactive),
3529                                 SD_BUS_NO_RESULT,
3530                                 method_set_user_linger,
3531                                 SD_BUS_VTABLE_UNPRIVILEGED),
3532         SD_BUS_METHOD_WITH_ARGS("AttachDevice",
3533                                 SD_BUS_ARGS("s", seat_id, "s", sysfs_path, "b", interactive),
3534                                 SD_BUS_NO_RESULT,
3535                                 method_attach_device,
3536                                 SD_BUS_VTABLE_UNPRIVILEGED),
3537         SD_BUS_METHOD_WITH_ARGS("FlushDevices",
3538                                 SD_BUS_ARGS("b", interactive),
3539                                 SD_BUS_NO_RESULT,
3540                                 method_flush_devices,
3541                                 SD_BUS_VTABLE_UNPRIVILEGED),
3542         SD_BUS_METHOD_WITH_ARGS("PowerOff",
3543                                 SD_BUS_ARGS("b", interactive),
3544                                 SD_BUS_NO_RESULT,
3545                                 method_poweroff,
3546                                 SD_BUS_VTABLE_UNPRIVILEGED),
3547         SD_BUS_METHOD_WITH_ARGS("PowerOffWithFlags",
3548                                 SD_BUS_ARGS("t", flags),
3549                                 SD_BUS_NO_RESULT,
3550                                 method_poweroff,
3551                                 SD_BUS_VTABLE_UNPRIVILEGED),
3552         SD_BUS_METHOD_WITH_ARGS("Reboot",
3553                                 SD_BUS_ARGS("b", interactive),
3554                                 SD_BUS_NO_RESULT,
3555                                 method_reboot,
3556                                 SD_BUS_VTABLE_UNPRIVILEGED),
3557         SD_BUS_METHOD_WITH_ARGS("RebootWithFlags",
3558                                 SD_BUS_ARGS("t", flags),
3559                                 SD_BUS_NO_RESULT,
3560                                 method_reboot,
3561                                 SD_BUS_VTABLE_UNPRIVILEGED),
3562         SD_BUS_METHOD_WITH_ARGS("Halt",
3563                                 SD_BUS_ARGS("b", interactive),
3564                                 SD_BUS_NO_RESULT,
3565                                 method_halt,
3566                                 SD_BUS_VTABLE_UNPRIVILEGED),
3567         SD_BUS_METHOD_WITH_ARGS("HaltWithFlags",
3568                                 SD_BUS_ARGS("t", flags),
3569                                 SD_BUS_NO_RESULT,
3570                                 method_halt,
3571                                 SD_BUS_VTABLE_UNPRIVILEGED),
3572         SD_BUS_METHOD_WITH_ARGS("Suspend",
3573                                 SD_BUS_ARGS("b", interactive),
3574                                 SD_BUS_NO_RESULT,
3575                                 method_suspend,
3576                                 SD_BUS_VTABLE_UNPRIVILEGED),
3577         SD_BUS_METHOD_WITH_ARGS("SuspendWithFlags",
3578                                 SD_BUS_ARGS("t", flags),
3579                                 SD_BUS_NO_RESULT,
3580                                 method_suspend,
3581                                 SD_BUS_VTABLE_UNPRIVILEGED),
3582         SD_BUS_METHOD_WITH_ARGS("Hibernate",
3583                                 SD_BUS_ARGS("b", interactive),
3584                                 SD_BUS_NO_RESULT,
3585                                 method_hibernate,
3586                                 SD_BUS_VTABLE_UNPRIVILEGED),
3587         SD_BUS_METHOD_WITH_ARGS("HibernateWithFlags",
3588                                 SD_BUS_ARGS("t", flags),
3589                                 SD_BUS_NO_RESULT,
3590                                 method_hibernate,
3591                                 SD_BUS_VTABLE_UNPRIVILEGED),
3592         SD_BUS_METHOD_WITH_ARGS("HybridSleep",
3593                                 SD_BUS_ARGS("b", interactive),
3594                                 SD_BUS_NO_RESULT,
3595                                 method_hybrid_sleep,
3596                                 SD_BUS_VTABLE_UNPRIVILEGED),
3597         SD_BUS_METHOD_WITH_ARGS("HybridSleepWithFlags",
3598                                 SD_BUS_ARGS("t", flags),
3599                                 SD_BUS_NO_RESULT,
3600                                 method_hybrid_sleep,
3601                                 SD_BUS_VTABLE_UNPRIVILEGED),
3602         SD_BUS_METHOD_WITH_ARGS("SuspendThenHibernate",
3603                                 SD_BUS_ARGS("b", interactive),
3604                                 SD_BUS_NO_RESULT,
3605                                 method_suspend_then_hibernate,
3606                                 SD_BUS_VTABLE_UNPRIVILEGED),
3607         SD_BUS_METHOD_WITH_ARGS("SuspendThenHibernateWithFlags",
3608                                 SD_BUS_ARGS("t", flags),
3609                                 SD_BUS_NO_RESULT,
3610                                 method_suspend_then_hibernate,
3611                                 SD_BUS_VTABLE_UNPRIVILEGED),
3612         SD_BUS_METHOD_WITH_ARGS("CanPowerOff",
3613                                 SD_BUS_NO_ARGS,
3614                                 SD_BUS_RESULT("s", result),
3615                                 method_can_poweroff,
3616                                 SD_BUS_VTABLE_UNPRIVILEGED),
3617         SD_BUS_METHOD_WITH_ARGS("CanReboot",
3618                                 SD_BUS_NO_ARGS,
3619                                 SD_BUS_RESULT("s", result),
3620                                 method_can_reboot,
3621                                 SD_BUS_VTABLE_UNPRIVILEGED),
3622         SD_BUS_METHOD_WITH_ARGS("CanHalt",
3623                                 SD_BUS_NO_ARGS,
3624                                 SD_BUS_RESULT("s", result),
3625                                 method_can_halt,
3626                                 SD_BUS_VTABLE_UNPRIVILEGED),
3627         SD_BUS_METHOD_WITH_ARGS("CanSuspend",
3628                                 SD_BUS_NO_ARGS,
3629                                 SD_BUS_RESULT("s", result),
3630                                 method_can_suspend,
3631                                 SD_BUS_VTABLE_UNPRIVILEGED),
3632         SD_BUS_METHOD_WITH_ARGS("CanHibernate",
3633                                 SD_BUS_NO_ARGS,
3634                                 SD_BUS_RESULT("s", result),
3635                                 method_can_hibernate,
3636                                 SD_BUS_VTABLE_UNPRIVILEGED),
3637         SD_BUS_METHOD_WITH_ARGS("CanHybridSleep",
3638                                 SD_BUS_NO_ARGS,
3639                                 SD_BUS_RESULT("s", result),
3640                                 method_can_hybrid_sleep,
3641                                 SD_BUS_VTABLE_UNPRIVILEGED),
3642         SD_BUS_METHOD_WITH_ARGS("CanSuspendThenHibernate",
3643                                 SD_BUS_NO_ARGS,
3644                                 SD_BUS_RESULT("s", result),
3645                                 method_can_suspend_then_hibernate,
3646                                 SD_BUS_VTABLE_UNPRIVILEGED),
3647         SD_BUS_METHOD_WITH_ARGS("ScheduleShutdown",
3648                                 SD_BUS_ARGS("s", type, "t", usec),
3649                                 SD_BUS_NO_RESULT,
3650                                 method_schedule_shutdown,
3651                                 SD_BUS_VTABLE_UNPRIVILEGED),
3652         SD_BUS_METHOD_WITH_ARGS("CancelScheduledShutdown",
3653                                 SD_BUS_NO_ARGS,
3654                                 SD_BUS_RESULT("b", cancelled),
3655                                 method_cancel_scheduled_shutdown,
3656                                 SD_BUS_VTABLE_UNPRIVILEGED),
3657         SD_BUS_METHOD_WITH_ARGS("Inhibit",
3658                                 SD_BUS_ARGS("s", what, "s", who, "s", why, "s", mode),
3659                                 SD_BUS_RESULT("h", pipe_fd),
3660                                 method_inhibit,
3661                                 SD_BUS_VTABLE_UNPRIVILEGED),
3662         SD_BUS_METHOD_WITH_ARGS("CanRebootParameter",
3663                                 SD_BUS_NO_ARGS,
3664                                 SD_BUS_RESULT("s", result),
3665                                 method_can_reboot_parameter,
3666                                 SD_BUS_VTABLE_UNPRIVILEGED),
3667         SD_BUS_METHOD_WITH_ARGS("SetRebootParameter",
3668                                 SD_BUS_ARGS("s", parameter),
3669                                 SD_BUS_NO_RESULT,
3670                                 method_set_reboot_parameter,
3671                                 SD_BUS_VTABLE_UNPRIVILEGED),
3672         SD_BUS_METHOD_WITH_ARGS("CanRebootToFirmwareSetup",
3673                                 SD_BUS_NO_ARGS,
3674                                 SD_BUS_RESULT("s", result),
3675                                 method_can_reboot_to_firmware_setup,
3676                                 SD_BUS_VTABLE_UNPRIVILEGED),
3677         SD_BUS_METHOD_WITH_ARGS("SetRebootToFirmwareSetup",
3678                                 SD_BUS_ARGS("b", enable),
3679                                 SD_BUS_NO_RESULT,
3680                                 method_set_reboot_to_firmware_setup,
3681                                 SD_BUS_VTABLE_UNPRIVILEGED),
3682         SD_BUS_METHOD_WITH_ARGS("CanRebootToBootLoaderMenu",
3683                                 SD_BUS_NO_ARGS,
3684                                 SD_BUS_RESULT("s", result),
3685                                 method_can_reboot_to_boot_loader_menu,
3686                                 SD_BUS_VTABLE_UNPRIVILEGED),
3687         SD_BUS_METHOD_WITH_ARGS("SetRebootToBootLoaderMenu",
3688                                 SD_BUS_ARGS("t", timeout),
3689                                 SD_BUS_NO_RESULT,
3690                                 method_set_reboot_to_boot_loader_menu,
3691                                 SD_BUS_VTABLE_UNPRIVILEGED),
3692         SD_BUS_METHOD_WITH_ARGS("CanRebootToBootLoaderEntry",
3693                                 SD_BUS_NO_ARGS,
3694                                 SD_BUS_RESULT("s", result),
3695                                 method_can_reboot_to_boot_loader_entry,
3696                                 SD_BUS_VTABLE_UNPRIVILEGED),
3697         SD_BUS_METHOD_WITH_ARGS("SetRebootToBootLoaderEntry",
3698                                 SD_BUS_ARGS("s", boot_loader_entry),
3699                                 SD_BUS_NO_RESULT,
3700                                 method_set_reboot_to_boot_loader_entry,
3701                                 SD_BUS_VTABLE_UNPRIVILEGED),
3702         SD_BUS_METHOD_WITH_ARGS("SetWallMessage",
3703                                 SD_BUS_ARGS("s", wall_message, "b", enable),
3704                                 SD_BUS_NO_RESULT,
3705                                 method_set_wall_message,
3706                                 SD_BUS_VTABLE_UNPRIVILEGED),
3707 
3708         SD_BUS_SIGNAL_WITH_ARGS("SessionNew",
3709                                 SD_BUS_ARGS("s", session_id, "o", object_path),
3710                                 0),
3711         SD_BUS_SIGNAL_WITH_ARGS("SessionRemoved",
3712                                 SD_BUS_ARGS("s", session_id, "o", object_path),
3713                                 0),
3714         SD_BUS_SIGNAL_WITH_ARGS("UserNew",
3715                                 SD_BUS_ARGS("u", uid, "o", object_path),
3716                                 0),
3717         SD_BUS_SIGNAL_WITH_ARGS("UserRemoved",
3718                                 SD_BUS_ARGS("u", uid, "o", object_path),
3719                                 0),
3720         SD_BUS_SIGNAL_WITH_ARGS("SeatNew",
3721                                 SD_BUS_ARGS("s", seat_id, "o", object_path),
3722                                 0),
3723         SD_BUS_SIGNAL_WITH_ARGS("SeatRemoved",
3724                                 SD_BUS_ARGS("s", seat_id, "o", object_path),
3725                                 0),
3726         SD_BUS_SIGNAL_WITH_ARGS("PrepareForShutdown",
3727                                 SD_BUS_ARGS("b", start),
3728                                 0),
3729         SD_BUS_SIGNAL_WITH_ARGS("PrepareForSleep",
3730                                 SD_BUS_ARGS("b", start),
3731                                 0),
3732 
3733         SD_BUS_VTABLE_END
3734 };
3735 
3736 const BusObjectImplementation manager_object = {
3737         "/org/freedesktop/login1",
3738         "org.freedesktop.login1.Manager",
3739         .vtables = BUS_VTABLES(manager_vtable),
3740         .children = BUS_IMPLEMENTATIONS(&seat_object,
3741                                         &session_object,
3742                                         &user_object),
3743 };
3744 
session_jobs_reply(Session * s,uint32_t jid,const char * unit,const char * result)3745 static int session_jobs_reply(Session *s, uint32_t jid, const char *unit, const char *result) {
3746         assert(s);
3747         assert(unit);
3748 
3749         if (!s->started)
3750                 return 0;
3751 
3752         if (result && !streq(result, "done")) {
3753                 _cleanup_(sd_bus_error_free) sd_bus_error e = SD_BUS_ERROR_NULL;
3754 
3755                 sd_bus_error_setf(&e, BUS_ERROR_JOB_FAILED,
3756                                   "Job %u for unit '%s' failed with '%s'", jid, unit, result);
3757                 return session_send_create_reply(s, &e);
3758         }
3759 
3760         return session_send_create_reply(s, NULL);
3761 }
3762 
match_job_removed(sd_bus_message * message,void * userdata,sd_bus_error * error)3763 int match_job_removed(sd_bus_message *message, void *userdata, sd_bus_error *error) {
3764         const char *path, *result, *unit;
3765         Manager *m = userdata;
3766         Session *session;
3767         uint32_t id;
3768         User *user;
3769         int r;
3770 
3771         assert(message);
3772         assert(m);
3773 
3774         r = sd_bus_message_read(message, "uoss", &id, &path, &unit, &result);
3775         if (r < 0) {
3776                 bus_log_parse_error(r);
3777                 return 0;
3778         }
3779 
3780         if (m->action_job && streq(m->action_job, path)) {
3781                 assert(m->delayed_action);
3782                 log_info("Operation '%s' finished.", inhibit_what_to_string(m->delayed_action->inhibit_what));
3783 
3784                 /* Tell people that they now may take a lock again */
3785                 (void) send_prepare_for(m, m->delayed_action->inhibit_what, false);
3786 
3787                 m->action_job = mfree(m->action_job);
3788                 m->delayed_action = NULL;
3789                 return 0;
3790         }
3791 
3792         session = hashmap_get(m->session_units, unit);
3793         if (session) {
3794                 if (streq_ptr(path, session->scope_job)) {
3795                         session->scope_job = mfree(session->scope_job);
3796                         (void) session_jobs_reply(session, id, unit, result);
3797 
3798                         session_save(session);
3799                         user_save(session->user);
3800                 }
3801 
3802                 session_add_to_gc_queue(session);
3803         }
3804 
3805         user = hashmap_get(m->user_units, unit);
3806         if (user) {
3807                 if (streq_ptr(path, user->service_job)) {
3808                         user->service_job = mfree(user->service_job);
3809 
3810                         LIST_FOREACH(sessions_by_user, s, user->sessions)
3811                                 (void) session_jobs_reply(s, id, unit, NULL /* don't propagate user service failures to the client */);
3812 
3813                         user_save(user);
3814                 }
3815 
3816                 user_add_to_gc_queue(user);
3817         }
3818 
3819         return 0;
3820 }
3821 
match_unit_removed(sd_bus_message * message,void * userdata,sd_bus_error * error)3822 int match_unit_removed(sd_bus_message *message, void *userdata, sd_bus_error *error) {
3823         const char *path, *unit;
3824         Manager *m = userdata;
3825         Session *session;
3826         User *user;
3827         int r;
3828 
3829         assert(message);
3830         assert(m);
3831 
3832         r = sd_bus_message_read(message, "so", &unit, &path);
3833         if (r < 0) {
3834                 bus_log_parse_error(r);
3835                 return 0;
3836         }
3837 
3838         session = hashmap_get(m->session_units, unit);
3839         if (session)
3840                 session_add_to_gc_queue(session);
3841 
3842         user = hashmap_get(m->user_units, unit);
3843         if (user)
3844                 user_add_to_gc_queue(user);
3845 
3846         return 0;
3847 }
3848 
match_properties_changed(sd_bus_message * message,void * userdata,sd_bus_error * error)3849 int match_properties_changed(sd_bus_message *message, void *userdata, sd_bus_error *error) {
3850         _cleanup_free_ char *unit = NULL;
3851         Manager *m = userdata;
3852         const char *path;
3853         Session *session;
3854         User *user;
3855         int r;
3856 
3857         assert(message);
3858         assert(m);
3859 
3860         path = sd_bus_message_get_path(message);
3861         if (!path)
3862                 return 0;
3863 
3864         r = unit_name_from_dbus_path(path, &unit);
3865         if (r == -EINVAL) /* not a unit */
3866                 return 0;
3867         if (r < 0) {
3868                 log_oom();
3869                 return 0;
3870         }
3871 
3872         session = hashmap_get(m->session_units, unit);
3873         if (session)
3874                 session_add_to_gc_queue(session);
3875 
3876         user = hashmap_get(m->user_units, unit);
3877         if (user)
3878                 user_add_to_gc_queue(user);
3879 
3880         return 0;
3881 }
3882 
match_reloading(sd_bus_message * message,void * userdata,sd_bus_error * error)3883 int match_reloading(sd_bus_message *message, void *userdata, sd_bus_error *error) {
3884         Manager *m = userdata;
3885         Session *session;
3886         int b, r;
3887 
3888         assert(message);
3889         assert(m);
3890 
3891         r = sd_bus_message_read(message, "b", &b);
3892         if (r < 0) {
3893                 bus_log_parse_error(r);
3894                 return 0;
3895         }
3896 
3897         if (b)
3898                 return 0;
3899 
3900         /* systemd finished reloading, let's recheck all our sessions */
3901         log_debug("System manager has been reloaded, rechecking sessions...");
3902 
3903         HASHMAP_FOREACH(session, m->sessions)
3904                 session_add_to_gc_queue(session);
3905 
3906         return 0;
3907 }
3908 
manager_send_changed(Manager * manager,const char * property,...)3909 int manager_send_changed(Manager *manager, const char *property, ...) {
3910         char **l;
3911 
3912         assert(manager);
3913 
3914         l = strv_from_stdarg_alloca(property);
3915 
3916         return sd_bus_emit_properties_changed_strv(
3917                         manager->bus,
3918                         "/org/freedesktop/login1",
3919                         "org.freedesktop.login1.Manager",
3920                         l);
3921 }
3922 
strdup_job(sd_bus_message * reply,char ** job)3923 static int strdup_job(sd_bus_message *reply, char **job) {
3924         const char *j;
3925         char *copy;
3926         int r;
3927 
3928         r = sd_bus_message_read(reply, "o", &j);
3929         if (r < 0)
3930                 return r;
3931 
3932         copy = strdup(j);
3933         if (!copy)
3934                 return -ENOMEM;
3935 
3936         *job = copy;
3937         return 1;
3938 }
3939 
manager_start_scope(Manager * manager,const char * scope,pid_t pid,const char * slice,const char * description,char ** wants,char ** after,const char * requires_mounts_for,sd_bus_message * more_properties,sd_bus_error * error,char ** job)3940 int manager_start_scope(
3941                 Manager *manager,
3942                 const char *scope,
3943                 pid_t pid,
3944                 const char *slice,
3945                 const char *description,
3946                 char **wants,
3947                 char **after,
3948                 const char *requires_mounts_for,
3949                 sd_bus_message *more_properties,
3950                 sd_bus_error *error,
3951                 char **job) {
3952 
3953         _cleanup_(sd_bus_message_unrefp) sd_bus_message *m = NULL, *reply = NULL;
3954         int r;
3955 
3956         assert(manager);
3957         assert(scope);
3958         assert(pid > 1);
3959         assert(job);
3960 
3961         r = bus_message_new_method_call(manager->bus, &m, bus_systemd_mgr, "StartTransientUnit");
3962         if (r < 0)
3963                 return r;
3964 
3965         r = sd_bus_message_append(m, "ss", strempty(scope), "fail");
3966         if (r < 0)
3967                 return r;
3968 
3969         r = sd_bus_message_open_container(m, 'a', "(sv)");
3970         if (r < 0)
3971                 return r;
3972 
3973         if (!isempty(slice)) {
3974                 r = sd_bus_message_append(m, "(sv)", "Slice", "s", slice);
3975                 if (r < 0)
3976                         return r;
3977         }
3978 
3979         if (!isempty(description)) {
3980                 r = sd_bus_message_append(m, "(sv)", "Description", "s", description);
3981                 if (r < 0)
3982                         return r;
3983         }
3984 
3985         STRV_FOREACH(i, wants) {
3986                 r = sd_bus_message_append(m, "(sv)", "Wants", "as", 1, *i);
3987                 if (r < 0)
3988                         return r;
3989         }
3990 
3991         STRV_FOREACH(i, after) {
3992                 r = sd_bus_message_append(m, "(sv)", "After", "as", 1, *i);
3993                 if (r < 0)
3994                         return r;
3995         }
3996 
3997         if (!empty_or_root(requires_mounts_for)) {
3998                 r = sd_bus_message_append(m, "(sv)", "RequiresMountsFor", "as", 1, requires_mounts_for);
3999                 if (r < 0)
4000                         return r;
4001         }
4002 
4003         /* Make sure that the session shells are terminated with SIGHUP since bash and friends tend to ignore
4004          * SIGTERM */
4005         r = sd_bus_message_append(m, "(sv)", "SendSIGHUP", "b", true);
4006         if (r < 0)
4007                 return r;
4008 
4009         r = sd_bus_message_append(m, "(sv)", "PIDs", "au", 1, pid);
4010         if (r < 0)
4011                 return r;
4012 
4013         /* disable TasksMax= for the session scope, rely on the slice setting for it */
4014         r = sd_bus_message_append(m, "(sv)", "TasksMax", "t", UINT64_MAX);
4015         if (r < 0)
4016                 return bus_log_create_error(r);
4017 
4018         if (more_properties) {
4019                 /* If TasksMax also appears here, it will overwrite the default value set above */
4020                 r = sd_bus_message_copy(m, more_properties, true);
4021                 if (r < 0)
4022                         return r;
4023         }
4024 
4025         r = sd_bus_message_close_container(m);
4026         if (r < 0)
4027                 return r;
4028 
4029         r = sd_bus_message_append(m, "a(sa(sv))", 0);
4030         if (r < 0)
4031                 return r;
4032 
4033         r = sd_bus_call(manager->bus, m, 0, error, &reply);
4034         if (r < 0)
4035                 return r;
4036 
4037         return strdup_job(reply, job);
4038 }
4039 
manager_start_unit(Manager * manager,const char * unit,sd_bus_error * error,char ** job)4040 int manager_start_unit(Manager *manager, const char *unit, sd_bus_error *error, char **job) {
4041         _cleanup_(sd_bus_message_unrefp) sd_bus_message *reply = NULL;
4042         int r;
4043 
4044         assert(manager);
4045         assert(unit);
4046         assert(job);
4047 
4048         r = bus_call_method(
4049                         manager->bus,
4050                         bus_systemd_mgr,
4051                         "StartUnit",
4052                         error,
4053                         &reply,
4054                         "ss", unit, "replace");
4055         if (r < 0)
4056                 return r;
4057 
4058         return strdup_job(reply, job);
4059 }
4060 
manager_stop_unit(Manager * manager,const char * unit,const char * job_mode,sd_bus_error * error,char ** ret_job)4061 int manager_stop_unit(Manager *manager, const char *unit, const char *job_mode, sd_bus_error *error, char **ret_job) {
4062         _cleanup_(sd_bus_message_unrefp) sd_bus_message *reply = NULL;
4063         int r;
4064 
4065         assert(manager);
4066         assert(unit);
4067         assert(ret_job);
4068 
4069         r = bus_call_method(
4070                         manager->bus,
4071                         bus_systemd_mgr,
4072                         "StopUnit",
4073                         error,
4074                         &reply,
4075                         "ss", unit, job_mode ?: "fail");
4076         if (r < 0) {
4077                 if (sd_bus_error_has_names(error, BUS_ERROR_NO_SUCH_UNIT,
4078                                                   BUS_ERROR_LOAD_FAILED)) {
4079 
4080                         *ret_job = NULL;
4081                         sd_bus_error_free(error);
4082                         return 0;
4083                 }
4084 
4085                 return r;
4086         }
4087 
4088         return strdup_job(reply, ret_job);
4089 }
4090 
manager_abandon_scope(Manager * manager,const char * scope,sd_bus_error * ret_error)4091 int manager_abandon_scope(Manager *manager, const char *scope, sd_bus_error *ret_error) {
4092         _cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
4093         _cleanup_free_ char *path = NULL;
4094         int r;
4095 
4096         assert(manager);
4097         assert(scope);
4098 
4099         path = unit_dbus_path_from_name(scope);
4100         if (!path)
4101                 return -ENOMEM;
4102 
4103         r = sd_bus_call_method(
4104                         manager->bus,
4105                         "org.freedesktop.systemd1",
4106                         path,
4107                         "org.freedesktop.systemd1.Scope",
4108                         "Abandon",
4109                         &error,
4110                         NULL,
4111                         NULL);
4112         if (r < 0) {
4113                 if (sd_bus_error_has_names(&error, BUS_ERROR_NO_SUCH_UNIT,
4114                                                    BUS_ERROR_LOAD_FAILED,
4115                                                    BUS_ERROR_SCOPE_NOT_RUNNING))
4116                         return 0;
4117 
4118                 sd_bus_error_move(ret_error, &error);
4119                 return r;
4120         }
4121 
4122         return 1;
4123 }
4124 
manager_kill_unit(Manager * manager,const char * unit,KillWho who,int signo,sd_bus_error * error)4125 int manager_kill_unit(Manager *manager, const char *unit, KillWho who, int signo, sd_bus_error *error) {
4126         assert(manager);
4127         assert(unit);
4128 
4129         return bus_call_method(
4130                         manager->bus,
4131                         bus_systemd_mgr,
4132                         "KillUnit",
4133                         error,
4134                         NULL,
4135                         "ssi", unit, who == KILL_LEADER ? "main" : "all", signo);
4136 }
4137 
manager_unit_is_active(Manager * manager,const char * unit,sd_bus_error * ret_error)4138 int manager_unit_is_active(Manager *manager, const char *unit, sd_bus_error *ret_error) {
4139         _cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
4140         _cleanup_(sd_bus_message_unrefp) sd_bus_message *reply = NULL;
4141         _cleanup_free_ char *path = NULL;
4142         const char *state;
4143         int r;
4144 
4145         assert(manager);
4146         assert(unit);
4147 
4148         path = unit_dbus_path_from_name(unit);
4149         if (!path)
4150                 return -ENOMEM;
4151 
4152         r = sd_bus_get_property(
4153                         manager->bus,
4154                         "org.freedesktop.systemd1",
4155                         path,
4156                         "org.freedesktop.systemd1.Unit",
4157                         "ActiveState",
4158                         &error,
4159                         &reply,
4160                         "s");
4161         if (r < 0) {
4162                 /* systemd might have dropped off momentarily, let's
4163                  * not make this an error */
4164                 if (sd_bus_error_has_names(&error, SD_BUS_ERROR_NO_REPLY,
4165                                                    SD_BUS_ERROR_DISCONNECTED))
4166                         return true;
4167 
4168                 /* If the unit is already unloaded then it's not
4169                  * active */
4170                 if (sd_bus_error_has_names(&error, BUS_ERROR_NO_SUCH_UNIT,
4171                                                    BUS_ERROR_LOAD_FAILED))
4172                         return false;
4173 
4174                 sd_bus_error_move(ret_error, &error);
4175                 return r;
4176         }
4177 
4178         r = sd_bus_message_read(reply, "s", &state);
4179         if (r < 0)
4180                 return r;
4181 
4182         return !STR_IN_SET(state, "inactive", "failed");
4183 }
4184 
manager_job_is_active(Manager * manager,const char * path,sd_bus_error * ret_error)4185 int manager_job_is_active(Manager *manager, const char *path, sd_bus_error *ret_error) {
4186         _cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
4187         _cleanup_(sd_bus_message_unrefp) sd_bus_message *reply = NULL;
4188         int r;
4189 
4190         assert(manager);
4191         assert(path);
4192 
4193         r = sd_bus_get_property(
4194                         manager->bus,
4195                         "org.freedesktop.systemd1",
4196                         path,
4197                         "org.freedesktop.systemd1.Job",
4198                         "State",
4199                         &error,
4200                         &reply,
4201                         "s");
4202         if (r < 0) {
4203                 if (sd_bus_error_has_names(&error, SD_BUS_ERROR_NO_REPLY,
4204                                                    SD_BUS_ERROR_DISCONNECTED))
4205                         return true;
4206 
4207                 if (sd_bus_error_has_name(&error, SD_BUS_ERROR_UNKNOWN_OBJECT))
4208                         return false;
4209 
4210                 sd_bus_error_move(ret_error, &error);
4211                 return r;
4212         }
4213 
4214         /* We don't actually care about the state really. The fact
4215          * that we could read the job state is enough for us */
4216 
4217         return true;
4218 }
4219