aed857
From 50ce13182e07af7f240c61d03bf113e86a269917 Mon Sep 17 00:00:00 2001
aed857
From: Michal Schmidt <mschmidt@redhat.com>
aed857
Date: Tue, 21 Jul 2015 14:54:24 +0200
aed857
Subject: [PATCH] core: try harder to get job completion messages too
aed857
aed857
This is similar to "core: always try harder to get unit status
aed857
message format string", but for job completion status messages.
aed857
It makes generic status messages applicable for printing to the console.
aed857
And it rewrites the functions in a more table-based style.
aed857
aed857
(cherry picked from commit aa49ab5f22c0fdc7a5381d4e452f40705f3d7bf8)
aed857
aed857
Related: #1506256
aed857
---
23b3cf
 src/core/job.c | 192 ++++++++++++++++++-------------------------------
aed857
 1 file changed, 68 insertions(+), 124 deletions(-)
aed857
aed857
diff --git a/src/core/job.c b/src/core/job.c
aed857
index 612caa604..f371f914d 100644
aed857
--- a/src/core/job.c
aed857
+++ b/src/core/job.c
aed857
@@ -622,156 +622,100 @@ int job_run_and_invalidate(Job *j) {
aed857
 }
aed857
 
aed857
 _pure_ static const char *job_get_status_message_format(Unit *u, JobType t, JobResult result) {
aed857
+        const char *format;
aed857
         const UnitStatusMessageFormats *format_table;
aed857
+        static const char *const generic_finished_start_job[_JOB_RESULT_MAX] = {
aed857
+                [JOB_DONE]        = "Started %s.",
aed857
+                [JOB_TIMEOUT]     = "Timed out starting %s.",
aed857
+                [JOB_FAILED]      = "Failed to start %s.",
aed857
+                [JOB_DEPENDENCY]  = "Dependency failed for %s.",
aed857
+                [JOB_ASSERT]      = "Assertion failed for %s.",
aed857
+                [JOB_UNSUPPORTED] = "Starting of %s not supported.",
aed857
+        };
aed857
+        static const char *const generic_finished_stop_job[_JOB_RESULT_MAX] = {
aed857
+                [JOB_DONE]        = "Stopped %s.",
aed857
+                [JOB_FAILED]      = "Stopped (with error) %s.",
aed857
+                [JOB_TIMEOUT]     = "Timed out stoppping %s.",
aed857
+        };
aed857
+        static const char *const generic_finished_reload_job[_JOB_RESULT_MAX] = {
aed857
+                [JOB_DONE]        = "Reloaded %s.",
aed857
+                [JOB_FAILED]      = "Reload failed for %s.",
aed857
+                [JOB_TIMEOUT]     = "Timed out reloading %s.",
aed857
+        };
aed857
+        /* When verify-active detects the unit is inactive, report it.
aed857
+         * Most likely a DEPEND warning from a requisiting unit will
aed857
+         * occur next and it's nice to see what was requisited. */
aed857
+        static const char *const generic_finished_verify_active_job[_JOB_RESULT_MAX] = {
aed857
+                [JOB_SKIPPED]     = "%s is not active.",
aed857
+        };
aed857
 
aed857
         assert(u);
aed857
         assert(t >= 0);
aed857
         assert(t < _JOB_TYPE_MAX);
aed857
 
aed857
-        format_table = &UNIT_VTABLE(u)->status_message_formats;
aed857
-        if (!format_table)
aed857
-                return NULL;
aed857
+        if (t == JOB_START || t == JOB_STOP || t == JOB_RESTART) {
aed857
+                format_table = &UNIT_VTABLE(u)->status_message_formats;
aed857
+                if (format_table) {
aed857
+                        format = t == JOB_START ? format_table->finished_start_job[result] :
aed857
+                                                  format_table->finished_stop_job[result];
aed857
+                        if (format)
aed857
+                                return format;
aed857
+                }
aed857
+        }
aed857
 
aed857
+        /* Return generic strings */
aed857
         if (t == JOB_START)
aed857
-                return format_table->finished_start_job[result];
aed857
+                return generic_finished_start_job[result];
aed857
         else if (t == JOB_STOP || t == JOB_RESTART)
aed857
-                return format_table->finished_stop_job[result];
aed857
-
aed857
-        return NULL;
aed857
-}
aed857
-
aed857
-_pure_ static const char *job_get_status_message_format_try_harder(Unit *u, JobType t, JobResult result) {
aed857
-        const char *format;
aed857
-
aed857
-        assert(u);
aed857
-        assert(t >= 0);
aed857
-        assert(t < _JOB_TYPE_MAX);
aed857
-
aed857
-        format = job_get_status_message_format(u, t, result);
aed857
-        if (format)
aed857
-                return format;
aed857
-
aed857
-        /* Return generic strings */
aed857
-        if (t == JOB_START) {
aed857
-                if (result == JOB_DONE)
aed857
-                        return "Started %s.";
aed857
-                else if (result == JOB_TIMEOUT)
aed857
-                        return "Timed out starting %s.";
aed857
-                else if (result == JOB_FAILED)
aed857
-                        return "Failed to start %s.";
aed857
-                else if (result == JOB_DEPENDENCY)
aed857
-                        return "Dependency failed for %s.";
aed857
-                else if (result == JOB_ASSERT)
aed857
-                        return "Assertion failed for %s.";
aed857
-                else if (result == JOB_UNSUPPORTED)
aed857
-                        return "Starting of %s not supported.";
aed857
-        } else if (t == JOB_STOP || t == JOB_RESTART) {
aed857
-                if (result == JOB_DONE)
aed857
-                        return "Stopped %s.";
aed857
-                else if (result == JOB_FAILED)
aed857
-                        return "Stopped (with error) %s.";
aed857
-                else if (result == JOB_TIMEOUT)
aed857
-                        return "Timed out stoppping %s.";
aed857
-        } else if (t == JOB_RELOAD) {
aed857
-                if (result == JOB_DONE)
aed857
-                        return "Reloaded %s.";
aed857
-                else if (result == JOB_FAILED)
aed857
-                        return "Reload failed for %s.";
aed857
-                else if (result == JOB_TIMEOUT)
aed857
-                        return "Timed out reloading %s.";
aed857
-        }
aed857
+                return generic_finished_stop_job[result];
aed857
+        else if (t == JOB_RELOAD)
aed857
+                return generic_finished_reload_job[result];
aed857
+        else if (t == JOB_VERIFY_ACTIVE)
aed857
+                return generic_finished_verify_active_job[result];
aed857
 
aed857
         return NULL;
aed857
 }
