From 7f2a7ccf7d44591789fd9e072e7b07b8cf1536ee Mon Sep 17 00:00:00 2001 From: Mike Yuan Date: Wed, 28 Aug 2024 19:46:22 +0200 Subject: [PATCH] core/unit: introduce unit_set_debug_invocation() Given that debug_invocation is a Unit thing, make service_set_debug_invocation() generic. Plus, don't say "Service failed", as it would be spurious when Restart=always. --- src/core/service.c | 32 +++++++++++--------------------- src/core/unit.c | 19 ++++++++++++++++--- src/core/unit.h | 3 ++- 3 files changed, 29 insertions(+), 25 deletions(-) diff --git a/src/core/service.c b/src/core/service.c index b3a81434276..ca1f54340d0 100644 --- a/src/core/service.c +++ b/src/core/service.c @@ -2022,22 +2022,6 @@ static ServiceState service_determine_dead_state(Service *s) { return s->fd_store && s->fd_store_preserve_mode == EXEC_PRESERVE_YES ? SERVICE_DEAD_RESOURCES_PINNED : SERVICE_DEAD; } -static void service_set_debug_invocation(Service *s, bool enable) { - assert(s); - - if (s->restart_mode != SERVICE_RESTART_MODE_DEBUG) - return; - - if (enable == UNIT(s)->debug_invocation) - return; /* Nothing to do */ - - UNIT(s)->debug_invocation = enable; - unit_overwrite_log_level_max(UNIT(s), enable ? LOG_PRI(LOG_DEBUG) : s->exec_context.log_level_max); - - if (enable) - log_unit_notice(UNIT(s), "Service failed, subsequent restarts will be executed with debug level logging."); -} - static void service_enter_dead(Service *s, ServiceResult f, bool allow_restart) { ServiceState end_state, restart_state; int r; @@ -2101,13 +2085,19 @@ static void service_enter_dead(Service *s, ServiceResult f, bool allow_restart) return service_enter_dead(s, SERVICE_FAILURE_RESOURCES, /* allow_restart= */ false); } - log_unit_debug(UNIT(s), "Next restart interval calculated as: %s", FORMAT_TIMESPAN(restart_usec_next, 0)); - /* If the relevant option is set, and the unit doesn't already have logging level set to * debug, enable it now. Make sure to overwrite the state in /run/systemd/units/ too, to * ensure journald doesn't prune the messages. The previous state is saved and restored * once the auto-restart flow ends. */ - service_set_debug_invocation(s, /* enable= */ true); + if (s->restart_mode == SERVICE_RESTART_MODE_DEBUG) { + r = unit_set_debug_invocation(UNIT(s), true); + if (r < 0) + log_unit_warning_errno(UNIT(s), r, "Failed to enable debug invocation, ignoring: %m"); + if (r > 0) + log_unit_notice(UNIT(s), "Service dead, subsequent restarts will be executed with debug level logging."); + } + + log_unit_debug(UNIT(s), "Next restart interval calculated as: %s", FORMAT_TIMESPAN(restart_usec_next, 0)); service_set_state(s, SERVICE_AUTO_RESTART); } else { @@ -2116,7 +2106,7 @@ static void service_enter_dead(Service *s, ServiceResult f, bool allow_restart) * can still introspect the counter. */ service_set_state(s, end_state); - service_set_debug_invocation(s, /* enable= */ false); + (void) unit_set_debug_invocation(UNIT(s), false); } /* The new state is in effect, let's decrease the fd store ref counter again. Let's also re-add us to the GC @@ -4952,7 +4942,7 @@ static void service_reset_failed(Unit *u) { s->live_mount_result = SERVICE_SUCCESS; s->n_restarts = 0; - service_set_debug_invocation(s, /* enable= */ false); + (void) unit_set_debug_invocation(u, /* enable= */ false); } static PidRef* service_main_pid(Unit *u, bool *ret_is_alien) { diff --git a/src/core/unit.c b/src/core/unit.c index 4468733a636..cebae4d53e4 100644 --- a/src/core/unit.c +++ b/src/core/unit.c @@ -5839,14 +5839,27 @@ void unit_unlink_state_files(Unit *u) { } } -int unit_overwrite_log_level_max(Unit *u, int log_level_max) { +int unit_set_debug_invocation(Unit *u, bool enable) { + int r; + assert(u); - if (!u->exported_log_level_max) + if (u->debug_invocation == enable) return 0; /* Nothing to do */ + u->debug_invocation = enable; + /* Ensure that the new log level is exported for the journal, in place of the previous one */ - return unit_export_log_level_max(u, log_level_max, /* overwrite= */ true); + if (u->exported_log_level_max) { + const ExecContext *ec = unit_get_exec_context(u); + if (ec) { + r = unit_export_log_level_max(u, enable ? LOG_PRI(LOG_DEBUG) : ec->log_level_max, /* overwrite= */ true); + if (r < 0) + return r; + } + } + + return 1; } int unit_prepare_exec(Unit *u) { diff --git a/src/core/unit.h b/src/core/unit.h index 8aac5f59992..5ffd82b67eb 100644 --- a/src/core/unit.h +++ b/src/core/unit.h @@ -992,7 +992,8 @@ void unit_remove_dependencies(Unit *u, UnitDependencyMask mask); void unit_export_state_files(Unit *u); void unit_unlink_state_files(Unit *u); -int unit_overwrite_log_level_max(Unit *u, int log_level_max); + +int unit_set_debug_invocation(Unit *u, bool enable); int unit_prepare_exec(Unit *u);