X-Git-Url: http://www.chiark.greenend.org.uk/ucgi/~ianmdlvl/git?p=elogind.git;a=blobdiff_plain;f=src%2Flogin%2Flogind-core.c;h=107b3243a5a1701f1e2ac9ed017eaaf9dd0aa740;hp=b8d03c3a59f3dcbd0c02198204759466e214b518;hb=16ffa6bfe836f9b0fa5f1dd10d9cc774b9955a0b;hpb=6a79c58603ea816a1b4fa1520397b4e138bc1ca0 diff --git a/src/login/logind-core.c b/src/login/logind-core.c index b8d03c3a5..107b3243a 100644 --- a/src/login/logind-core.c +++ b/src/login/logind-core.c @@ -20,20 +20,18 @@ ***/ #include -#include #include #include #include -#include #include #include "strv.h" #include "cgroup-util.h" -#include "audit.h" #include "bus-util.h" #include "bus-error.h" #include "udev-util.h" #include "logind.h" +#include "terminal-util.h" int manager_add_device(Manager *m, const char *sysfs, bool master, Device **_device) { Device *d; @@ -42,20 +40,15 @@ int manager_add_device(Manager *m, const char *sysfs, bool master, Device **_dev assert(sysfs); d = hashmap_get(m->devices, sysfs); - if (d) { - if (_device) - *_device = d; - + if (d) /* we support adding master-flags, but not removing them */ d->master = d->master || master; - - return 0; + else { + d = device_new(m, sysfs, master); + if (!d) + return -ENOMEM; } - d = device_new(m, sysfs, master); - if (!d) - return -ENOMEM; - if (_device) *_device = d; @@ -69,17 +62,12 @@ int manager_add_seat(Manager *m, const char *id, Seat **_seat) { assert(id); s = hashmap_get(m->seats, id); - if (s) { - if (_seat) - *_seat = s; - - return 0; + if (!s) { + s = seat_new(m, id); + if (!s) + return -ENOMEM; } - s = seat_new(m, id); - if (!s) - return -ENOMEM; - if (_seat) *_seat = s; @@ -93,17 +81,12 @@ int manager_add_session(Manager *m, const char *id, Session **_session) { assert(id); s = hashmap_get(m->sessions, id); - if (s) { - if (_session) - *_session = s; - - return 0; + if (!s) { + s = session_new(m, id); + if (!s) + return -ENOMEM; } - s = session_new(m, id); - if (!s) - return -ENOMEM; - if (_session) *_session = s; @@ -116,18 +99,13 @@ int manager_add_user(Manager *m, uid_t uid, gid_t gid, const char *name, User ** assert(m); assert(name); - u = hashmap_get(m->users, ULONG_TO_PTR((unsigned long) uid)); - if (u) { - if (_user) - *_user = u; - - return 0; + u = hashmap_get(m->users, UID_TO_PTR(uid)); + if (!u) { + u = user_new(m, uid, gid, name); + if (!u) + return -ENOMEM; } - u = user_new(m, uid, gid, name); - if (!u) - return -ENOMEM; - if (_user) *_user = u; @@ -193,61 +171,18 @@ int manager_add_button(Manager *m, const char *name, Button **_button) { assert(name); b = hashmap_get(m->buttons, name); - if (b) { - if (_button) - *_button = b; - - return 0; + if (!b) { + b = button_new(m, name); + if (!b) + return -ENOMEM; } - b = button_new(m, name); - if (!b) - return -ENOMEM; - if (_button) *_button = b; return 0; } -int manager_watch_busname(Manager *m, const char *name) { - char *n; - int r; - - assert(m); - assert(name); - - if (set_get(m->busnames, (char*) name)) - return 0; - - n = strdup(name); - if (!n) - return -ENOMEM; - - r = set_put(m->busnames, n); - if (r < 0) { - free(n); - return r; - } - - return 0; -} - -void manager_drop_busname(Manager *m, const char *name) { - Session *session; - Iterator i; - - assert(m); - assert(name); - - /* keep it if the name still owns a controller */ - HASHMAP_FOREACH(session, m->sessions, i) - if (session_is_controller(session, name)) - return; - - free(set_remove(m->busnames, (char*) name)); -} - int manager_process_seat_device(Manager *m, struct udev_device *d) { Device *device; int r; @@ -441,7 +376,8 @@ bool manager_shall_kill(Manager *m, const char *user) { static int vt_is_busy(unsigned int vtnr) { struct vt_stat vt_stat; - int r = 0, fd; + int r = 0; + _cleanup_close_ int fd; assert(vtnr >= 1); @@ -460,14 +396,12 @@ static int vt_is_busy(unsigned int vtnr) { else r = !!(vt_stat.v_state & (1 << vtnr)); - close_nointr_nofail(fd); - return r; } int manager_spawn_autovt(Manager *m, unsigned int vtnr) { _cleanup_bus_error_free_ sd_bus_error error = SD_BUS_ERROR_NULL; - _cleanup_free_ char *name = NULL; + char name[sizeof("autovt@tty.service") + DECIMAL_STR_MAX(unsigned int)]; int r; assert(m); @@ -489,9 +423,7 @@ int manager_spawn_autovt(Manager *m, unsigned int vtnr) { return -EBUSY; } - if (asprintf(&name, "autovt@tty%u.service", vtnr) < 0) - return log_oom(); - + snprintf(name, sizeof(name), "autovt@tty%u.service", vtnr); r = sd_bus_call_method( m->bus, "org.freedesktop.systemd1", @@ -548,7 +480,7 @@ int manager_count_displays(Manager *m) { p = udev_device_get_parent(d); if (!p) - return -ENOMEM; + continue; /* If the parent shares the same subsystem as the * device we are looking at then it is a connector, @@ -565,3 +497,25 @@ int manager_count_displays(Manager *m) { return n; } + +bool manager_is_docked_or_multiple_displays(Manager *m) { + int n; + + /* If we are docked don't react to lid closing */ + if (manager_is_docked(m)) { + log_debug("System is docked."); + return true; + } + + /* If we have more than one display connected, + * assume that we are docked. */ + n = manager_count_displays(m); + if (n < 0) + log_warning_errno(n, "Display counting failed: %m"); + else if (n > 1) { + log_debug("Multiple (%i) displays connected.", n); + return true; + } + + return false; +}