chiark / gitweb /
Emit PrepareForSleep when resuming.
[elogind.git] / src / login / logind-dbus.c
1 /*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
2
3 /***
4   This file is part of systemd.
5
6   Copyright 2011 Lennart Poettering
7
8   systemd is free software; you can redistribute it and/or modify it
9   under the terms of the GNU Lesser General Public License as published by
10   the Free Software Foundation; either version 2.1 of the License, or
11   (at your option) any later version.
12
13   systemd is distributed in the hope that it will be useful, but
14   WITHOUT ANY WARRANTY; without even the implied warranty of
15   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16   Lesser General Public License for more details.
17
18   You should have received a copy of the GNU Lesser General Public License
19   along with systemd; If not, see <http://www.gnu.org/licenses/>.
20 ***/
21
22 #include <errno.h>
23 #include <string.h>
24 #include <unistd.h>
25 #include <pwd.h>
26
27 #include "sd-messages.h"
28 #include "strv.h"
29 #include "mkdir.h"
30 #include "path-util.h"
31 #include "special.h"
32 #include "sleep-config.h"
33 #include "fileio-label.h"
34 #include "unit-name.h"
35 #include "audit.h"
36 #include "bus-util.h"
37 #include "bus-error.h"
38 #include "bus-common-errors.h"
39 #include "udev-util.h"
40 #include "selinux-util.h"
41 #include "logind.h"
42
43 int manager_get_session_from_creds(Manager *m, sd_bus_message *message, const char *name, sd_bus_error *error, Session **ret) {
44         _cleanup_bus_creds_unref_ sd_bus_creds *creds = NULL;
45         Session *session;
46         int r;
47
48         assert(m);
49         assert(message);
50         assert(ret);
51
52         if (isempty(name)) {
53                 r = sd_bus_query_sender_creds(message, SD_BUS_CREDS_SESSION|SD_BUS_CREDS_AUGMENT, &creds);
54                 if (r < 0)
55                         return r;
56
57                 r = sd_bus_creds_get_session(creds, &name);
58                 if (r < 0)
59                         return r;
60         }
61
62         session = hashmap_get(m->sessions, name);
63         if (!session)
64                 return sd_bus_error_setf(error, BUS_ERROR_NO_SUCH_SESSION, "No session '%s' known", name);
65
66         *ret = session;
67         return 0;
68 }
69
70 int manager_get_user_from_creds(Manager *m, sd_bus_message *message, uid_t uid, sd_bus_error *error, User **ret) {
71         User *user;
72         int r;
73
74         assert(m);
75         assert(message);
76         assert(ret);
77
78         if (uid == UID_INVALID) {
79                 _cleanup_bus_creds_unref_ sd_bus_creds *creds = NULL;
80
81                 /* Note that we get the owner UID of the session, not the actual client UID here! */
82                 r = sd_bus_query_sender_creds(message, SD_BUS_CREDS_OWNER_UID|SD_BUS_CREDS_AUGMENT, &creds);
83                 if (r < 0)
84                         return r;
85
86                 r = sd_bus_creds_get_owner_uid(creds, &uid);
87                 if (r < 0)
88                         return r;
89         }
90
91         user = hashmap_get(m->users, UID_TO_PTR(uid));
92         if (!user)
93                 return sd_bus_error_setf(error, BUS_ERROR_NO_SUCH_USER, "No user "UID_FMT" known or logged in", uid);
94
95         *ret = user;
96         return 0;
97 }
98
99 int manager_get_seat_from_creds(Manager *m, sd_bus_message *message, const char *name, sd_bus_error *error, Seat **ret) {
100         Seat *seat;
101         int r;
102
103         assert(m);
104         assert(message);
105         assert(ret);
106
107         if (isempty(name)) {
108                 Session *session;
109
110                 r = manager_get_session_from_creds(m, message, NULL, error, &session);
111                 if (r < 0)
112                         return r;
113
114                 seat = session->seat;
115
116                 if (!seat)
117                         return sd_bus_error_setf(error, BUS_ERROR_NO_SUCH_SEAT, "Session has no seat.");
118         } else {
119                 seat = hashmap_get(m->seats, name);
120                 if (!seat)
121                         return sd_bus_error_setf(error, BUS_ERROR_NO_SUCH_SEAT, "No seat '%s' known", name);
122         }
123
124         *ret = seat;
125         return 0;
126 }
127
128 static int property_get_idle_hint(
129                 sd_bus *bus,
130                 const char *path,
131                 const char *interface,
132                 const char *property,
133                 sd_bus_message *reply,
134                 void *userdata,
135                 sd_bus_error *error) {
136
137         Manager *m = userdata;
138
139         assert(bus);
140         assert(reply);
141         assert(m);
142
143         return sd_bus_message_append(reply, "b", manager_get_idle_hint(m, NULL) > 0);
144 }
145
146 static int property_get_idle_since_hint(
147                 sd_bus *bus,
148                 const char *path,
149                 const char *interface,
150                 const char *property,
151                 sd_bus_message *reply,
152                 void *userdata,
153                 sd_bus_error *error) {
154
155         Manager *m = userdata;
156         dual_timestamp t;
157
158         assert(bus);
159         assert(reply);
160         assert(m);
161
162         manager_get_idle_hint(m, &t);
163
164         return sd_bus_message_append(reply, "t", streq(property, "IdleSinceHint") ? t.realtime : t.monotonic);
165 }
166
167 static int property_get_inhibited(
168                 sd_bus *bus,
169                 const char *path,
170                 const char *interface,
171                 const char *property,
172                 sd_bus_message *reply,
173                 void *userdata,
174                 sd_bus_error *error) {
175
176         Manager *m = userdata;
177         InhibitWhat w;
178
179         assert(bus);
180         assert(reply);
181         assert(m);
182
183         w = manager_inhibit_what(m, streq(property, "BlockInhibited") ? INHIBIT_BLOCK : INHIBIT_DELAY);
184
185         return sd_bus_message_append(reply, "s", inhibit_what_to_string(w));
186 }
187
188 static int property_get_preparing(
189                 sd_bus *bus,
190                 const char *path,
191                 const char *interface,
192                 const char *property,
193                 sd_bus_message *reply,
194                 void *userdata,
195                 sd_bus_error *error) {
196
197         Manager *m = userdata;
198         bool b;
199
200         assert(bus);
201         assert(reply);
202         assert(m);
203
204         if (streq(property, "PreparingForShutdown"))
205                 b = !!(m->action_what & INHIBIT_SHUTDOWN);
206         else
207                 b = !!(m->action_what & INHIBIT_SLEEP);
208
209         return sd_bus_message_append(reply, "b", b);
210 }
211
212 static BUS_DEFINE_PROPERTY_GET_ENUM(property_get_handle_action, handle_action, HandleAction);
213
214 static int method_get_session(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
215         _cleanup_free_ char *p = NULL;
216         Manager *m = userdata;
217         const char *name;
218         Session *session;
219         int r;
220
221         assert(bus);
222         assert(message);
223         assert(m);
224
225         r = sd_bus_message_read(message, "s", &name);
226         if (r < 0)
227                 return r;
228
229         r = manager_get_session_from_creds(m, message, name, error, &session);
230         if (r < 0)
231                 return r;
232
233         p = session_bus_path(session);
234         if (!p)
235                 return -ENOMEM;
236
237         return sd_bus_reply_method_return(message, "o", p);
238 }
239
240 static int method_get_session_by_pid(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
241         _cleanup_free_ char *p = NULL;
242         Session *session = NULL;
243         Manager *m = userdata;
244         pid_t pid;
245         int r;
246
247         assert(bus);
248         assert(message);
249         assert(m);
250
251         assert_cc(sizeof(pid_t) == sizeof(uint32_t));
252
253         r = sd_bus_message_read(message, "u", &pid);
254         if (r < 0)
255                 return r;
256
257         if (pid <= 0) {
258                 r = manager_get_session_from_creds(m, message, NULL, error, &session);
259                 if (r < 0)
260                         return r;
261         } else {
262                 r = manager_get_session_by_pid(m, pid, &session);
263                 if (r < 0)
264                         return r;
265
266                 if (!session)
267                         return sd_bus_error_setf(error, BUS_ERROR_NO_SESSION_FOR_PID, "PID "PID_FMT" does not belong to any known session", pid);
268         }
269
270         p = session_bus_path(session);
271         if (!p)
272                 return -ENOMEM;
273
274         return sd_bus_reply_method_return(message, "o", p);
275 }
276
277 static int method_get_user(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
278         _cleanup_free_ char *p = NULL;
279         Manager *m = userdata;
280         uint32_t uid;
281         User *user;
282         int r;
283
284         assert(bus);
285         assert(message);
286         assert(m);
287
288         r = sd_bus_message_read(message, "u", &uid);
289         if (r < 0)
290                 return r;
291
292         r = manager_get_user_from_creds(m, message, uid, error, &user);
293         if (r < 0)
294                 return r;
295
296         p = user_bus_path(user);
297         if (!p)
298                 return -ENOMEM;
299
300         return sd_bus_reply_method_return(message, "o", p);
301 }
302
303 static int method_get_user_by_pid(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
304         _cleanup_free_ char *p = NULL;
305         Manager *m = userdata;
306         User *user = NULL;
307         pid_t pid;
308         int r;
309
310         assert(bus);
311         assert(message);
312         assert(m);
313
314         assert_cc(sizeof(pid_t) == sizeof(uint32_t));
315
316         r = sd_bus_message_read(message, "u", &pid);
317         if (r < 0)
318                 return r;
319
320         if (pid <= 0) {
321                 r = manager_get_user_from_creds(m, message, UID_INVALID, error, &user);
322                 if (r < 0)
323                         return r;
324         } else {
325                 r = manager_get_user_by_pid(m, pid, &user);
326                 if (r < 0)
327                         return r;
328                 if (!user)
329                         return sd_bus_error_setf(error, BUS_ERROR_NO_USER_FOR_PID, "PID "PID_FMT" does not belong to any known or logged in user", pid);
330         }
331
332         p = user_bus_path(user);
333         if (!p)
334                 return -ENOMEM;
335
336         return sd_bus_reply_method_return(message, "o", p);
337 }
338
339 static int method_get_seat(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
340         _cleanup_free_ char *p = NULL;
341         Manager *m = userdata;
342         const char *name;
343         Seat *seat;
344         int r;
345
346         assert(bus);
347         assert(message);
348         assert(m);
349
350         r = sd_bus_message_read(message, "s", &name);
351         if (r < 0)
352                 return r;
353
354         r = manager_get_seat_from_creds(m, message, name, error, &seat);
355         if (r < 0)
356                 return r;
357
358         p = seat_bus_path(seat);
359         if (!p)
360                 return -ENOMEM;
361
362         return sd_bus_reply_method_return(message, "o", p);
363 }
364
365 static int method_list_sessions(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
366         _cleanup_bus_message_unref_ sd_bus_message *reply = NULL;
367         Manager *m = userdata;
368         Session *session;
369         Iterator i;
370         int r;
371
372         assert(bus);
373         assert(message);
374         assert(m);
375
376         r = sd_bus_message_new_method_return(message, &reply);
377         if (r < 0)
378                 return r;
379
380         r = sd_bus_message_open_container(reply, 'a', "(susso)");
381         if (r < 0)
382                 return r;
383
384         HASHMAP_FOREACH(session, m->sessions, i) {
385                 _cleanup_free_ char *p = NULL;
386
387                 p = session_bus_path(session);
388                 if (!p)
389                         return -ENOMEM;
390
391                 r = sd_bus_message_append(reply, "(susso)",
392                                           session->id,
393                                           (uint32_t) session->user->uid,
394                                           session->user->name,
395                                           session->seat ? session->seat->id : "",
396                                           p);
397                 if (r < 0)
398                         return r;
399         }
400
401         r = sd_bus_message_close_container(reply);
402         if (r < 0)
403                 return r;
404
405         return sd_bus_send(bus, reply, NULL);
406 }
407
408 static int method_list_users(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
409         _cleanup_bus_message_unref_ sd_bus_message *reply = NULL;
410         Manager *m = userdata;
411         User *user;
412         Iterator i;
413         int r;
414
415         assert(bus);
416         assert(message);
417         assert(m);
418
419         r = sd_bus_message_new_method_return(message, &reply);
420         if (r < 0)
421                 return r;
422
423         r = sd_bus_message_open_container(reply, 'a', "(uso)");
424         if (r < 0)
425                 return r;
426
427         HASHMAP_FOREACH(user, m->users, i) {
428                 _cleanup_free_ char *p = NULL;
429
430                 p = user_bus_path(user);
431                 if (!p)
432                         return -ENOMEM;
433
434                 r = sd_bus_message_append(reply, "(uso)",
435                                           (uint32_t) user->uid,
436                                           user->name,
437                                           p);
438                 if (r < 0)
439                         return r;
440         }
441
442         r = sd_bus_message_close_container(reply);
443         if (r < 0)
444                 return r;
445
446         return sd_bus_send(bus, reply, NULL);
447 }
448
449 static int method_list_seats(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
450         _cleanup_bus_message_unref_ sd_bus_message *reply = NULL;
451         Manager *m = userdata;
452         Seat *seat;
453         Iterator i;
454         int r;
455
456         assert(bus);
457         assert(message);
458         assert(m);
459
460         r = sd_bus_message_new_method_return(message, &reply);
461         if (r < 0)
462                 return r;
463
464         r = sd_bus_message_open_container(reply, 'a', "(so)");
465         if (r < 0)
466                 return r;
467
468         HASHMAP_FOREACH(seat, m->seats, i) {
469                 _cleanup_free_ char *p = NULL;
470
471                 p = seat_bus_path(seat);
472                 if (!p)
473                         return -ENOMEM;
474
475                 r = sd_bus_message_append(reply, "(so)", seat->id, p);
476                 if (r < 0)
477                         return r;
478         }
479
480         r = sd_bus_message_close_container(reply);
481         if (r < 0)
482                 return r;
483
484         return sd_bus_send(bus, reply, NULL);
485 }
486
487 static int method_list_inhibitors(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
488         _cleanup_bus_message_unref_ sd_bus_message *reply = NULL;
489         Manager *m = userdata;
490         Inhibitor *inhibitor;
491         Iterator i;
492         int r;
493
494         r = sd_bus_message_new_method_return(message, &reply);
495         if (r < 0)
496                 return r;
497
498         r = sd_bus_message_open_container(reply, 'a', "(ssssuu)");
499         if (r < 0)
500                 return r;
501
502         HASHMAP_FOREACH(inhibitor, m->inhibitors, i) {
503
504                 r = sd_bus_message_append(reply, "(ssssuu)",
505                                           strempty(inhibit_what_to_string(inhibitor->what)),
506                                           strempty(inhibitor->who),
507                                           strempty(inhibitor->why),
508                                           strempty(inhibit_mode_to_string(inhibitor->mode)),
509                                           (uint32_t) inhibitor->uid,
510                                           (uint32_t) inhibitor->pid);
511                 if (r < 0)
512                         return r;
513         }
514
515         r = sd_bus_message_close_container(reply);
516         if (r < 0)
517                 return r;
518
519         return sd_bus_send(bus, reply, NULL);
520 }
521
522 static int method_create_session(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
523         const char *service, *type, *class, *cseat, *tty, *display, *remote_user, *remote_host, *desktop;
524         uint32_t uid, leader, audit_id = 0;
525         _cleanup_free_ char *id = NULL;
526         Session *session = NULL;
527         Manager *m = userdata;
528         User *user = NULL;
529         Seat *seat = NULL;
530         int remote;
531         uint32_t vtnr = 0;
532         SessionType t;
533         SessionClass c;
534         int r;
535
536         assert(bus);
537         assert(message);
538         assert(m);
539
540         r = sd_bus_message_read(message, "uusssssussbss", &uid, &leader, &service, &type, &class, &desktop, &cseat, &vtnr, &tty, &display, &remote, &remote_user, &remote_host);
541         if (r < 0)
542                 return r;
543
544         if (leader == 1)
545                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Invalid leader PID");
546
547         if (isempty(type))
548                 t = _SESSION_TYPE_INVALID;
549         else {
550                 t = session_type_from_string(type);
551                 if (t < 0)
552                         return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Invalid session type %s", type);
553         }
554
555         if (isempty(class))
556                 c = _SESSION_CLASS_INVALID;
557         else {
558                 c = session_class_from_string(class);
559                 if (c < 0)
560                         return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Invalid session class %s", class);
561         }
562
563         if (isempty(desktop))
564                 desktop = NULL;
565         else {
566                 if (!string_is_safe(desktop))
567                         return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Invalid desktop string %s", desktop);
568         }
569
570         if (isempty(cseat))
571                 seat = NULL;
572         else {
573                 seat = hashmap_get(m->seats, cseat);
574                 if (!seat)
575                         return sd_bus_error_setf(error, BUS_ERROR_NO_SUCH_SEAT, "No seat '%s' known", cseat);
576         }
577
578         if (tty_is_vc(tty)) {
579                 int v;
580
581                 if (!seat)
582                         seat = m->seat0;
583                 else if (seat != m->seat0)
584                         return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "TTY %s is virtual console but seat %s is not seat0", tty, seat->id);
585
586                 v = vtnr_from_tty(tty);
587                 if (v <= 0)
588                         return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Cannot determine VT number from virtual console TTY %s", tty);
589
590                 if (!vtnr)
591                         vtnr = (uint32_t) v;
592                 else if (vtnr != (uint32_t) v)
593                         return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Specified TTY and VT number do not match");
594
595         } else if (tty_is_console(tty)) {
596
597                 if (!seat)
598                         seat = m->seat0;
599                 else if (seat != m->seat0)
600                         return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Console TTY specified but seat is not seat0");
601
602                 if (vtnr != 0)
603                         return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Console TTY specified but VT number is not 0");
604         }
605
606         if (seat) {
607                 if (seat_has_vts(seat)) {
608                         if (!vtnr || vtnr > 63)
609                                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "VT number out of range");
610                 } else {
611                         if (vtnr != 0)
612                                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Seat has no VTs but VT number not 0");
613                 }
614         }
615
616         r = sd_bus_message_enter_container(message, 'a', "(sv)");
617         if (r < 0)
618                 return r;
619
620         if (t == _SESSION_TYPE_INVALID) {
621                 if (!isempty(display))
622                         t = SESSION_X11;
623                 else if (!isempty(tty))
624                         t = SESSION_TTY;
625                 else
626                         t = SESSION_UNSPECIFIED;
627         }
628
629         if (c == _SESSION_CLASS_INVALID) {
630                 if (t == SESSION_UNSPECIFIED)
631                         c = SESSION_BACKGROUND;
632                 else
633                         c = SESSION_USER;
634         }
635
636         if (leader <= 0) {
637                 _cleanup_bus_creds_unref_ sd_bus_creds *creds = NULL;
638
639                 r = sd_bus_query_sender_creds(message, SD_BUS_CREDS_PID, &creds);
640                 if (r < 0)
641                         return r;
642
643                 r = sd_bus_creds_get_pid(creds, (pid_t*) &leader);
644                 if (r < 0)
645                         return r;
646         }
647
648         manager_get_session_by_pid(m, leader, &session);
649         if (session) {
650                 _cleanup_free_ char *path = NULL;
651                 _cleanup_close_ int fifo_fd = -1;
652
653                 /* Session already exists, client is probably
654                  * something like "su" which changes uid but is still
655                  * the same session */
656
657                 fifo_fd = session_create_fifo(session);
658                 if (fifo_fd < 0)
659                         return fifo_fd;
660
661                 path = session_bus_path(session);
662                 if (!path)
663                         return -ENOMEM;
664
665                 log_debug("Sending reply about an existing session: "
666                           "id=%s object_path=%s uid=%u runtime_path=%s "
667                           "session_fd=%d seat=%s vtnr=%u",
668                           session->id,
669                           path,
670                           (uint32_t) session->user->uid,
671                           session->user->runtime_path,
672                           fifo_fd,
673                           session->seat ? session->seat->id : "",
674                           (uint32_t) session->vtnr);
675
676                 return sd_bus_reply_method_return(
677                                 message, "soshusub",
678                                 session->id,
679                                 path,
680                                 session->user->runtime_path,
681                                 fifo_fd,
682                                 (uint32_t) session->user->uid,
683                                 session->seat ? session->seat->id : "",
684                                 (uint32_t) session->vtnr,
685                                 true);
686         }
687
688         audit_session_from_pid(leader, &audit_id);
689         if (audit_id > 0) {
690                 /* Keep our session IDs and the audit session IDs in sync */
691
692                 if (asprintf(&id, "%"PRIu32, audit_id) < 0)
693                         return -ENOMEM;
694
695                 /* Wut? There's already a session by this name and we
696                  * didn't find it above? Weird, then let's not trust
697                  * the audit data and let's better register a new
698                  * ID */
699                 if (hashmap_get(m->sessions, id)) {
700                         log_warning("Existing logind session ID %s used by new audit session, ignoring", id);
701                         audit_id = 0;
702
703                         free(id);
704                         id = NULL;
705                 }
706         }
707
708         if (!id) {
709                 do {
710                         free(id);
711                         id = NULL;
712
713                         if (asprintf(&id, "c%lu", ++m->session_counter) < 0)
714                                 return -ENOMEM;
715
716                 } while (hashmap_get(m->sessions, id));
717         }
718
719         r = manager_add_user_by_uid(m, uid, &user);
720         if (r < 0)
721                 goto fail;
722
723         r = manager_add_session(m, id, &session);
724         if (r < 0)
725                 goto fail;
726
727         session_set_user(session, user);
728
729         session->leader = leader;
730         session->audit_id = audit_id;
731         session->type = t;
732         session->class = c;
733         session->remote = remote;
734         session->vtnr = vtnr;
735
736         if (!isempty(tty)) {
737                 session->tty = strdup(tty);
738                 if (!session->tty) {
739                         r = -ENOMEM;
740                         goto fail;
741                 }
742         }
743
744         if (!isempty(display)) {
745                 session->display = strdup(display);
746                 if (!session->display) {
747                         r = -ENOMEM;
748                         goto fail;
749                 }
750         }
751
752         if (!isempty(remote_user)) {
753                 session->remote_user = strdup(remote_user);
754                 if (!session->remote_user) {
755                         r = -ENOMEM;
756                         goto fail;
757                 }
758         }
759
760         if (!isempty(remote_host)) {
761                 session->remote_host = strdup(remote_host);
762                 if (!session->remote_host) {
763                         r = -ENOMEM;
764                         goto fail;
765                 }
766         }
767
768         if (!isempty(service)) {
769                 session->service = strdup(service);
770                 if (!session->service) {
771                         r = -ENOMEM;
772                         goto fail;
773                 }
774         }
775
776         if (!isempty(desktop)) {
777                 session->desktop = strdup(desktop);
778                 if (!session->desktop) {
779                         r = -ENOMEM;
780                         goto fail;
781                 }
782         }
783
784         if (seat) {
785                 r = seat_attach_session(seat, session);
786                 if (r < 0)
787                         goto fail;
788         }
789
790         r = session_start(session);
791         if (r < 0)
792                 goto fail;
793
794         session->create_message = sd_bus_message_ref(message);
795
796         /* Here upstream systemd starts cgroups and the user systemd,
797            and arranges to reply asynchronously.  We reply
798            directly.  */
799
800         r = session_send_create_reply(session, NULL);
801         if (r < 0)
802                 goto fail;
803
804         return 1;
805
806 fail:
807         if (session)
808                 session_add_to_gc_queue(session);
809
810         if (user)
811                 user_add_to_gc_queue(user);
812
813         return r;
814 }
815
816 static int method_release_session(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
817         Manager *m = userdata;
818         Session *session;
819         const char *name;
820         int r;
821
822         assert(bus);
823         assert(message);
824         assert(m);
825
826         r = sd_bus_message_read(message, "s", &name);
827         if (r < 0)
828                 return r;
829
830         r = manager_get_session_from_creds(m, message, name, error, &session);
831         if (r < 0)
832                 return r;
833
834         r = session_release(session);
835         if (r < 0)
836                 return r;
837
838         session_add_to_gc_queue(session);
839
840         return sd_bus_reply_method_return(message, NULL);
841 }
842
843 static int method_activate_session(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
844         Manager *m = userdata;
845         Session *session;
846         const char *name;
847         int r;
848
849         assert(bus);
850         assert(message);
851         assert(m);
852
853         r = sd_bus_message_read(message, "s", &name);
854         if (r < 0)
855                 return r;
856
857         r = manager_get_session_from_creds(m, message, name, error, &session);
858         if (r < 0)
859                 return r;
860
861         return bus_session_method_activate(bus, message, session, error);
862 }
863
864 static int method_activate_session_on_seat(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
865         const char *session_name, *seat_name;
866         Manager *m = userdata;
867         Session *session;
868         Seat *seat;
869         int r;
870
871         assert(bus);
872         assert(message);
873         assert(m);
874
875         /* Same as ActivateSession() but refuses to work if
876          * the seat doesn't match */
877
878         r = sd_bus_message_read(message, "ss", &session_name, &seat_name);
879         if (r < 0)
880                 return r;
881
882         r = manager_get_session_from_creds(m, message, session_name, error, &session);
883         if (r < 0)
884                 return r;
885
886         r = manager_get_seat_from_creds(m, message, seat_name, error, &seat);
887         if (r < 0)
888                 return r;
889
890         if (session->seat != seat)
891                 return sd_bus_error_setf(error, BUS_ERROR_SESSION_NOT_ON_SEAT, "Session %s not on seat %s", session_name, seat_name);
892
893         r = session_activate(session);
894         if (r < 0)
895                 return r;
896
897         return sd_bus_reply_method_return(message, NULL);
898 }
899
900 static int method_lock_session(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
901         Manager *m = userdata;
902         Session *session;
903         const char *name;
904         int r;
905
906         assert(bus);
907         assert(message);
908         assert(m);
909
910         r = sd_bus_message_read(message, "s", &name);
911         if (r < 0)
912                 return r;
913
914         r = manager_get_session_from_creds(m, message, name, error, &session);
915         if (r < 0)
916                 return r;
917
918         return bus_session_method_lock(bus, message, session, error);
919 }
920
921 static int method_lock_sessions(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
922         Manager *m = userdata;
923         int r;
924
925         assert(bus);
926         assert(message);
927         assert(m);
928
929         r = bus_verify_polkit_async(
930                         message,
931                         CAP_SYS_ADMIN,
932                         "org.freedesktop.login1.lock-sessions",
933                         false,
934                         UID_INVALID,
935                         &m->polkit_registry,
936                         error);
937         if (r < 0)
938                 return r;
939         if (r == 0)
940                 return 1; /* Will call us back */
941
942         r = session_send_lock_all(m, streq(sd_bus_message_get_member(message), "LockSessions"));
943         if (r < 0)
944                 return r;
945
946         return sd_bus_reply_method_return(message, NULL);
947 }
948
949 static int method_kill_session(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
950         const char *name;
951         Manager *m = userdata;
952         Session *session;
953         int r;
954
955         assert(bus);
956         assert(message);
957         assert(m);
958
959         r = sd_bus_message_read(message, "s", &name);
960         if (r < 0)
961                 return r;
962
963         r = manager_get_session_from_creds(m, message, name, error, &session);
964         if (r < 0)
965                 return r;
966
967         return bus_session_method_kill(bus, message, session, error);
968 }
969
970 static int method_kill_user(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
971         Manager *m = userdata;
972         uint32_t uid;
973         User *user;
974         int r;
975
976         assert(bus);
977         assert(message);
978         assert(m);
979
980         r = sd_bus_message_read(message, "u", &uid);
981         if (r < 0)
982                 return r;
983
984         r = manager_get_user_from_creds(m, message, uid, error, &user);
985         if (r < 0)
986                 return r;
987
988         return bus_user_method_kill(bus, message, user, error);
989 }
990
991 static int method_terminate_session(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
992         Manager *m = userdata;
993         const char *name;
994         Session *session;
995         int r;
996
997         assert(bus);
998         assert(message);
999         assert(m);
1000
1001         r = sd_bus_message_read(message, "s", &name);
1002         if (r < 0)
1003                 return r;
1004
1005         r = manager_get_session_from_creds(m, message, name, error, &session);
1006         if (r < 0)
1007                 return r;
1008
1009         return bus_session_method_terminate(bus, message, session, error);
1010 }
1011
1012 static int method_terminate_user(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1013         Manager *m = userdata;
1014         uint32_t uid;
1015         User *user;
1016         int r;
1017
1018         assert(bus);
1019         assert(message);
1020         assert(m);
1021
1022         r = sd_bus_message_read(message, "u", &uid);
1023         if (r < 0)
1024                 return r;
1025
1026         r = manager_get_user_from_creds(m, message, uid, error, &user);
1027         if (r < 0)
1028                 return r;
1029
1030         return bus_user_method_terminate(bus, message, user, error);
1031 }
1032
1033 static int method_terminate_seat(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1034         Manager *m = userdata;
1035         const char *name;
1036         Seat *seat;
1037         int r;
1038
1039         assert(bus);
1040         assert(message);
1041         assert(m);
1042
1043         r = sd_bus_message_read(message, "s", &name);
1044         if (r < 0)
1045                 return r;
1046
1047         r = manager_get_seat_from_creds(m, message, name, error, &seat);
1048         if (r < 0)
1049                 return r;
1050
1051         return bus_seat_method_terminate(bus, message, seat, error);
1052 }
1053
1054 static int method_set_user_linger(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1055         _cleanup_free_ char *cc = NULL;
1056         Manager *m = userdata;
1057         int b, r;
1058         struct passwd *pw;
1059         const char *path;
1060         uint32_t uid;
1061         int interactive;
1062
1063         assert(bus);
1064         assert(message);
1065         assert(m);
1066
1067         r = sd_bus_message_read(message, "ubb", &uid, &b, &interactive);
1068         if (r < 0)
1069                 return r;
1070
1071         if (uid == UID_INVALID) {
1072                 _cleanup_bus_creds_unref_ sd_bus_creds *creds = NULL;
1073
1074                 /* Note that we get the owner UID of the session, not the actual client UID here! */
1075                 r = sd_bus_query_sender_creds(message, SD_BUS_CREDS_OWNER_UID|SD_BUS_CREDS_AUGMENT, &creds);
1076                 if (r < 0)
1077                         return r;
1078
1079                 r = sd_bus_creds_get_owner_uid(creds, &uid);
1080                 if (r < 0)
1081                         return r;
1082         }
1083
1084         errno = 0;
1085         pw = getpwuid(uid);
1086         if (!pw)
1087                 return errno ? -errno : -ENOENT;
1088
1089         r = bus_verify_polkit_async(
1090                         message,
1091                         CAP_SYS_ADMIN,
1092                         "org.freedesktop.login1.set-user-linger",
1093                         interactive,
1094                         UID_INVALID,
1095                         &m->polkit_registry,
1096                         error);
1097         if (r < 0)
1098                 return r;
1099         if (r == 0)
1100                 return 1; /* No authorization for now, but the async polkit stuff will call us again when it has it */
1101
1102         mkdir_p_label("/var/lib/systemd", 0755);
1103
1104         r = mkdir_safe_label("/var/lib/systemd/linger", 0755, 0, 0);
1105         if (r < 0)
1106                 return r;
1107
1108         cc = cescape(pw->pw_name);
1109         if (!cc)
1110                 return -ENOMEM;
1111
1112         path = strjoina("/var/lib/systemd/linger/", cc);
1113         if (b) {
1114                 User *u;
1115
1116                 r = touch(path);
1117                 if (r < 0)
1118                         return r;
1119
1120                 if (manager_add_user_by_uid(m, uid, &u) >= 0)
1121                         user_start(u);
1122
1123         } else {
1124                 User *u;
1125
1126                 r = unlink(path);
1127                 if (r < 0 && errno != ENOENT)
1128                         return -errno;
1129
1130                 u = hashmap_get(m->users, UID_TO_PTR(uid));
1131                 if (u)
1132                         user_add_to_gc_queue(u);
1133         }
1134
1135         return sd_bus_reply_method_return(message, NULL);
1136 }
1137
1138 static int trigger_device(Manager *m, struct udev_device *d) {
1139         _cleanup_udev_enumerate_unref_ struct udev_enumerate *e = NULL;
1140         struct udev_list_entry *first, *item;
1141         int r;
1142
1143         assert(m);
1144
1145         e = udev_enumerate_new(m->udev);
1146         if (!e)
1147                 return -ENOMEM;
1148
1149         if (d) {
1150                 r = udev_enumerate_add_match_parent(e, d);
1151                 if (r < 0)
1152                         return r;
1153         }
1154
1155         r = udev_enumerate_scan_devices(e);
1156         if (r < 0)
1157                 return r;
1158
1159         first = udev_enumerate_get_list_entry(e);
1160         udev_list_entry_foreach(item, first) {
1161                 _cleanup_free_ char *t = NULL;
1162                 const char *p;
1163
1164                 p = udev_list_entry_get_name(item);
1165
1166                 t = strappend(p, "/uevent");
1167                 if (!t)
1168                         return -ENOMEM;
1169
1170                 write_string_file(t, "change");
1171         }
1172
1173         return 0;
1174 }
1175
1176 static int attach_device(Manager *m, const char *seat, const char *sysfs) {
1177         _cleanup_udev_device_unref_ struct udev_device *d = NULL;
1178         _cleanup_free_ char *rule = NULL, *file = NULL;
1179         const char *id_for_seat;
1180         int r;
1181
1182         assert(m);
1183         assert(seat);
1184         assert(sysfs);
1185
1186         d = udev_device_new_from_syspath(m->udev, sysfs);
1187         if (!d)
1188                 return -ENODEV;
1189
1190         if (!udev_device_has_tag(d, "seat"))
1191                 return -ENODEV;
1192
1193         id_for_seat = udev_device_get_property_value(d, "ID_FOR_SEAT");
1194         if (!id_for_seat)
1195                 return -ENODEV;
1196
1197         if (asprintf(&file, "/etc/udev/rules.d/72-seat-%s.rules", id_for_seat) < 0)
1198                 return -ENOMEM;
1199
1200         if (asprintf(&rule, "TAG==\"seat\", ENV{ID_FOR_SEAT}==\"%s\", ENV{ID_SEAT}=\"%s\"", id_for_seat, seat) < 0)
1201                 return -ENOMEM;
1202
1203         mkdir_p_label("/etc/udev/rules.d", 0755);
1204         mac_selinux_init("/etc");
1205         r = write_string_file_atomic_label(file, rule);
1206         if (r < 0)
1207                 return r;
1208
1209         return trigger_device(m, d);
1210 }
1211
1212 static int flush_devices(Manager *m) {
1213         _cleanup_closedir_ DIR *d;
1214
1215         assert(m);
1216
1217         d = opendir("/etc/udev/rules.d");
1218         if (!d) {
1219                 if (errno != ENOENT)
1220                         log_warning_errno(errno, "Failed to open /etc/udev/rules.d: %m");
1221         } else {
1222                 struct dirent *de;
1223
1224                 while ((de = readdir(d))) {
1225
1226                         if (!dirent_is_file(de))
1227                                 continue;
1228
1229                         if (!startswith(de->d_name, "72-seat-"))
1230                                 continue;
1231
1232                         if (!endswith(de->d_name, ".rules"))
1233                                 continue;
1234
1235                         if (unlinkat(dirfd(d), de->d_name, 0) < 0)
1236                                 log_warning_errno(errno, "Failed to unlink %s: %m", de->d_name);
1237                 }
1238         }
1239
1240         return trigger_device(m, NULL);
1241 }
1242
1243 static int method_attach_device(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1244         const char *sysfs, *seat;
1245         Manager *m = userdata;
1246         int interactive, r;
1247
1248         assert(bus);
1249         assert(message);
1250         assert(m);
1251
1252         r = sd_bus_message_read(message, "ssb", &seat, &sysfs, &interactive);
1253         if (r < 0)
1254                 return r;
1255
1256         if (!path_startswith(sysfs, "/sys"))
1257                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Path %s is not in /sys", sysfs);
1258
1259         if (!seat_name_is_valid(seat))
1260                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Seat %s is not valid", seat);
1261
1262         r = bus_verify_polkit_async(
1263                         message,
1264                         CAP_SYS_ADMIN,
1265                         "org.freedesktop.login1.attach-device",
1266                         interactive,
1267                         UID_INVALID,
1268                         &m->polkit_registry,
1269                         error);
1270         if (r < 0)
1271                 return r;
1272         if (r == 0)
1273                 return 1; /* No authorization for now, but the async polkit stuff will call us again when it has it */
1274
1275         r = attach_device(m, seat, sysfs);
1276         if (r < 0)
1277                 return r;
1278
1279         return sd_bus_reply_method_return(message, NULL);
1280 }
1281
1282 static int method_flush_devices(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1283         Manager *m = userdata;
1284         int interactive, r;
1285
1286         assert(bus);
1287         assert(message);
1288         assert(m);
1289
1290         r = sd_bus_message_read(message, "b", &interactive);
1291         if (r < 0)
1292                 return r;
1293
1294         r = bus_verify_polkit_async(
1295                         message,
1296                         CAP_SYS_ADMIN,
1297                         "org.freedesktop.login1.flush-devices",
1298                         interactive,
1299                         UID_INVALID,
1300                         &m->polkit_registry,
1301                         error);
1302         if (r < 0)
1303                 return r;
1304         if (r == 0)
1305                 return 1; /* No authorization for now, but the async polkit stuff will call us again when it has it */
1306
1307         r = flush_devices(m);
1308         if (r < 0)
1309                 return r;
1310
1311         return sd_bus_reply_method_return(message, NULL);
1312 }
1313
1314 static int have_multiple_sessions(
1315                 Manager *m,
1316                 uid_t uid) {
1317
1318         Session *session;
1319         Iterator i;
1320
1321         assert(m);
1322
1323         /* Check for other users' sessions. Greeter sessions do not
1324          * count, and non-login sessions do not count either. */
1325         HASHMAP_FOREACH(session, m->sessions, i)
1326                 if (session->class == SESSION_USER &&
1327                     session->user->uid != uid)
1328                         return true;
1329
1330         return false;
1331 }
1332
1333 static int bus_manager_log_shutdown(
1334                 Manager *m,
1335                 InhibitWhat w,
1336                 HandleAction action) {
1337
1338         const char *p, *q;
1339
1340         assert(m);
1341
1342         if (w != INHIBIT_SHUTDOWN)
1343                 return 0;
1344
1345         switch (action) {
1346         case HANDLE_POWEROFF:
1347                 p = "MESSAGE=System is powering down.";
1348                 q = "SHUTDOWN=power-off";
1349                 break;
1350         case HANDLE_HALT:
1351                 p = "MESSAGE=System is halting.";
1352                 q = "SHUTDOWN=halt";
1353                 break;
1354         case HANDLE_REBOOT:
1355                 p = "MESSAGE=System is rebooting.";
1356                 q = "SHUTDOWN=reboot";
1357                 break;
1358         case HANDLE_KEXEC:
1359                 p = "MESSAGE=System is rebooting with kexec.";
1360                 q = "SHUTDOWN=kexec";
1361                 break;
1362         default:
1363                 p = "MESSAGE=System is shutting down.";
1364                 q = NULL;
1365                 break;
1366         }
1367
1368         return log_struct(LOG_NOTICE,
1369                           LOG_MESSAGE_ID(SD_MESSAGE_SHUTDOWN),
1370                           p,
1371                           q,
1372                           NULL);
1373 }
1374
1375 static int lid_switch_ignore_handler(sd_event_source *e, uint64_t usec, void *userdata) {
1376         Manager *m = userdata;
1377
1378         assert(e);
1379         assert(m);
1380
1381         m->lid_switch_ignore_event_source = sd_event_source_unref(m->lid_switch_ignore_event_source);
1382         return 0;
1383 }
1384
1385 int manager_set_lid_switch_ignore(Manager *m, usec_t until) {
1386         int r;
1387
1388         assert(m);
1389
1390         if (until <= now(CLOCK_MONOTONIC))
1391                 return 0;
1392
1393         /* We want to ignore the lid switch for a while after each
1394          * suspend, and after boot-up. Hence let's install a timer for
1395          * this. As long as the event source exists we ignore the lid
1396          * switch. */
1397
1398         if (m->lid_switch_ignore_event_source) {
1399                 usec_t u;
1400
1401                 r = sd_event_source_get_time(m->lid_switch_ignore_event_source, &u);
1402                 if (r < 0)
1403                         return r;
1404
1405                 if (until <= u)
1406                         return 0;
1407
1408                 r = sd_event_source_set_time(m->lid_switch_ignore_event_source, until);
1409         } else
1410                 r = sd_event_add_time(
1411                                 m->event,
1412                                 &m->lid_switch_ignore_event_source,
1413                                 CLOCK_MONOTONIC,
1414                                 until, 0,
1415                                 lid_switch_ignore_handler, m);
1416
1417         return r;
1418 }
1419
1420 static int send_prepare_for(Manager *m, InhibitWhat w, bool _active) {
1421
1422         static const char * const signal_name[_INHIBIT_WHAT_MAX] = {
1423                 [INHIBIT_SHUTDOWN] = "PrepareForShutdown",
1424                 [INHIBIT_SLEEP] = "PrepareForSleep"
1425         };
1426
1427         int active = _active;
1428
1429         assert(m);
1430         assert(w >= 0);
1431         assert(w < _INHIBIT_WHAT_MAX);
1432         assert(signal_name[w]);
1433
1434         return sd_bus_emit_signal(m->bus,
1435                                   "/org/freedesktop/login1",
1436                                   "org.freedesktop.login1.Manager",
1437                                   signal_name[w],
1438                                   "b",
1439                                   active);
1440 }
1441
1442 static int execute_shutdown_or_sleep(
1443                 Manager *m,
1444                 InhibitWhat w,
1445                 HandleAction action,
1446                 sd_bus_error *error) {
1447         int r;
1448
1449         assert(m);
1450         assert(w >= 0);
1451         assert(w < _INHIBIT_WHAT_MAX);
1452
1453         bus_manager_log_shutdown(m, w, action);
1454
1455         r = shutdown_or_sleep(m, action);
1456         if (r < 0)
1457                 return r;
1458
1459         /* And we're back. */
1460         send_prepare_for(m, w, false);
1461
1462         /* Make sure the lid switch is ignored for a while (?) */
1463         manager_set_lid_switch_ignore(m, now(CLOCK_MONOTONIC) + m->holdoff_timeout_usec);
1464
1465         return 0;
1466 }
1467
1468 static int delay_shutdown_or_sleep(
1469                 Manager *m,
1470                 InhibitWhat w,
1471                 HandleAction action) {
1472
1473         assert(m);
1474         assert(w >= 0);
1475         assert(w < _INHIBIT_WHAT_MAX);
1476
1477         m->action_timestamp = now(CLOCK_MONOTONIC);
1478         m->pending_action = action;
1479         m->action_what = w;
1480
1481         return 0;
1482 }
1483
1484 int bus_manager_shutdown_or_sleep_now_or_later(
1485                 Manager *m,
1486                 HandleAction action,
1487                 InhibitWhat w,
1488                 sd_bus_error *error) {
1489
1490         bool delayed;
1491         int r;
1492
1493         assert(m);
1494         assert(w >= 0);
1495         assert(w <= _INHIBIT_WHAT_MAX);
1496
1497         /* Tell everybody to prepare for shutdown/sleep */
1498         send_prepare_for(m, w, true);
1499
1500         delayed =
1501                 m->inhibit_delay_max > 0 &&
1502                 manager_is_inhibited(m, w, INHIBIT_DELAY, NULL, false, false, 0, NULL);
1503
1504         if (delayed)
1505                 /* Shutdown is delayed, keep in mind what we
1506                  * want to do, and start a timeout */
1507                 r = delay_shutdown_or_sleep(m, w, action);
1508         else
1509                 /* Shutdown is not delayed, execute it
1510                  * immediately */
1511                 r = execute_shutdown_or_sleep(m, w, action, error);
1512
1513         return r;
1514 }
1515
1516 static int method_do_shutdown_or_sleep(
1517                 Manager *m,
1518                 sd_bus_message *message,
1519                 HandleAction sleep_action,
1520                 InhibitWhat w,
1521                 const char *action,
1522                 const char *action_multiple_sessions,
1523                 const char *action_ignore_inhibit,
1524                 const char *sleep_verb,
1525                 sd_bus_message_handler_t method,
1526                 sd_bus_error *error) {
1527
1528         _cleanup_bus_creds_unref_ sd_bus_creds *creds = NULL;
1529         bool multiple_sessions, blocked;
1530         int interactive, r;
1531         uid_t uid;
1532
1533         assert(m);
1534         assert(message);
1535         assert(w >= 0);
1536         assert(w <= _INHIBIT_WHAT_MAX);
1537         assert(action);
1538         assert(action_multiple_sessions);
1539         assert(action_ignore_inhibit);
1540         assert(method);
1541
1542         r = sd_bus_message_read(message, "b", &interactive);
1543         if (r < 0)
1544                 return r;
1545
1546         /* Don't allow multiple jobs being executed at the same time */
1547         if (m->action_what)
1548                 return sd_bus_error_setf(error, BUS_ERROR_OPERATION_IN_PROGRESS, "There's already a shutdown or sleep operation in progress");
1549
1550         if (sleep_verb) {
1551                 r = can_sleep(sleep_verb);
1552                 if (r < 0)
1553                         return r;
1554
1555                 if (r == 0)
1556                         return sd_bus_error_setf(error, BUS_ERROR_SLEEP_VERB_NOT_SUPPORTED, "Sleep verb not supported");
1557         }
1558
1559         r = sd_bus_query_sender_creds(message, SD_BUS_CREDS_EUID, &creds);
1560         if (r < 0)
1561                 return r;
1562
1563         r = sd_bus_creds_get_euid(creds, &uid);
1564         if (r < 0)
1565                 return r;
1566
1567         r = have_multiple_sessions(m, uid);
1568         if (r < 0)
1569                 return r;
1570
1571         multiple_sessions = r > 0;
1572         blocked = manager_is_inhibited(m, w, INHIBIT_BLOCK, NULL, false, true, uid, NULL);
1573
1574         if (multiple_sessions) {
1575                 r = bus_verify_polkit_async(message, CAP_SYS_BOOT, action_multiple_sessions, interactive, UID_INVALID, &m->polkit_registry, error);
1576                 if (r < 0)
1577                         return r;
1578                 if (r == 0)
1579                         return 1; /* No authorization for now, but the async polkit stuff will call us again when it has it */
1580         }
1581
1582         if (blocked) {
1583                 r = bus_verify_polkit_async(message, CAP_SYS_BOOT, action_ignore_inhibit, interactive, UID_INVALID, &m->polkit_registry, error);
1584                 if (r < 0)
1585                         return r;
1586                 if (r == 0)
1587                         return 1; /* No authorization for now, but the async polkit stuff will call us again when it has it */
1588         }
1589
1590         if (!multiple_sessions && !blocked) {
1591                 r = bus_verify_polkit_async(message, CAP_SYS_BOOT, action, interactive, UID_INVALID, &m->polkit_registry, error);
1592                 if (r < 0)
1593                         return r;
1594                 if (r == 0)
1595                         return 1; /* No authorization for now, but the async polkit stuff will call us again when it has it */
1596         }
1597
1598         r = bus_manager_shutdown_or_sleep_now_or_later(m, sleep_action, w, error);
1599         if (r < 0)
1600                 return r;
1601
1602         return sd_bus_reply_method_return(message, NULL);
1603 }
1604
1605 static int method_poweroff(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1606         Manager *m = userdata;
1607
1608         return method_do_shutdown_or_sleep(
1609                         m, message,
1610                         HANDLE_POWEROFF,
1611                         INHIBIT_SHUTDOWN,
1612                         "org.freedesktop.login1.power-off",
1613                         "org.freedesktop.login1.power-off-multiple-sessions",
1614                         "org.freedesktop.login1.power-off-ignore-inhibit",
1615                         NULL,
1616                         method_poweroff,
1617                         error);
1618 }
1619
1620 static int method_reboot(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1621         Manager *m = userdata;
1622
1623         return method_do_shutdown_or_sleep(
1624                         m, message,
1625                         HANDLE_REBOOT,
1626                         INHIBIT_SHUTDOWN,
1627                         "org.freedesktop.login1.reboot",
1628                         "org.freedesktop.login1.reboot-multiple-sessions",
1629                         "org.freedesktop.login1.reboot-ignore-inhibit",
1630                         NULL,
1631                         method_reboot,
1632                         error);
1633 }
1634
1635 static int method_suspend(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1636         Manager *m = userdata;
1637
1638         return method_do_shutdown_or_sleep(
1639                         m, message,
1640                         HANDLE_SUSPEND,
1641                         INHIBIT_SLEEP,
1642                         "org.freedesktop.login1.suspend",
1643                         "org.freedesktop.login1.suspend-multiple-sessions",
1644                         "org.freedesktop.login1.suspend-ignore-inhibit",
1645                         "suspend",
1646                         method_suspend,
1647                         error);
1648 }
1649
1650 static int method_hibernate(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1651         Manager *m = userdata;
1652
1653         return method_do_shutdown_or_sleep(
1654                         m, message,
1655                         HANDLE_HIBERNATE,
1656                         INHIBIT_SLEEP,
1657                         "org.freedesktop.login1.hibernate",
1658                         "org.freedesktop.login1.hibernate-multiple-sessions",
1659                         "org.freedesktop.login1.hibernate-ignore-inhibit",
1660                         "hibernate",
1661                         method_hibernate,
1662                         error);
1663 }
1664
1665 static int method_hybrid_sleep(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1666         Manager *m = userdata;
1667
1668         return method_do_shutdown_or_sleep(
1669                         m, message,
1670                         HANDLE_HYBRID_SLEEP,
1671                         INHIBIT_SLEEP,
1672                         "org.freedesktop.login1.hibernate",
1673                         "org.freedesktop.login1.hibernate-multiple-sessions",
1674                         "org.freedesktop.login1.hibernate-ignore-inhibit",
1675                         "hybrid-sleep",
1676                         method_hybrid_sleep,
1677                         error);
1678 }
1679
1680 static int method_can_shutdown_or_sleep(
1681                 Manager *m,
1682                 sd_bus_message *message,
1683                 InhibitWhat w,
1684                 const char *action,
1685                 const char *action_multiple_sessions,
1686                 const char *action_ignore_inhibit,
1687                 const char *sleep_verb,
1688                 sd_bus_error *error) {
1689
1690         _cleanup_bus_creds_unref_ sd_bus_creds *creds = NULL;
1691         bool multiple_sessions, challenge, blocked;
1692         const char *result = NULL;
1693         uid_t uid;
1694         int r;
1695
1696         assert(m);
1697         assert(message);
1698         assert(w >= 0);
1699         assert(w <= _INHIBIT_WHAT_MAX);
1700         assert(action);
1701         assert(action_multiple_sessions);
1702         assert(action_ignore_inhibit);
1703
1704         if (sleep_verb) {
1705                 r = can_sleep(sleep_verb);
1706                 if (r < 0)
1707                         return r;
1708                 if (r == 0)
1709                         return sd_bus_reply_method_return(message, "s", "na");
1710         }
1711
1712         r = sd_bus_query_sender_creds(message, SD_BUS_CREDS_EUID, &creds);
1713         if (r < 0)
1714                 return r;
1715
1716         r = sd_bus_creds_get_euid(creds, &uid);
1717         if (r < 0)
1718                 return r;
1719
1720         r = have_multiple_sessions(m, uid);
1721         if (r < 0)
1722                 return r;
1723
1724         multiple_sessions = r > 0;
1725         blocked = manager_is_inhibited(m, w, INHIBIT_BLOCK, NULL, false, true, uid, NULL);
1726
1727         if (multiple_sessions) {
1728                 r = bus_verify_polkit(message, CAP_SYS_BOOT, action_multiple_sessions, false, UID_INVALID, &challenge, error);
1729                 if (r < 0)
1730                         return r;
1731
1732                 if (r > 0)
1733                         result = "yes";
1734                 else if (challenge)
1735                         result = "challenge";
1736                 else
1737                         result = "no";
1738         }
1739
1740         if (blocked) {
1741                 r = bus_verify_polkit(message, CAP_SYS_BOOT, action_ignore_inhibit, false, UID_INVALID, &challenge, error);
1742                 if (r < 0)
1743                         return r;
1744
1745                 if (r > 0 && !result)
1746                         result = "yes";
1747                 else if (challenge && (!result || streq(result, "yes")))
1748                         result = "challenge";
1749                 else
1750                         result = "no";
1751         }
1752
1753         if (!multiple_sessions && !blocked) {
1754                 /* If neither inhibit nor multiple sessions
1755                  * apply then just check the normal policy */
1756
1757                 r = bus_verify_polkit(message, CAP_SYS_BOOT, action, false, UID_INVALID, &challenge, error);
1758                 if (r < 0)
1759                         return r;
1760
1761                 if (r > 0)
1762                         result = "yes";
1763                 else if (challenge)
1764                         result = "challenge";
1765                 else
1766                         result = "no";
1767         }
1768
1769         return sd_bus_reply_method_return(message, "s", result);
1770 }
1771
1772 static int method_can_poweroff(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1773         Manager *m = userdata;
1774
1775         return method_can_shutdown_or_sleep(
1776                         m, message,
1777                         INHIBIT_SHUTDOWN,
1778                         "org.freedesktop.login1.power-off",
1779                         "org.freedesktop.login1.power-off-multiple-sessions",
1780                         "org.freedesktop.login1.power-off-ignore-inhibit",
1781                         NULL,
1782                         error);
1783 }
1784
1785 static int method_can_reboot(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1786         Manager *m = userdata;
1787
1788         return method_can_shutdown_or_sleep(
1789                         m, message,
1790                         INHIBIT_SHUTDOWN,
1791                         "org.freedesktop.login1.reboot",
1792                         "org.freedesktop.login1.reboot-multiple-sessions",
1793                         "org.freedesktop.login1.reboot-ignore-inhibit",
1794                         NULL,
1795                         error);
1796 }
1797
1798 static int method_can_suspend(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1799         Manager *m = userdata;
1800
1801         return method_can_shutdown_or_sleep(
1802                         m, message,
1803                         INHIBIT_SLEEP,
1804                         "org.freedesktop.login1.suspend",
1805                         "org.freedesktop.login1.suspend-multiple-sessions",
1806                         "org.freedesktop.login1.suspend-ignore-inhibit",
1807                         "suspend",
1808                         error);
1809 }
1810
1811 static int method_can_hibernate(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1812         Manager *m = userdata;
1813
1814         return method_can_shutdown_or_sleep(
1815                         m, message,
1816                         INHIBIT_SLEEP,
1817                         "org.freedesktop.login1.hibernate",
1818                         "org.freedesktop.login1.hibernate-multiple-sessions",
1819                         "org.freedesktop.login1.hibernate-ignore-inhibit",
1820                         "hibernate",
1821                         error);
1822 }
1823
1824 static int method_can_hybrid_sleep(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1825         Manager *m = userdata;
1826
1827         return method_can_shutdown_or_sleep(
1828                         m, message,
1829                         INHIBIT_SLEEP,
1830                         "org.freedesktop.login1.hibernate",
1831                         "org.freedesktop.login1.hibernate-multiple-sessions",
1832                         "org.freedesktop.login1.hibernate-ignore-inhibit",
1833                         "hybrid-sleep",
1834                         error);
1835 }
1836
1837 static int method_inhibit(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *error) {
1838         _cleanup_bus_creds_unref_ sd_bus_creds *creds = NULL;
1839         const char *who, *why, *what, *mode;
1840         _cleanup_free_ char *id = NULL;
1841         _cleanup_close_ int fifo_fd = -1;
1842         Manager *m = userdata;
1843         Inhibitor *i = NULL;
1844         InhibitMode mm;
1845         InhibitWhat w;
1846         pid_t pid;
1847         uid_t uid;
1848         int r;
1849
1850         assert(bus);
1851         assert(message);
1852         assert(m);
1853
1854         r = sd_bus_message_read(message, "ssss", &what, &who, &why, &mode);
1855         if (r < 0)
1856                 return r;
1857
1858         w = inhibit_what_from_string(what);
1859         if (w <= 0)
1860                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Invalid what specification %s", what);
1861
1862         mm = inhibit_mode_from_string(mode);
1863         if (mm < 0)
1864                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Invalid mode specification %s", mode);
1865
1866         /* Delay is only supported for shutdown/sleep */
1867         if (mm == INHIBIT_DELAY && (w & ~(INHIBIT_SHUTDOWN|INHIBIT_SLEEP)))
1868                 return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Delay inhibitors only supported for shutdown and sleep");
1869
1870         /* Don't allow taking delay locks while we are already
1871          * executing the operation. We shouldn't create the impression
1872          * that the lock was successful if the machine is about to go
1873          * down/suspend any moment. */
1874         if (m->action_what & w)
1875                 return sd_bus_error_setf(error, BUS_ERROR_OPERATION_IN_PROGRESS, "The operation inhibition has been requested for is already running");
1876
1877         r = bus_verify_polkit_async(
1878                         message,
1879                         CAP_SYS_BOOT,
1880                         w == INHIBIT_SHUTDOWN             ? (mm == INHIBIT_BLOCK ? "org.freedesktop.login1.inhibit-block-shutdown" : "org.freedesktop.login1.inhibit-delay-shutdown") :
1881                         w == INHIBIT_SLEEP                ? (mm == INHIBIT_BLOCK ? "org.freedesktop.login1.inhibit-block-sleep"    : "org.freedesktop.login1.inhibit-delay-sleep") :
1882                         w == INHIBIT_IDLE                 ? "org.freedesktop.login1.inhibit-block-idle" :
1883                         w == INHIBIT_HANDLE_POWER_KEY     ? "org.freedesktop.login1.inhibit-handle-power-key" :
1884                         w == INHIBIT_HANDLE_SUSPEND_KEY   ? "org.freedesktop.login1.inhibit-handle-suspend-key" :
1885                         w == INHIBIT_HANDLE_HIBERNATE_KEY ? "org.freedesktop.login1.inhibit-handle-hibernate-key" :
1886                                                             "org.freedesktop.login1.inhibit-handle-lid-switch",
1887                         false,
1888                         UID_INVALID,
1889                         &m->polkit_registry,
1890                         error);
1891         if (r < 0)
1892                 return r;
1893         if (r == 0)
1894                 return 1; /* No authorization for now, but the async polkit stuff will call us again when it has it */
1895
1896         r = sd_bus_query_sender_creds(message, SD_BUS_CREDS_EUID|SD_BUS_CREDS_PID, &creds);
1897         if (r < 0)
1898                 return r;
1899
1900         r = sd_bus_creds_get_euid(creds, &uid);
1901         if (r < 0)
1902                 return r;
1903
1904         r = sd_bus_creds_get_pid(creds, &pid);
1905         if (r < 0)
1906                 return r;
1907
1908         do {
1909                 free(id);
1910                 id = NULL;
1911
1912                 if (asprintf(&id, "%lu", ++m->inhibit_counter) < 0)
1913                         return -ENOMEM;
1914
1915         } while (hashmap_get(m->inhibitors, id));
1916
1917         r = manager_add_inhibitor(m, id, &i);
1918         if (r < 0)
1919                 return r;
1920
1921         i->what = w;
1922         i->mode = mm;
1923         i->pid = pid;
1924         i->uid = uid;
1925         i->why = strdup(why);
1926         i->who = strdup(who);
1927
1928         if (!i->why || !i->who) {
1929                 r = -ENOMEM;
1930                 goto fail;
1931         }
1932
1933         fifo_fd = inhibitor_create_fifo(i);
1934         if (fifo_fd < 0) {
1935                 r = fifo_fd;
1936                 goto fail;
1937         }
1938
1939         inhibitor_start(i);
1940
1941         return sd_bus_reply_method_return(message, "h", fifo_fd);
1942
1943 fail:
1944         if (i)
1945                 inhibitor_free(i);
1946
1947         return r;
1948 }
1949
1950 const sd_bus_vtable manager_vtable[] = {
1951         SD_BUS_VTABLE_START(0),
1952
1953         SD_BUS_PROPERTY("KillOnlyUsers", "as", NULL, offsetof(Manager, kill_only_users), SD_BUS_VTABLE_PROPERTY_CONST),
1954         SD_BUS_PROPERTY("KillExcludeUsers", "as", NULL, offsetof(Manager, kill_exclude_users), SD_BUS_VTABLE_PROPERTY_CONST),
1955         SD_BUS_PROPERTY("KillUserProcesses", "b", NULL, offsetof(Manager, kill_user_processes), SD_BUS_VTABLE_PROPERTY_CONST),
1956         SD_BUS_PROPERTY("IdleHint", "b", property_get_idle_hint, 0, SD_BUS_VTABLE_PROPERTY_EMITS_CHANGE),
1957         SD_BUS_PROPERTY("IdleSinceHint", "t", property_get_idle_since_hint, 0, SD_BUS_VTABLE_PROPERTY_EMITS_CHANGE),
1958         SD_BUS_PROPERTY("IdleSinceHintMonotonic", "t", property_get_idle_since_hint, 0, SD_BUS_VTABLE_PROPERTY_EMITS_CHANGE),
1959         SD_BUS_PROPERTY("BlockInhibited", "s", property_get_inhibited, 0, SD_BUS_VTABLE_PROPERTY_EMITS_CHANGE),
1960         SD_BUS_PROPERTY("DelayInhibited", "s", property_get_inhibited, 0, SD_BUS_VTABLE_PROPERTY_EMITS_CHANGE),
1961         SD_BUS_PROPERTY("InhibitDelayMaxUSec", "t", NULL, offsetof(Manager, inhibit_delay_max), SD_BUS_VTABLE_PROPERTY_CONST),
1962         SD_BUS_PROPERTY("HandlePowerKey", "s", property_get_handle_action, offsetof(Manager, handle_power_key), SD_BUS_VTABLE_PROPERTY_CONST),
1963         SD_BUS_PROPERTY("HandleSuspendKey", "s", property_get_handle_action, offsetof(Manager, handle_suspend_key), SD_BUS_VTABLE_PROPERTY_CONST),
1964         SD_BUS_PROPERTY("HandleHibernateKey", "s", property_get_handle_action, offsetof(Manager, handle_hibernate_key), SD_BUS_VTABLE_PROPERTY_CONST),
1965         SD_BUS_PROPERTY("HandleLidSwitch", "s", property_get_handle_action, offsetof(Manager, handle_lid_switch), SD_BUS_VTABLE_PROPERTY_CONST),
1966         SD_BUS_PROPERTY("HandleLidSwitchDocked", "s", property_get_handle_action, offsetof(Manager, handle_lid_switch_docked), SD_BUS_VTABLE_PROPERTY_CONST),
1967         SD_BUS_PROPERTY("HoldoffTimeoutUSec", "t", NULL, offsetof(Manager, holdoff_timeout_usec), SD_BUS_VTABLE_PROPERTY_CONST),
1968         SD_BUS_PROPERTY("IdleAction", "s", property_get_handle_action, offsetof(Manager, idle_action), SD_BUS_VTABLE_PROPERTY_CONST),
1969         SD_BUS_PROPERTY("IdleActionUSec", "t", NULL, offsetof(Manager, idle_action_usec), SD_BUS_VTABLE_PROPERTY_CONST),
1970         SD_BUS_PROPERTY("PreparingForShutdown", "b", property_get_preparing, 0, 0),
1971         SD_BUS_PROPERTY("PreparingForSleep", "b", property_get_preparing, 0, 0),
1972
1973         SD_BUS_METHOD("GetSession", "s", "o", method_get_session, SD_BUS_VTABLE_UNPRIVILEGED),
1974         SD_BUS_METHOD("GetSessionByPID", "u", "o", method_get_session_by_pid, SD_BUS_VTABLE_UNPRIVILEGED),
1975         SD_BUS_METHOD("GetUser", "u", "o", method_get_user, SD_BUS_VTABLE_UNPRIVILEGED),
1976         SD_BUS_METHOD("GetUserByPID", "u", "o", method_get_user_by_pid, SD_BUS_VTABLE_UNPRIVILEGED),
1977         SD_BUS_METHOD("GetSeat", "s", "o", method_get_seat, SD_BUS_VTABLE_UNPRIVILEGED),
1978         SD_BUS_METHOD("ListSessions", NULL, "a(susso)", method_list_sessions, SD_BUS_VTABLE_UNPRIVILEGED),
1979         SD_BUS_METHOD("ListUsers", NULL, "a(uso)", method_list_users, SD_BUS_VTABLE_UNPRIVILEGED),
1980         SD_BUS_METHOD("ListSeats", NULL, "a(so)", method_list_seats, SD_BUS_VTABLE_UNPRIVILEGED),
1981         SD_BUS_METHOD("ListInhibitors", NULL, "a(ssssuu)", method_list_inhibitors, SD_BUS_VTABLE_UNPRIVILEGED),
1982         SD_BUS_METHOD("CreateSession", "uusssssussbssa(sv)", "soshusub", method_create_session, 0),
1983         SD_BUS_METHOD("ReleaseSession", "s", NULL, method_release_session, 0),
1984         SD_BUS_METHOD("ActivateSession", "s", NULL, method_activate_session, SD_BUS_VTABLE_UNPRIVILEGED),
1985         SD_BUS_METHOD("ActivateSessionOnSeat", "ss", NULL, method_activate_session_on_seat, SD_BUS_VTABLE_UNPRIVILEGED),
1986         SD_BUS_METHOD("LockSession", "s", NULL, method_lock_session, SD_BUS_VTABLE_UNPRIVILEGED),
1987         SD_BUS_METHOD("UnlockSession", "s", NULL, method_lock_session, SD_BUS_VTABLE_UNPRIVILEGED),
1988         SD_BUS_METHOD("LockSessions", NULL, NULL, method_lock_sessions, SD_BUS_VTABLE_UNPRIVILEGED),
1989         SD_BUS_METHOD("UnlockSessions", NULL, NULL, method_lock_sessions, SD_BUS_VTABLE_UNPRIVILEGED),
1990         SD_BUS_METHOD("KillSession", "ssi", NULL, method_kill_session, SD_BUS_VTABLE_UNPRIVILEGED),
1991         SD_BUS_METHOD("KillUser", "ui", NULL, method_kill_user, SD_BUS_VTABLE_UNPRIVILEGED),
1992         SD_BUS_METHOD("TerminateSession", "s", NULL, method_terminate_session, SD_BUS_VTABLE_UNPRIVILEGED),
1993         SD_BUS_METHOD("TerminateUser", "u", NULL, method_terminate_user, SD_BUS_VTABLE_UNPRIVILEGED),
1994         SD_BUS_METHOD("TerminateSeat", "s", NULL, method_terminate_seat, SD_BUS_VTABLE_UNPRIVILEGED),
1995         SD_BUS_METHOD("SetUserLinger", "ubb", NULL, method_set_user_linger, SD_BUS_VTABLE_UNPRIVILEGED),
1996         SD_BUS_METHOD("AttachDevice", "ssb", NULL, method_attach_device, SD_BUS_VTABLE_UNPRIVILEGED),
1997         SD_BUS_METHOD("FlushDevices", "b", NULL, method_flush_devices, SD_BUS_VTABLE_UNPRIVILEGED),
1998         SD_BUS_METHOD("PowerOff", "b", NULL, method_poweroff, SD_BUS_VTABLE_UNPRIVILEGED),
1999         SD_BUS_METHOD("Reboot", "b", NULL, method_reboot, SD_BUS_VTABLE_UNPRIVILEGED),
2000         SD_BUS_METHOD("Suspend", "b", NULL, method_suspend, SD_BUS_VTABLE_UNPRIVILEGED),
2001         SD_BUS_METHOD("Hibernate", "b", NULL, method_hibernate, SD_BUS_VTABLE_UNPRIVILEGED),
2002         SD_BUS_METHOD("HybridSleep", "b", NULL, method_hybrid_sleep, SD_BUS_VTABLE_UNPRIVILEGED),
2003         SD_BUS_METHOD("CanPowerOff", NULL, "s", method_can_poweroff, SD_BUS_VTABLE_UNPRIVILEGED),
2004         SD_BUS_METHOD("CanReboot", NULL, "s", method_can_reboot, SD_BUS_VTABLE_UNPRIVILEGED),
2005         SD_BUS_METHOD("CanSuspend", NULL, "s", method_can_suspend, SD_BUS_VTABLE_UNPRIVILEGED),
2006         SD_BUS_METHOD("CanHibernate", NULL, "s", method_can_hibernate, SD_BUS_VTABLE_UNPRIVILEGED),
2007         SD_BUS_METHOD("CanHybridSleep", NULL, "s", method_can_hybrid_sleep, SD_BUS_VTABLE_UNPRIVILEGED),
2008         SD_BUS_METHOD("Inhibit", "ssss", "h", method_inhibit, SD_BUS_VTABLE_UNPRIVILEGED),
2009
2010         SD_BUS_SIGNAL("SessionNew", "so", 0),
2011         SD_BUS_SIGNAL("SessionRemoved", "so", 0),
2012         SD_BUS_SIGNAL("UserNew", "uo", 0),
2013         SD_BUS_SIGNAL("UserRemoved", "uo", 0),
2014         SD_BUS_SIGNAL("SeatNew", "so", 0),
2015         SD_BUS_SIGNAL("SeatRemoved", "so", 0),
2016         SD_BUS_SIGNAL("PrepareForShutdown", "b", 0),
2017         SD_BUS_SIGNAL("PrepareForSleep", "b", 0),
2018
2019         SD_BUS_VTABLE_END
2020 };
2021
2022 int manager_send_changed(Manager *manager, const char *property, ...) {
2023         char **l;
2024
2025         assert(manager);
2026
2027         l = strv_from_stdarg_alloca(property);
2028
2029         return sd_bus_emit_properties_changed_strv(
2030                         manager->bus,
2031                         "/org/freedesktop/login1",
2032                         "org.freedesktop.login1.Manager",
2033                         l);
2034 }
2035
2036 int manager_dispatch_delayed(Manager *manager) {
2037         _cleanup_bus_error_free_ sd_bus_error error = SD_BUS_ERROR_NULL;
2038         Inhibitor *offending = NULL;
2039         int r;
2040
2041         assert(manager);
2042
2043         if (manager->action_what == 0)
2044                 return 0;
2045
2046         /* Continue delay? */
2047         if (manager_is_inhibited(manager, manager->action_what, INHIBIT_DELAY, NULL, false, false, 0, &offending)) {
2048                 _cleanup_free_ char *comm = NULL, *u = NULL;
2049
2050                 get_process_comm(offending->pid, &comm);
2051                 u = uid_to_name(offending->uid);
2052
2053                 if (manager->action_timestamp + manager->inhibit_delay_max > now(CLOCK_MONOTONIC))
2054                         return 0;
2055
2056                 log_info("Delay lock is active (UID "UID_FMT"/%s, PID "PID_FMT"/%s) but inhibitor timeout is reached.",
2057                          offending->uid, strna(u),
2058                          offending->pid, strna(comm));
2059         }
2060
2061         /* Actually do the operation */
2062         r = execute_shutdown_or_sleep(manager, manager->action_what, manager->pending_action, &error);
2063         if (r < 0) {
2064                 log_warning("Failed to send delayed message: %s", bus_error_message(&error, r));
2065
2066                 manager->pending_action = HANDLE_IGNORE;
2067                 manager->action_what = 0;
2068                 return r;
2069         }
2070
2071         return 1;
2072 }