mirror of
https://github.com/Dasharo/systemd.git
synced 2026-03-06 15:02:31 -08:00
logind-dbus: rearrange functions
This commit is contained in:
@@ -70,9 +70,7 @@
|
||||
|
||||
#define SHUTDOWN_SCHEDULE_FILE "/run/systemd/shutdown/scheduled"
|
||||
|
||||
static int update_schedule_file(Manager *m);
|
||||
static void reset_scheduled_shutdown(Manager *m);
|
||||
static int manager_setup_shutdown_timers(Manager* m);
|
||||
|
||||
static int get_sender_session(
|
||||
Manager *m,
|
||||
@@ -2278,7 +2276,7 @@ static int nologin_timeout_handler(
|
||||
uint64_t usec,
|
||||
void *userdata) {
|
||||
|
||||
Manager *m = userdata;
|
||||
Manager *m = ASSERT_PTR(userdata);
|
||||
|
||||
log_info("Creating /run/nologin, blocking further logins...");
|
||||
|
||||
@@ -2293,6 +2291,153 @@ static usec_t nologin_timeout_usec(usec_t elapse) {
|
||||
return LESS_BY(elapse, 5 * USEC_PER_MINUTE);
|
||||
}
|
||||
|
||||
static void reset_scheduled_shutdown(Manager *m) {
|
||||
assert(m);
|
||||
|
||||
m->scheduled_shutdown_timeout_source = sd_event_source_unref(m->scheduled_shutdown_timeout_source);
|
||||
m->wall_message_timeout_source = sd_event_source_unref(m->wall_message_timeout_source);
|
||||
m->nologin_timeout_source = sd_event_source_unref(m->nologin_timeout_source);
|
||||
|
||||
m->scheduled_shutdown_action = _HANDLE_ACTION_INVALID;
|
||||
m->scheduled_shutdown_timeout = USEC_INFINITY;
|
||||
m->scheduled_shutdown_uid = UID_INVALID;
|
||||
m->scheduled_shutdown_tty = mfree(m->scheduled_shutdown_tty);
|
||||
m->shutdown_dry_run = false;
|
||||
|
||||
if (m->unlink_nologin) {
|
||||
(void) unlink_or_warn("/run/nologin");
|
||||
m->unlink_nologin = false;
|
||||
}
|
||||
|
||||
(void) unlink(SHUTDOWN_SCHEDULE_FILE);
|
||||
}
|
||||
|
||||
static int update_schedule_file(Manager *m) {
|
||||
_cleanup_(unlink_and_freep) char *temp_path = NULL;
|
||||
_cleanup_fclose_ FILE *f = NULL;
|
||||
int r;
|
||||
|
||||
assert(m);
|
||||
assert(handle_action_valid(m->scheduled_shutdown_action));
|
||||
|
||||
r = mkdir_parents_label(SHUTDOWN_SCHEDULE_FILE, 0755);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to create shutdown subdirectory: %m");
|
||||
|
||||
r = fopen_temporary(SHUTDOWN_SCHEDULE_FILE, &f, &temp_path);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to save information about scheduled shutdowns: %m");
|
||||
|
||||
(void) fchmod(fileno(f), 0644);
|
||||
|
||||
serialize_usec(f, "USEC", m->scheduled_shutdown_timeout);
|
||||
serialize_item_format(f, "WARN_WALL", "%s", one_zero(m->enable_wall_messages));
|
||||
serialize_item_format(f, "MODE", "%s", handle_action_to_string(m->scheduled_shutdown_action));
|
||||
serialize_item_format(f, "UID", UID_FMT, m->scheduled_shutdown_uid);
|
||||
|
||||
if (m->scheduled_shutdown_tty)
|
||||
serialize_item_format(f, "TTY", "%s", m->scheduled_shutdown_tty);
|
||||
|
||||
if (!isempty(m->wall_message)) {
|
||||
r = serialize_item_escaped(f, "WALL_MESSAGE", m->wall_message);
|
||||
if (r < 0)
|
||||
goto fail;
|
||||
}
|
||||
|
||||
r = fflush_and_check(f);
|
||||
if (r < 0)
|
||||
goto fail;
|
||||
|
||||
if (rename(temp_path, SHUTDOWN_SCHEDULE_FILE) < 0) {
|
||||
r = -errno;
|
||||
goto fail;
|
||||
}
|
||||
|
||||
temp_path = mfree(temp_path);
|
||||
return 0;
|
||||
|
||||
fail:
|
||||
(void) unlink(SHUTDOWN_SCHEDULE_FILE);
|
||||
|
||||
return log_error_errno(r, "Failed to write information about scheduled shutdowns: %m");
|
||||
}
|
||||
|
||||
static int manager_scheduled_shutdown_handler(
|
||||
sd_event_source *s,
|
||||
uint64_t usec,
|
||||
void *userdata) {
|
||||
|
||||
Manager *m = ASSERT_PTR(userdata);
|
||||
_cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
|
||||
const HandleActionData *a;
|
||||
int r;
|
||||
|
||||
assert_se(a = handle_action_lookup(m->scheduled_shutdown_action));
|
||||
|
||||
/* Don't allow multiple jobs being executed at the same time */
|
||||
if (m->delayed_action) {
|
||||
r = log_error_errno(SYNTHETIC_ERRNO(EALREADY),
|
||||
"Scheduled shutdown to %s failed: shutdown or sleep operation already in progress.",
|
||||
a->target);
|
||||
goto error;
|
||||
}
|
||||
|
||||
if (m->shutdown_dry_run) {
|
||||
/* We do not process delay inhibitors here. Otherwise, we
|
||||
* would have to be considered "in progress" (like the check
|
||||
* above) for some seconds after our admin has seen the final
|
||||
* wall message. */
|
||||
|
||||
bus_manager_log_shutdown(m, a);
|
||||
log_info("Running in dry run, suppressing action.");
|
||||
reset_scheduled_shutdown(m);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
r = bus_manager_shutdown_or_sleep_now_or_later(m, a, &error);
|
||||
if (r < 0) {
|
||||
log_error_errno(r, "Scheduled shutdown to %s failed: %m", a->target);
|
||||
goto error;
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
||||
error:
|
||||
reset_scheduled_shutdown(m);
|
||||
return r;
|
||||
}
|
||||
|
||||
static int manager_setup_shutdown_timers(Manager* m) {
|
||||
int r;
|
||||
|
||||
assert(m);
|
||||
|
||||
r = event_reset_time(m->event, &m->scheduled_shutdown_timeout_source,
|
||||
CLOCK_REALTIME,
|
||||
m->scheduled_shutdown_timeout, 0,
|
||||
manager_scheduled_shutdown_handler, m,
|
||||
0, "scheduled-shutdown-timeout", true);
|
||||
if (r < 0)
|
||||
goto fail;
|
||||
|
||||
r = event_reset_time(m->event, &m->nologin_timeout_source,
|
||||
CLOCK_REALTIME,
|
||||
nologin_timeout_usec(m->scheduled_shutdown_timeout), 0,
|
||||
nologin_timeout_handler, m,
|
||||
0, "nologin-timeout", true);
|
||||
if (r < 0)
|
||||
goto fail;
|
||||
|
||||
return 0;
|
||||
|
||||
fail:
|
||||
m->scheduled_shutdown_timeout_source = sd_event_source_unref(m->scheduled_shutdown_timeout_source);
|
||||
m->nologin_timeout_source = sd_event_source_unref(m->nologin_timeout_source);
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
void manager_load_scheduled_shutdown(Manager *m) {
|
||||
_cleanup_fclose_ FILE *f = NULL;
|
||||
_cleanup_free_ char *usec = NULL,
|
||||
@@ -2306,12 +2451,12 @@ void manager_load_scheduled_shutdown(Manager *m) {
|
||||
assert(m);
|
||||
|
||||
r = parse_env_file(f, SHUTDOWN_SCHEDULE_FILE,
|
||||
"USEC", &usec,
|
||||
"WARN_WALL", &warn_wall,
|
||||
"MODE", &mode,
|
||||
"WALL_MESSAGE", &wall_message,
|
||||
"UID", &uid,
|
||||
"TTY", &tty);
|
||||
"USEC", &usec,
|
||||
"WARN_WALL", &warn_wall,
|
||||
"MODE", &mode,
|
||||
"WALL_MESSAGE", &wall_message,
|
||||
"UID", &uid,
|
||||
"TTY", &tty);
|
||||
|
||||
/* reset will delete the file */
|
||||
reset_scheduled_shutdown(m);
|
||||
@@ -2368,123 +2513,6 @@ void manager_load_scheduled_shutdown(Manager *m) {
|
||||
return;
|
||||
}
|
||||
|
||||
static int update_schedule_file(Manager *m) {
|
||||
_cleanup_(unlink_and_freep) char *temp_path = NULL;
|
||||
_cleanup_fclose_ FILE *f = NULL;
|
||||
int r;
|
||||
|
||||
assert(m);
|
||||
assert(handle_action_valid(m->scheduled_shutdown_action));
|
||||
|
||||
r = mkdir_parents_label(SHUTDOWN_SCHEDULE_FILE, 0755);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to create shutdown subdirectory: %m");
|
||||
|
||||
r = fopen_temporary(SHUTDOWN_SCHEDULE_FILE, &f, &temp_path);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to save information about scheduled shutdowns: %m");
|
||||
|
||||
(void) fchmod(fileno(f), 0644);
|
||||
|
||||
serialize_usec(f, "USEC", m->scheduled_shutdown_timeout);
|
||||
serialize_item_format(f, "WARN_WALL", "%s", one_zero(m->enable_wall_messages));
|
||||
serialize_item_format(f, "MODE", "%s", handle_action_to_string(m->scheduled_shutdown_action));
|
||||
serialize_item_format(f, "UID", UID_FMT, m->scheduled_shutdown_uid);
|
||||
|
||||
if (m->scheduled_shutdown_tty)
|
||||
serialize_item_format(f, "TTY", "%s", m->scheduled_shutdown_tty);
|
||||
|
||||
if (!isempty(m->wall_message)) {
|
||||
r = serialize_item_escaped(f, "WALL_MESSAGE", m->wall_message);
|
||||
if (r < 0)
|
||||
goto fail;
|
||||
}
|
||||
|
||||
r = fflush_and_check(f);
|
||||
if (r < 0)
|
||||
goto fail;
|
||||
|
||||
if (rename(temp_path, SHUTDOWN_SCHEDULE_FILE) < 0) {
|
||||
r = -errno;
|
||||
goto fail;
|
||||
}
|
||||
|
||||
temp_path = mfree(temp_path);
|
||||
return 0;
|
||||
|
||||
fail:
|
||||
(void) unlink(SHUTDOWN_SCHEDULE_FILE);
|
||||
|
||||
return log_error_errno(r, "Failed to write information about scheduled shutdowns: %m");
|
||||
}
|
||||
|
||||
static void reset_scheduled_shutdown(Manager *m) {
|
||||
assert(m);
|
||||
|
||||
m->scheduled_shutdown_timeout_source = sd_event_source_unref(m->scheduled_shutdown_timeout_source);
|
||||
m->wall_message_timeout_source = sd_event_source_unref(m->wall_message_timeout_source);
|
||||
m->nologin_timeout_source = sd_event_source_unref(m->nologin_timeout_source);
|
||||
|
||||
m->scheduled_shutdown_action = _HANDLE_ACTION_INVALID;
|
||||
m->scheduled_shutdown_timeout = USEC_INFINITY;
|
||||
m->scheduled_shutdown_uid = UID_INVALID;
|
||||
m->scheduled_shutdown_tty = mfree(m->scheduled_shutdown_tty);
|
||||
m->shutdown_dry_run = false;
|
||||
|
||||
if (m->unlink_nologin) {
|
||||
(void) unlink_or_warn("/run/nologin");
|
||||
m->unlink_nologin = false;
|
||||
}
|
||||
|
||||
(void) unlink(SHUTDOWN_SCHEDULE_FILE);
|
||||
}
|
||||
|
||||
static int manager_scheduled_shutdown_handler(
|
||||
sd_event_source *s,
|
||||
uint64_t usec,
|
||||
void *userdata) {
|
||||
|
||||
Manager *m = ASSERT_PTR(userdata);
|
||||
_cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
|
||||
const HandleActionData *a;
|
||||
int r;
|
||||
|
||||
assert_se(a = handle_action_lookup(m->scheduled_shutdown_action));
|
||||
|
||||
/* Don't allow multiple jobs being executed at the same time */
|
||||
if (m->delayed_action) {
|
||||
r = log_error_errno(SYNTHETIC_ERRNO(EALREADY),
|
||||
"Scheduled shutdown to %s failed: shutdown or sleep operation already in progress.",
|
||||
a->target);
|
||||
goto error;
|
||||
}
|
||||
|
||||
if (m->shutdown_dry_run) {
|
||||
/* We do not process delay inhibitors here. Otherwise, we
|
||||
* would have to be considered "in progress" (like the check
|
||||
* above) for some seconds after our admin has seen the final
|
||||
* wall message. */
|
||||
|
||||
bus_manager_log_shutdown(m, a);
|
||||
log_info("Running in dry run, suppressing action.");
|
||||
reset_scheduled_shutdown(m);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
r = bus_manager_shutdown_or_sleep_now_or_later(m, a, &error);
|
||||
if (r < 0) {
|
||||
log_error_errno(r, "Scheduled shutdown to %s failed: %m", a->target);
|
||||
goto error;
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
||||
error:
|
||||
reset_scheduled_shutdown(m);
|
||||
return r;
|
||||
}
|
||||
|
||||
static int method_schedule_shutdown(sd_bus_message *message, void *userdata, sd_bus_error *error) {
|
||||
Manager *m = ASSERT_PTR(userdata);
|
||||
HandleAction handle;
|
||||
@@ -2536,34 +2564,6 @@ static int method_schedule_shutdown(sd_bus_message *message, void *userdata, sd_
|
||||
return sd_bus_reply_method_return(message, NULL);
|
||||
}
|
||||
|
||||
static int manager_setup_shutdown_timers(Manager* m) {
|
||||
int r;
|
||||
|
||||
r = event_reset_time(m->event, &m->scheduled_shutdown_timeout_source,
|
||||
CLOCK_REALTIME,
|
||||
m->scheduled_shutdown_timeout, 0,
|
||||
manager_scheduled_shutdown_handler, m,
|
||||
0, "scheduled-shutdown-timeout", true);
|
||||
if (r < 0)
|
||||
goto fail;
|
||||
|
||||
r = event_reset_time(m->event, &m->nologin_timeout_source,
|
||||
CLOCK_REALTIME,
|
||||
nologin_timeout_usec(m->scheduled_shutdown_timeout), 0,
|
||||
nologin_timeout_handler, m,
|
||||
0, "nologin-timeout", true);
|
||||
if (r < 0)
|
||||
goto fail;
|
||||
|
||||
return 0;
|
||||
|
||||
fail:
|
||||
m->scheduled_shutdown_timeout_source = sd_event_source_unref(m->scheduled_shutdown_timeout_source);
|
||||
m->nologin_timeout_source = sd_event_source_unref(m->nologin_timeout_source);
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
static int method_cancel_scheduled_shutdown(sd_bus_message *message, void *userdata, sd_bus_error *error) {
|
||||
Manager *m = ASSERT_PTR(userdata);
|
||||
const HandleActionData *a;
|
||||
|
||||
Reference in New Issue
Block a user