mirror of
https://github.com/systemd/systemd-stable.git
synced 2024-12-24 21:34:08 +03:00
parent
23cff6d4fe
commit
2aaf565a2d
@ -134,6 +134,7 @@ int home_new(Manager *m, UserRecord *hr, const char *sysfs, Home **ret) {
|
|||||||
.sysfs = TAKE_PTR(ns),
|
.sysfs = TAKE_PTR(ns),
|
||||||
.signed_locally = -1,
|
.signed_locally = -1,
|
||||||
.pin_fd = -1,
|
.pin_fd = -1,
|
||||||
|
.luks_lock_fd = -1,
|
||||||
};
|
};
|
||||||
|
|
||||||
r = hashmap_put(m->homes_by_name, home->user_name, home);
|
r = hashmap_put(m->homes_by_name, home->user_name, home);
|
||||||
@ -208,6 +209,7 @@ Home *home_free(Home *h) {
|
|||||||
h->current_operation = operation_unref(h->current_operation);
|
h->current_operation = operation_unref(h->current_operation);
|
||||||
|
|
||||||
safe_close(h->pin_fd);
|
safe_close(h->pin_fd);
|
||||||
|
safe_close(h->luks_lock_fd);
|
||||||
|
|
||||||
h->retry_deactivate_event_source = sd_event_source_disable_unref(h->retry_deactivate_event_source);
|
h->retry_deactivate_event_source = sd_event_source_disable_unref(h->retry_deactivate_event_source);
|
||||||
|
|
||||||
@ -367,6 +369,23 @@ static void home_update_pin_fd(Home *h, HomeState state) {
|
|||||||
return HOME_STATE_SHALL_PIN(state) ? home_pin(h) : home_unpin(h);
|
return HOME_STATE_SHALL_PIN(state) ? home_pin(h) : home_unpin(h);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void home_maybe_close_luks_lock_fd(Home *h, HomeState state) {
|
||||||
|
assert(h);
|
||||||
|
|
||||||
|
if (h->luks_lock_fd < 0)
|
||||||
|
return;
|
||||||
|
|
||||||
|
if (state < 0)
|
||||||
|
state = home_get_state(h);
|
||||||
|
|
||||||
|
/* Keep the lock as long as the home dir is active or has some operation going */
|
||||||
|
if (HOME_STATE_IS_EXECUTING_OPERATION(state) || HOME_STATE_IS_ACTIVE(state) || state == HOME_LOCKED)
|
||||||
|
return;
|
||||||
|
|
||||||
|
h->luks_lock_fd = safe_close(h->luks_lock_fd);
|
||||||
|
log_debug("Successfully closed LUKS backing file lock for %s.", h->user_name);
|
||||||
|
}
|
||||||
|
|
||||||
static void home_maybe_stop_retry_deactivate(Home *h, HomeState state) {
|
static void home_maybe_stop_retry_deactivate(Home *h, HomeState state) {
|
||||||
assert(h);
|
assert(h);
|
||||||
|
|
||||||
@ -458,6 +477,7 @@ static void home_set_state(Home *h, HomeState state) {
|
|||||||
home_state_to_string(new_state));
|
home_state_to_string(new_state));
|
||||||
|
|
||||||
home_update_pin_fd(h, new_state);
|
home_update_pin_fd(h, new_state);
|
||||||
|
home_maybe_close_luks_lock_fd(h, new_state);
|
||||||
home_maybe_stop_retry_deactivate(h, new_state);
|
home_maybe_stop_retry_deactivate(h, new_state);
|
||||||
|
|
||||||
if (HOME_STATE_IS_EXECUTING_OPERATION(old_state) && !HOME_STATE_IS_EXECUTING_OPERATION(new_state)) {
|
if (HOME_STATE_IS_EXECUTING_OPERATION(old_state) && !HOME_STATE_IS_EXECUTING_OPERATION(new_state)) {
|
||||||
@ -612,6 +632,8 @@ static int convert_worker_errno(Home *h, int e, sd_bus_error *error) {
|
|||||||
return sd_bus_error_setf(error, BUS_ERROR_NO_DISK_SPACE, "Not enough disk space for home %s", h->user_name);
|
return sd_bus_error_setf(error, BUS_ERROR_NO_DISK_SPACE, "Not enough disk space for home %s", h->user_name);
|
||||||
case -EKEYREVOKED:
|
case -EKEYREVOKED:
|
||||||
return sd_bus_error_setf(error, BUS_ERROR_HOME_CANT_AUTHENTICATE, "Home %s has no password or other authentication mechanism defined.", h->user_name);
|
return sd_bus_error_setf(error, BUS_ERROR_HOME_CANT_AUTHENTICATE, "Home %s has no password or other authentication mechanism defined.", h->user_name);
|
||||||
|
case -EADDRINUSE:
|
||||||
|
return sd_bus_error_setf(error, BUS_ERROR_HOME_IN_USE, "Home %s is currently being used elsewhere.", h->user_name);
|
||||||
}
|
}
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
@ -1158,6 +1180,12 @@ static int home_start_work(Home *h, const char *verb, UserRecord *hr, UserRecord
|
|||||||
_exit(EXIT_FAILURE);
|
_exit(EXIT_FAILURE);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* If we haven't locked the device yet, ask for a lock to be taken and be passed back to us via sd_notify(). */
|
||||||
|
if (setenv("SYSTEMD_LUKS_LOCK", one_zero(h->luks_lock_fd < 0), 1) < 0) {
|
||||||
|
log_error_errno(errno, "Failed to set $SYSTEMD_LUKS_LOCK: %m");
|
||||||
|
_exit(EXIT_FAILURE);
|
||||||
|
}
|
||||||
|
|
||||||
if (h->manager->default_storage >= 0)
|
if (h->manager->default_storage >= 0)
|
||||||
if (setenv("SYSTEMD_HOME_DEFAULT_STORAGE", user_storage_to_string(h->manager->default_storage), 1) < 0) {
|
if (setenv("SYSTEMD_HOME_DEFAULT_STORAGE", user_storage_to_string(h->manager->default_storage), 1) < 0) {
|
||||||
log_error_errno(errno, "Failed to set $SYSTEMD_HOME_DEFAULT_STORAGE: %m");
|
log_error_errno(errno, "Failed to set $SYSTEMD_HOME_DEFAULT_STORAGE: %m");
|
||||||
@ -1957,28 +1985,49 @@ HomeState home_get_state(Home *h) {
|
|||||||
return HOME_INACTIVE;
|
return HOME_INACTIVE;
|
||||||
}
|
}
|
||||||
|
|
||||||
void home_process_notify(Home *h, char **l) {
|
void home_process_notify(Home *h, char **l, int fd) {
|
||||||
|
_cleanup_close_ int taken_fd = TAKE_FD(fd);
|
||||||
const char *e;
|
const char *e;
|
||||||
int error;
|
int error;
|
||||||
int r;
|
int r;
|
||||||
|
|
||||||
assert(h);
|
assert(h);
|
||||||
|
|
||||||
e = strv_env_get(l, "ERRNO");
|
e = strv_env_get(l, "SYSTEMD_LUKS_LOCK_FD");
|
||||||
if (!e) {
|
if (e) {
|
||||||
log_debug("Got notify message lacking ERRNO= field, ignoring.");
|
r = parse_boolean(e);
|
||||||
|
if (r < 0)
|
||||||
|
return (void) log_debug_errno(r, "Failed to parse SYSTEMD_LUKS_LOCK_FD value: %m");
|
||||||
|
if (r > 0) {
|
||||||
|
if (taken_fd < 0)
|
||||||
|
return (void) log_debug("Got notify message with SYSTEMD_LUKS_LOCK_FD=1 but no fd passed, ignoring: %m");
|
||||||
|
|
||||||
|
safe_close(h->luks_lock_fd);
|
||||||
|
h->luks_lock_fd = TAKE_FD(taken_fd);
|
||||||
|
|
||||||
|
log_debug("Successfully acquired LUKS lock fd from worker.");
|
||||||
|
|
||||||
|
/* Immediately check if we actually want to keep it */
|
||||||
|
home_maybe_close_luks_lock_fd(h, _HOME_STATE_INVALID);
|
||||||
|
} else {
|
||||||
|
if (taken_fd >= 0)
|
||||||
|
return (void) log_debug("Got notify message with SYSTEMD_LUKS_LOCK_FD=0 but fd passed, ignoring: %m");
|
||||||
|
|
||||||
|
h->luks_lock_fd = safe_close(h->luks_lock_fd);
|
||||||
|
}
|
||||||
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
e = strv_env_get(l, "ERRNO");
|
||||||
|
if (!e)
|
||||||
|
return (void) log_debug("Got notify message lacking both ERRNO= and SYSTEMD_LUKS_LOCK_FD= field, ignoring.");
|
||||||
|
|
||||||
r = safe_atoi(e, &error);
|
r = safe_atoi(e, &error);
|
||||||
if (r < 0) {
|
if (r < 0)
|
||||||
log_debug_errno(r, "Failed to parse received error number, ignoring: %s", e);
|
return (void) log_debug_errno(r, "Failed to parse received error number, ignoring: %s", e);
|
||||||
return;
|
if (error <= 0)
|
||||||
}
|
return (void) log_debug("Error number is out of range: %i", error);
|
||||||
if (error <= 0) {
|
|
||||||
log_debug("Error number is out of range: %i", error);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
h->worker_error_code = error;
|
h->worker_error_code = error;
|
||||||
}
|
}
|
||||||
|
@ -161,6 +161,9 @@ struct Home {
|
|||||||
|
|
||||||
/* A time event used to repeatedly try to unmount home dir after use if it didn't work on first try */
|
/* A time event used to repeatedly try to unmount home dir after use if it didn't work on first try */
|
||||||
sd_event_source *retry_deactivate_event_source;
|
sd_event_source *retry_deactivate_event_source;
|
||||||
|
|
||||||
|
/* An fd that locks the backing file of LUKS home dirs with a BSD lock. */
|
||||||
|
int luks_lock_fd;
|
||||||
};
|
};
|
||||||
|
|
||||||
int home_new(Manager *m, UserRecord *hr, const char *sysfs, Home **ret);
|
int home_new(Manager *m, UserRecord *hr, const char *sysfs, Home **ret);
|
||||||
@ -187,7 +190,7 @@ int home_unlock(Home *h, UserRecord *secret, sd_bus_error *error);
|
|||||||
|
|
||||||
HomeState home_get_state(Home *h);
|
HomeState home_get_state(Home *h);
|
||||||
|
|
||||||
void home_process_notify(Home *h, char **l);
|
void home_process_notify(Home *h, char **l, int fd);
|
||||||
|
|
||||||
int home_killall(Home *h);
|
int home_killall(Home *h);
|
||||||
|
|
||||||
|
@ -1010,13 +1010,25 @@ static int manager_bind_varlink(Manager *m) {
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static ssize_t read_datagram(int fd, struct ucred *ret_sender, void **ret) {
|
static ssize_t read_datagram(
|
||||||
|
int fd,
|
||||||
|
struct ucred *ret_sender,
|
||||||
|
void **ret,
|
||||||
|
int *ret_passed_fd) {
|
||||||
|
|
||||||
|
CMSG_BUFFER_TYPE(CMSG_SPACE(sizeof(struct ucred)) + CMSG_SPACE(sizeof(int))) control;
|
||||||
_cleanup_free_ void *buffer = NULL;
|
_cleanup_free_ void *buffer = NULL;
|
||||||
|
_cleanup_close_ int passed_fd = -1;
|
||||||
|
struct ucred *sender = NULL;
|
||||||
|
struct cmsghdr *cmsg;
|
||||||
|
struct msghdr mh;
|
||||||
|
struct iovec iov;
|
||||||
ssize_t n, m;
|
ssize_t n, m;
|
||||||
|
|
||||||
assert(fd >= 0);
|
assert(fd >= 0);
|
||||||
assert(ret_sender);
|
assert(ret_sender);
|
||||||
assert(ret);
|
assert(ret);
|
||||||
|
assert(ret_passed_fd);
|
||||||
|
|
||||||
n = next_datagram_size_fd(fd);
|
n = next_datagram_size_fd(fd);
|
||||||
if (n < 0)
|
if (n < 0)
|
||||||
@ -1026,58 +1038,54 @@ static ssize_t read_datagram(int fd, struct ucred *ret_sender, void **ret) {
|
|||||||
if (!buffer)
|
if (!buffer)
|
||||||
return -ENOMEM;
|
return -ENOMEM;
|
||||||
|
|
||||||
if (ret_sender) {
|
/* Pass one extra byte, as a size check */
|
||||||
CMSG_BUFFER_TYPE(CMSG_SPACE(sizeof(struct ucred))) control;
|
iov = IOVEC_MAKE(buffer, n + 1);
|
||||||
bool found_ucred = false;
|
|
||||||
struct cmsghdr *cmsg;
|
|
||||||
struct msghdr mh;
|
|
||||||
struct iovec iov;
|
|
||||||
|
|
||||||
/* Pass one extra byte, as a size check */
|
mh = (struct msghdr) {
|
||||||
iov = IOVEC_MAKE(buffer, n + 1);
|
.msg_iov = &iov,
|
||||||
|
.msg_iovlen = 1,
|
||||||
|
.msg_control = &control,
|
||||||
|
.msg_controllen = sizeof(control),
|
||||||
|
};
|
||||||
|
|
||||||
mh = (struct msghdr) {
|
m = recvmsg_safe(fd, &mh, MSG_DONTWAIT|MSG_CMSG_CLOEXEC);
|
||||||
.msg_iov = &iov,
|
if (m < 0)
|
||||||
.msg_iovlen = 1,
|
return m;
|
||||||
.msg_control = &control,
|
|
||||||
.msg_controllen = sizeof(control),
|
|
||||||
};
|
|
||||||
|
|
||||||
m = recvmsg_safe(fd, &mh, MSG_DONTWAIT|MSG_CMSG_CLOEXEC);
|
|
||||||
if (m < 0)
|
|
||||||
return m;
|
|
||||||
|
|
||||||
|
/* Ensure the size matches what we determined before */
|
||||||
|
if (m != n) {
|
||||||
cmsg_close_all(&mh);
|
cmsg_close_all(&mh);
|
||||||
|
return -EMSGSIZE;
|
||||||
|
}
|
||||||
|
|
||||||
/* Ensure the size matches what we determined before */
|
CMSG_FOREACH(cmsg, &mh) {
|
||||||
if (m != n)
|
if (cmsg->cmsg_level == SOL_SOCKET &&
|
||||||
return -EMSGSIZE;
|
cmsg->cmsg_type == SCM_CREDENTIALS &&
|
||||||
|
cmsg->cmsg_len == CMSG_LEN(sizeof(struct ucred))) {
|
||||||
|
assert(!sender);
|
||||||
|
sender = (struct ucred*) CMSG_DATA(cmsg);
|
||||||
|
}
|
||||||
|
|
||||||
CMSG_FOREACH(cmsg, &mh)
|
if (cmsg->cmsg_level == SOL_SOCKET &&
|
||||||
if (cmsg->cmsg_level == SOL_SOCKET &&
|
cmsg->cmsg_type == SCM_RIGHTS) {
|
||||||
cmsg->cmsg_type == SCM_CREDENTIALS &&
|
|
||||||
cmsg->cmsg_len == CMSG_LEN(sizeof(struct ucred))) {
|
|
||||||
|
|
||||||
memcpy(ret_sender, CMSG_DATA(cmsg), sizeof(struct ucred));
|
if (cmsg->cmsg_len != CMSG_LEN(sizeof(int))) {
|
||||||
found_ucred = true;
|
cmsg_close_all(&mh);
|
||||||
|
return -EMSGSIZE;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!found_ucred)
|
assert(passed_fd < 0);
|
||||||
*ret_sender = (struct ucred) {
|
passed_fd = *(int*) CMSG_DATA(cmsg);
|
||||||
.pid = 0,
|
}
|
||||||
.uid = UID_INVALID,
|
|
||||||
.gid = GID_INVALID,
|
|
||||||
};
|
|
||||||
} else {
|
|
||||||
m = recv(fd, buffer, n + 1, MSG_DONTWAIT);
|
|
||||||
if (m < 0)
|
|
||||||
return -errno;
|
|
||||||
|
|
||||||
/* Ensure the size matches what we determined before */
|
|
||||||
if (m != n)
|
|
||||||
return -EMSGSIZE;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (sender)
|
||||||
|
*ret_sender = *sender;
|
||||||
|
else
|
||||||
|
*ret_sender = (struct ucred) UCRED_INVALID;
|
||||||
|
|
||||||
|
*ret_passed_fd = TAKE_FD(passed_fd);
|
||||||
|
|
||||||
/* For safety reasons: let's always NUL terminate. */
|
/* For safety reasons: let's always NUL terminate. */
|
||||||
((char*) buffer)[n] = 0;
|
((char*) buffer)[n] = 0;
|
||||||
*ret = TAKE_PTR(buffer);
|
*ret = TAKE_PTR(buffer);
|
||||||
@ -1088,7 +1096,8 @@ static ssize_t read_datagram(int fd, struct ucred *ret_sender, void **ret) {
|
|||||||
static int on_notify_socket(sd_event_source *s, int fd, uint32_t revents, void *userdata) {
|
static int on_notify_socket(sd_event_source *s, int fd, uint32_t revents, void *userdata) {
|
||||||
_cleanup_strv_free_ char **l = NULL;
|
_cleanup_strv_free_ char **l = NULL;
|
||||||
_cleanup_free_ void *datagram = NULL;
|
_cleanup_free_ void *datagram = NULL;
|
||||||
struct ucred sender;
|
_cleanup_close_ int passed_fd = -1;
|
||||||
|
struct ucred sender = UCRED_INVALID;
|
||||||
Manager *m = userdata;
|
Manager *m = userdata;
|
||||||
ssize_t n;
|
ssize_t n;
|
||||||
Home *h;
|
Home *h;
|
||||||
@ -1096,7 +1105,7 @@ static int on_notify_socket(sd_event_source *s, int fd, uint32_t revents, void *
|
|||||||
assert(s);
|
assert(s);
|
||||||
assert(m);
|
assert(m);
|
||||||
|
|
||||||
n = read_datagram(fd, &sender, &datagram);
|
n = read_datagram(fd, &sender, &datagram, &passed_fd);
|
||||||
if (IN_SET(n, -EAGAIN, -EINTR))
|
if (IN_SET(n, -EAGAIN, -EINTR))
|
||||||
return 0;
|
return 0;
|
||||||
if (n < 0)
|
if (n < 0)
|
||||||
@ -1117,7 +1126,7 @@ static int on_notify_socket(sd_event_source *s, int fd, uint32_t revents, void *
|
|||||||
if (!l)
|
if (!l)
|
||||||
return log_oom();
|
return log_oom();
|
||||||
|
|
||||||
home_process_notify(h, l);
|
home_process_notify(h, l, TAKE_FD(passed_fd));
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -8,11 +8,14 @@
|
|||||||
#include <sys/mount.h>
|
#include <sys/mount.h>
|
||||||
#include <sys/xattr.h>
|
#include <sys/xattr.h>
|
||||||
|
|
||||||
|
#include "sd-daemon.h"
|
||||||
|
|
||||||
#include "blkid-util.h"
|
#include "blkid-util.h"
|
||||||
#include "blockdev-util.h"
|
#include "blockdev-util.h"
|
||||||
#include "btrfs-util.h"
|
#include "btrfs-util.h"
|
||||||
#include "chattr-util.h"
|
#include "chattr-util.h"
|
||||||
#include "dm-util.h"
|
#include "dm-util.h"
|
||||||
|
#include "env-util.h"
|
||||||
#include "errno-util.h"
|
#include "errno-util.h"
|
||||||
#include "fd-util.h"
|
#include "fd-util.h"
|
||||||
#include "fileio.h"
|
#include "fileio.h"
|
||||||
@ -1042,6 +1045,40 @@ int run_fallocate_by_path(const char *backing_path) {
|
|||||||
return run_fallocate(backing_fd, NULL);
|
return run_fallocate(backing_fd, NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int lock_image_fd(int image_fd, const char *ip) {
|
||||||
|
int r;
|
||||||
|
|
||||||
|
/* If the $SYSTEMD_LUKS_LOCK environment variable is set we'll take an exclusive BSD lock on the
|
||||||
|
* image file, and send it to our parent. homed will keep it open to ensure no other instance of
|
||||||
|
* homed (across the network or such) will also mount the file. */
|
||||||
|
|
||||||
|
r = getenv_bool("SYSTEMD_LUKS_LOCK");
|
||||||
|
if (r == -ENXIO)
|
||||||
|
return 0;
|
||||||
|
if (r < 0)
|
||||||
|
return log_error_errno(r, "Failed to parse $SYSTEMD_LUKS_LOCK environment variable: %m");
|
||||||
|
if (r > 0) {
|
||||||
|
if (flock(image_fd, LOCK_EX|LOCK_NB) < 0) {
|
||||||
|
|
||||||
|
if (errno == EWOULDBLOCK)
|
||||||
|
log_error_errno(errno, "Image file '%s' already locked, can't use.", ip);
|
||||||
|
else
|
||||||
|
log_error_errno(errno, "Failed to lock image file '%s': %m", ip);
|
||||||
|
|
||||||
|
return errno != EWOULDBLOCK ? -errno : -EADDRINUSE; /* Make error recognizable */
|
||||||
|
}
|
||||||
|
|
||||||
|
log_info("Successfully locked image file '%s'.", ip);
|
||||||
|
|
||||||
|
/* Now send it to our parent to keep safe while the home dir is active */
|
||||||
|
r = sd_pid_notify_with_fds(0, false, "SYSTEMD_LUKS_LOCK_FD=1", &image_fd, 1);
|
||||||
|
if (r < 0)
|
||||||
|
log_warning_errno(r, "Failed to send LUKS lock fd to parent, ignoring: %m");
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
int home_prepare_luks(
|
int home_prepare_luks(
|
||||||
UserRecord *h,
|
UserRecord *h,
|
||||||
bool already_activated,
|
bool already_activated,
|
||||||
@ -1176,6 +1213,10 @@ int home_prepare_luks(
|
|||||||
S_ISDIR(st.st_mode) ? SYNTHETIC_ERRNO(EISDIR) : SYNTHETIC_ERRNO(EBADFD),
|
S_ISDIR(st.st_mode) ? SYNTHETIC_ERRNO(EISDIR) : SYNTHETIC_ERRNO(EBADFD),
|
||||||
"Image file %s is not a regular file or block device: %m", ip);
|
"Image file %s is not a regular file or block device: %m", ip);
|
||||||
|
|
||||||
|
r = lock_image_fd(image_fd, ip);
|
||||||
|
if (r < 0)
|
||||||
|
return r;
|
||||||
|
|
||||||
r = luks_validate(image_fd, user_record_user_name_and_realm(h), h->partition_uuid, &found_partition_uuid, &offset, &size);
|
r = luks_validate(image_fd, user_record_user_name_and_realm(h), h->partition_uuid, &found_partition_uuid, &offset, &size);
|
||||||
if (r < 0)
|
if (r < 0)
|
||||||
return log_error_errno(r, "Failed to validate disk label: %m");
|
return log_error_errno(r, "Failed to validate disk label: %m");
|
||||||
|
@ -1706,6 +1706,7 @@ static int run(int argc, char *argv[]) {
|
|||||||
* ENOEXEC → file system is currently not active
|
* ENOEXEC → file system is currently not active
|
||||||
* ENOSPC → not enough disk space for operation
|
* ENOSPC → not enough disk space for operation
|
||||||
* EKEYREVOKED → user record has not suitable hashed password or pkcs#11 entry, we cannot authenticate
|
* EKEYREVOKED → user record has not suitable hashed password or pkcs#11 entry, we cannot authenticate
|
||||||
|
* EADDRINUSE → home image is already used elsewhere (lock taken)
|
||||||
*/
|
*/
|
||||||
|
|
||||||
if (streq(argv[1], "activate"))
|
if (streq(argv[1], "activate"))
|
||||||
|
@ -142,6 +142,7 @@ BUS_ERROR_MAP_ELF_REGISTER const sd_bus_error_map bus_common_errors[] = {
|
|||||||
SD_BUS_ERROR_MAP(BUS_ERROR_TOO_MANY_OPERATIONS, ENOBUFS),
|
SD_BUS_ERROR_MAP(BUS_ERROR_TOO_MANY_OPERATIONS, ENOBUFS),
|
||||||
SD_BUS_ERROR_MAP(BUS_ERROR_AUTHENTICATION_LIMIT_HIT, ETOOMANYREFS),
|
SD_BUS_ERROR_MAP(BUS_ERROR_AUTHENTICATION_LIMIT_HIT, ETOOMANYREFS),
|
||||||
SD_BUS_ERROR_MAP(BUS_ERROR_HOME_CANT_AUTHENTICATE, EKEYREVOKED),
|
SD_BUS_ERROR_MAP(BUS_ERROR_HOME_CANT_AUTHENTICATE, EKEYREVOKED),
|
||||||
|
SD_BUS_ERROR_MAP(BUS_ERROR_HOME_IN_USE, EADDRINUSE),
|
||||||
|
|
||||||
SD_BUS_ERROR_MAP_END
|
SD_BUS_ERROR_MAP_END
|
||||||
};
|
};
|
||||||
|
@ -126,5 +126,6 @@
|
|||||||
#define BUS_ERROR_TOO_MANY_OPERATIONS "org.freedesktop.home1.TooManyOperations"
|
#define BUS_ERROR_TOO_MANY_OPERATIONS "org.freedesktop.home1.TooManyOperations"
|
||||||
#define BUS_ERROR_AUTHENTICATION_LIMIT_HIT "org.freedesktop.home1.AuthenticationLimitHit"
|
#define BUS_ERROR_AUTHENTICATION_LIMIT_HIT "org.freedesktop.home1.AuthenticationLimitHit"
|
||||||
#define BUS_ERROR_HOME_CANT_AUTHENTICATE "org.freedesktop.home1.HomeCantAuthenticate"
|
#define BUS_ERROR_HOME_CANT_AUTHENTICATE "org.freedesktop.home1.HomeCantAuthenticate"
|
||||||
|
#define BUS_ERROR_HOME_IN_USE "org.freedesktop.home1.HomeInUse"
|
||||||
|
|
||||||
BUS_ERROR_MAP_ELF_USE(bus_common_errors);
|
BUS_ERROR_MAP_ELF_USE(bus_common_errors);
|
||||||
|
Loading…
Reference in New Issue
Block a user