aed857
 
aed857
 static void job_print_status_message(Unit *u, JobType t, JobResult result) {
aed857
         const char *format;
aed857
+        static const char* const job_result_status_table[_JOB_RESULT_MAX] = {
aed857
+                [JOB_DONE]        = ANSI_GREEN_ON            "  OK  " ANSI_HIGHLIGHT_OFF,
aed857
+                [JOB_TIMEOUT]     = ANSI_HIGHLIGHT_RED_ON    " TIME " ANSI_HIGHLIGHT_OFF,
aed857
+                [JOB_FAILED]      = ANSI_HIGHLIGHT_RED_ON    "FAILED" ANSI_HIGHLIGHT_OFF,
aed857
+                [JOB_DEPENDENCY]  = ANSI_HIGHLIGHT_YELLOW_ON "DEPEND" ANSI_HIGHLIGHT_OFF,
aed857
+                [JOB_SKIPPED]     = ANSI_HIGHLIGHT_ON        " INFO " ANSI_HIGHLIGHT_OFF,
aed857
+                [JOB_ASSERT]      = ANSI_HIGHLIGHT_YELLOW_ON "ASSERT" ANSI_HIGHLIGHT_OFF,
aed857
+                [JOB_UNSUPPORTED] = ANSI_HIGHLIGHT_YELLOW_ON "UNSUPP" ANSI_HIGHLIGHT_OFF,
aed857
+        };
aed857
 
aed857
         assert(u);
aed857
         assert(t >= 0);
aed857
         assert(t < _JOB_TYPE_MAX);
aed857
 
aed857
-        DISABLE_WARNING_FORMAT_NONLITERAL;
aed857
-
aed857
-        if (t == JOB_START) {
aed857
-                format = job_get_status_message_format(u, t, result);
aed857
-                if (!format)
aed857
-                        return;
aed857
-
aed857
-                switch (result) {
aed857
-
aed857
-                case JOB_DONE:
aed857
-                        if (u->condition_result)
aed857
-                                unit_status_printf(u, ANSI_GREEN_ON "  OK  " ANSI_HIGHLIGHT_OFF, format);
aed857
-                        break;
aed857
-
aed857
-                case JOB_TIMEOUT:
aed857
-                        manager_flip_auto_status(u->manager, true);
aed857
-                        unit_status_printf(u, ANSI_HIGHLIGHT_RED_ON " TIME " ANSI_HIGHLIGHT_OFF, format);
aed857
-                        break;
aed857
-
aed857
-                case JOB_FAILED: {
aed857
-                        _cleanup_free_ char *quoted = NULL;
aed857
-
aed857
-                        quoted = shell_maybe_quote(u->id);
aed857
-
aed857
-                        manager_flip_auto_status(u->manager, true);
aed857
-                        unit_status_printf(u, ANSI_HIGHLIGHT_RED_ON "FAILED" ANSI_HIGHLIGHT_OFF, format);
aed857
-                        manager_status_printf(u->manager, STATUS_TYPE_NORMAL, NULL, "See 'systemctl status %s' for details.", strna(quoted));
aed857
-                        break;
aed857
-                }
aed857
-
aed857
-                case JOB_DEPENDENCY:
aed857
-                        manager_flip_auto_status(u->manager, true);
aed857
-                        unit_status_printf(u, ANSI_HIGHLIGHT_YELLOW_ON "DEPEND" ANSI_HIGHLIGHT_OFF, format);
aed857
-                        break;
aed857
-
aed857
-                case JOB_ASSERT:
aed857
-                        manager_flip_auto_status(u->manager, true);
aed857
-                        unit_status_printf(u, ANSI_HIGHLIGHT_YELLOW_ON "ASSERT" ANSI_HIGHLIGHT_OFF, format);
aed857
-                        break;
aed857
-
aed857
-                case JOB_UNSUPPORTED:
aed857
-                        manager_flip_auto_status(u->manager, true);
aed857
-                        unit_status_printf(u, ANSI_HIGHLIGHT_YELLOW_ON "UNSUPP" ANSI_HIGHLIGHT_OFF, format);
aed857
-                        break;
aed857
-
aed857
-                default:
aed857
-                        ;
aed857
-                }
aed857
-
aed857
-        } else if (t == JOB_STOP || t == JOB_RESTART) {
aed857
-
aed857
-                format = job_get_status_message_format(u, t, result);
aed857
-                if (!format)
aed857
-                        return;
aed857
+        /* Reload status messages have traditionally not been printed to console. */
aed857
+        if (t == JOB_RELOAD)
aed857
+                return;
aed857
 
aed857
-                switch (result) {
aed857
+        if (t == JOB_START && result == JOB_DONE && !u->condition_result)
aed857
+                return;
aed857
 
aed857
-                case JOB_TIMEOUT:
aed857
-                        manager_flip_auto_status(u->manager, true);
aed857
-                        unit_status_printf(u, ANSI_HIGHLIGHT_RED_ON " TIME " ANSI_HIGHLIGHT_OFF, format);
aed857
-                        break;
aed857
+        format = job_get_status_message_format(u, t, result);
aed857
+        if (!format)
aed857
+                return;
aed857
 
aed857
-                case JOB_DONE:
aed857
-                case JOB_FAILED:
aed857
-                        unit_status_printf(u, ANSI_GREEN_ON "  OK  " ANSI_HIGHLIGHT_OFF, format);
aed857
-                        break;
aed857
+        if (result != JOB_DONE)
aed857
+                manager_flip_auto_status(u->manager, true);
aed857
 
aed857
-                default:
aed857
-                        ;
aed857
-                }
aed857
+        DISABLE_WARNING_FORMAT_NONLITERAL;
aed857
+        unit_status_printf(u, job_result_status_table[result], format);
aed857
+        REENABLE_WARNING;
aed857
 
aed857
-        } else if (t == JOB_VERIFY_ACTIVE) {
aed857
+        if (t == JOB_START && result == JOB_FAILED) {
aed857
+                _cleanup_free_ char *quoted = shell_maybe_quote(u->id);
aed857
 
aed857
-                /* When verify-active detects the unit is inactive, report it.
aed857
-                 * Most likely a DEPEND warning from a requisiting unit will
aed857
-                 * occur next and it's nice to see what was requisited. */
aed857
-                if (result == JOB_SKIPPED)
aed857
-                        unit_status_printf(u, ANSI_HIGHLIGHT_ON " INFO " ANSI_HIGHLIGHT_OFF, "%s is not active.");
aed857
+                manager_status_printf(u->manager, STATUS_TYPE_NORMAL, NULL,
aed857
+                                      "See 'systemctl status %s' for details.", strna(quoted));
aed857
         }
aed857
-
aed857
-        REENABLE_WARNING;
aed857
 }
aed857
 
aed857
 static void job_log_status_message(Unit *u, JobType t, JobResult result) {
aed857
@@ -788,7 +732,7 @@ static void job_log_status_message(Unit *u, JobType t, JobResult result) {
aed857
         if (log_on_console())
aed857
                 return;
aed857
 
aed857
-        format = job_get_status_message_format_try_harder(u, t, result);
aed857
+        format = job_get_status_message_format(u, t, result);
aed857
         if (!format)
aed857
                 return;
aed857