1 /*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
4 This file is part of systemd.
6 Copyright 2010 Lennart Poettering
8 systemd is free software; you can redistribute it and/or modify it
9 under the terms of the GNU Lesser General Public License as published by
10 the Free Software Foundation; either version 2.1 of the License, or
11 (at your option) any later version.
13 systemd is distributed in the hope that it will be useful, but
14 WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 Lesser General Public License for more details.
18 You should have received a copy of the GNU Lesser General Public License
19 along with systemd; If not, see <http://www.gnu.org/licenses/>.
25 #include "sd-messages.h"
35 #include "string-util.h"
37 #include "terminal-util.h"
42 Job
* job_new_raw(Unit
*unit
) {
45 /* used for deserialization */
53 j
->manager
= unit
->manager
;
55 j
->type
= _JOB_TYPE_INVALID
;
60 Job
* job_new(Unit
*unit
, JobType type
) {
63 assert(type
< _JOB_TYPE_MAX
);
65 j
= job_new_raw(unit
);
69 j
->id
= j
->manager
->current_job_id
++;
72 /* We don't link it here, that's what job_dependency() is for */
77 void job_free(Job
*j
) {
79 assert(!j
->installed
);
80 assert(!j
->transaction_prev
);
81 assert(!j
->transaction_next
);
82 assert(!j
->subject_list
);
83 assert(!j
->object_list
);
86 LIST_REMOVE(run_queue
, j
->manager
->run_queue
, j
);
89 LIST_REMOVE(dbus_queue
, j
->manager
->dbus_job_queue
, j
);
91 sd_event_source_unref(j
->timer_event_source
);
93 sd_bus_track_unref(j
->clients
);
94 strv_free(j
->deserialized_clients
);
99 static void job_set_state(Job
*j
, JobState state
) {
102 assert(state
< _JOB_STATE_MAX
);
104 if (j
->state
== state
)
112 if (j
->state
== JOB_RUNNING
)
113 j
->unit
->manager
->n_running_jobs
++;
115 assert(j
->state
== JOB_WAITING
);
116 assert(j
->unit
->manager
->n_running_jobs
> 0);
118 j
->unit
->manager
->n_running_jobs
--;
120 if (j
->unit
->manager
->n_running_jobs
<= 0)
121 j
->unit
->manager
->jobs_in_progress_event_source
= sd_event_source_unref(j
->unit
->manager
->jobs_in_progress_event_source
);
125 void job_uninstall(Job
*j
) {
128 assert(j
->installed
);
130 job_set_state(j
, JOB_WAITING
);
132 pj
= (j
->type
== JOB_NOP
) ? &j
->unit
->nop_job
: &j
->unit
->job
;
135 /* Detach from next 'bigger' objects */
137 /* daemon-reload should be transparent to job observers */
138 if (j
->manager
->n_reloading
<= 0)
139 bus_job_send_removed_signal(j
);
143 unit_add_to_gc_queue(j
->unit
);
145 hashmap_remove(j
->manager
->jobs
, UINT32_TO_PTR(j
->id
));
146 j
->installed
= false;
149 static bool job_type_allows_late_merge(JobType t
) {
150 /* Tells whether it is OK to merge a job of type 't' with an already
152 * Reloads cannot be merged this way. Think of the sequence:
153 * 1. Reload of a daemon is in progress; the daemon has already loaded
154 * its config file, but hasn't completed the reload operation yet.
155 * 2. Edit foo's config file.
156 * 3. Trigger another reload to have the daemon use the new config.
157 * Should the second reload job be merged into the first one, the daemon
158 * would not know about the new config.
159 * JOB_RESTART jobs on the other hand can be merged, because they get
160 * patched into JOB_START after stopping the unit. So if we see a
161 * JOB_RESTART running, it means the unit hasn't stopped yet and at
162 * this time the merge is still allowed. */
163 return t
!= JOB_RELOAD
;
166 static void job_merge_into_installed(Job
*j
, Job
*other
) {
167 assert(j
->installed
);
168 assert(j
->unit
== other
->unit
);
170 if (j
->type
!= JOB_NOP
)
171 job_type_merge_and_collapse(&j
->type
, other
->type
, j
->unit
);
173 assert(other
->type
== JOB_NOP
);
175 j
->override
= j
->override
|| other
->override
;
176 j
->irreversible
= j
->irreversible
|| other
->irreversible
;
177 j
->ignore_order
= j
->ignore_order
|| other
->ignore_order
;
180 Job
* job_install(Job
*j
) {
184 assert(!j
->installed
);
185 assert(j
->type
< _JOB_TYPE_MAX_IN_TRANSACTION
);
186 assert(j
->state
== JOB_WAITING
);
188 pj
= (j
->type
== JOB_NOP
) ? &j
->unit
->nop_job
: &j
->unit
->job
;
192 if (job_type_is_conflicting(uj
->type
, j
->type
))
193 job_finish_and_invalidate(uj
, JOB_CANCELED
, false);
195 /* not conflicting, i.e. mergeable */
197 if (uj
->state
== JOB_WAITING
||
198 (job_type_allows_late_merge(j
->type
) && job_type_is_superset(uj
->type
, j
->type
))) {
199 job_merge_into_installed(uj
, j
);
200 log_unit_debug(uj
->unit
,
201 "Merged into installed job %s/%s as %u",
202 uj
->unit
->id
, job_type_to_string(uj
->type
), (unsigned) uj
->id
);
205 /* already running and not safe to merge into */
206 /* Patch uj to become a merged job and re-run it. */
207 /* XXX It should be safer to queue j to run after uj finishes, but it is
208 * not currently possible to have more than one installed job per unit. */
209 job_merge_into_installed(uj
, j
);
210 log_unit_debug(uj
->unit
,
211 "Merged into running job, re-running: %s/%s as %u",
212 uj
->unit
->id
, job_type_to_string(uj
->type
), (unsigned) uj
->id
);
214 job_set_state(uj
, JOB_WAITING
);
220 /* Install the job */
224 j
->manager
->n_installed_jobs
++;
225 log_unit_debug(j
->unit
,
226 "Installed new job %s/%s as %u",
227 j
->unit
->id
, job_type_to_string(j
->type
), (unsigned) j
->id
);
231 int job_install_deserialized(Job
*j
) {
234 assert(!j
->installed
);
236 if (j
->type
< 0 || j
->type
>= _JOB_TYPE_MAX_IN_TRANSACTION
) {
237 log_debug("Invalid job type %s in deserialization.", strna(job_type_to_string(j
->type
)));
241 pj
= (j
->type
== JOB_NOP
) ? &j
->unit
->nop_job
: &j
->unit
->job
;
243 log_unit_debug(j
->unit
, "Unit already has a job installed. Not installing deserialized job.");
250 if (j
->state
== JOB_RUNNING
)
251 j
->unit
->manager
->n_running_jobs
++;
253 log_unit_debug(j
->unit
,
254 "Reinstalled deserialized job %s/%s as %u",
255 j
->unit
->id
, job_type_to_string(j
->type
), (unsigned) j
->id
);
259 JobDependency
* job_dependency_new(Job
*subject
, Job
*object
, bool matters
, bool conflicts
) {
264 /* Adds a new job link, which encodes that the 'subject' job
265 * needs the 'object' job in some way. If 'subject' is NULL
266 * this means the 'anchor' job (i.e. the one the user
267 * explicitly asked for) is the requester. */
269 if (!(l
= new0(JobDependency
, 1)))
272 l
->subject
= subject
;
274 l
->matters
= matters
;
275 l
->conflicts
= conflicts
;
278 LIST_PREPEND(subject
, subject
->subject_list
, l
);
280 LIST_PREPEND(object
, object
->object_list
, l
);
285 void job_dependency_free(JobDependency
*l
) {
289 LIST_REMOVE(subject
, l
->subject
->subject_list
, l
);
291 LIST_REMOVE(object
, l
->object
->object_list
, l
);
296 void job_dump(Job
*j
, FILE*f
, const char *prefix
) {
305 "%s\tAction: %s -> %s\n"
308 "%s\tIrreversible: %s\n",
310 prefix
, j
->unit
->id
, job_type_to_string(j
->type
),
311 prefix
, job_state_to_string(j
->state
),
312 prefix
, yes_no(j
->override
),
313 prefix
, yes_no(j
->irreversible
));
317 * Merging is commutative, so imagine the matrix as symmetric. We store only
318 * its lower triangle to avoid duplication. We don't store the main diagonal,
319 * because A merged with A is simply A.
321 * If the resulting type is collapsed immediately afterwards (to get rid of
322 * the JOB_RELOAD_OR_START, which lies outside the lookup function's domain),
323 * the following properties hold:
325 * Merging is associative! A merged with B, and then merged with C is the same
326 * as A merged with the result of B merged with C.
328 * Mergeability is transitive! If A can be merged with B and B with C then
331 * Also, if A merged with B cannot be merged with C, then either A or B cannot
332 * be merged with C either.
334 static const JobType job_merging_table
[] = {
335 /* What \ With * JOB_START JOB_VERIFY_ACTIVE JOB_STOP JOB_RELOAD */
336 /*********************************************************************************/
338 /*JOB_VERIFY_ACTIVE */ JOB_START
,
339 /*JOB_STOP */ -1, -1,
340 /*JOB_RELOAD */ JOB_RELOAD_OR_START
, JOB_RELOAD
, -1,
341 /*JOB_RESTART */ JOB_RESTART
, JOB_RESTART
, -1, JOB_RESTART
,
344 JobType
job_type_lookup_merge(JobType a
, JobType b
) {
345 assert_cc(ELEMENTSOF(job_merging_table
) == _JOB_TYPE_MAX_MERGING
* (_JOB_TYPE_MAX_MERGING
- 1) / 2);
346 assert(a
>= 0 && a
< _JOB_TYPE_MAX_MERGING
);
347 assert(b
>= 0 && b
< _JOB_TYPE_MAX_MERGING
);
358 return job_merging_table
[(a
- 1) * a
/ 2 + b
];
361 bool job_type_is_redundant(JobType a
, UnitActiveState b
) {
371 b
== UNIT_INACTIVE
||
374 case JOB_VERIFY_ACTIVE
:
385 b
== UNIT_ACTIVATING
;
391 assert_not_reached("Invalid job type");
395 JobType
job_type_collapse(JobType t
, Unit
*u
) {
400 case JOB_TRY_RESTART
:
401 s
= unit_active_state(u
);
402 if (UNIT_IS_INACTIVE_OR_DEACTIVATING(s
))
407 case JOB_RELOAD_OR_START
:
408 s
= unit_active_state(u
);
409 if (UNIT_IS_INACTIVE_OR_DEACTIVATING(s
))
419 int job_type_merge_and_collapse(JobType
*a
, JobType b
, Unit
*u
) {
422 t
= job_type_lookup_merge(*a
, b
);
426 *a
= job_type_collapse(t
, u
);
430 static bool job_is_runnable(Job
*j
) {
435 assert(j
->installed
);
437 /* Checks whether there is any job running for the units this
438 * job needs to be running after (in the case of a 'positive'
439 * job type) or before (in the case of a 'negative' job
442 /* Note that unit types have a say in what is runnable,
443 * too. For example, if they return -EAGAIN from
444 * unit_start() they can indicate they are not
447 /* First check if there is an override */
451 if (j
->type
== JOB_NOP
)
454 if (j
->type
== JOB_START
||
455 j
->type
== JOB_VERIFY_ACTIVE
||
456 j
->type
== JOB_RELOAD
) {
458 /* Immediate result is that the job is or might be
459 * started. In this case let's wait for the
460 * dependencies, regardless whether they are
461 * starting or stopping something. */
463 SET_FOREACH(other
, j
->unit
->dependencies
[UNIT_AFTER
], i
)
468 /* Also, if something else is being stopped and we should
469 * change state after it, then let's wait. */
471 SET_FOREACH(other
, j
->unit
->dependencies
[UNIT_BEFORE
], i
)
473 (other
->job
->type
== JOB_STOP
||
474 other
->job
->type
== JOB_RESTART
))
477 /* This means that for a service a and a service b where b
478 * shall be started after a:
480 * start a + start b → 1st step start a, 2nd step start b
481 * start a + stop b → 1st step stop b, 2nd step start a
482 * stop a + start b → 1st step stop a, 2nd step start b
483 * stop a + stop b → 1st step stop b, 2nd step stop a
485 * This has the side effect that restarts are properly
486 * synchronized too. */
491 static void job_change_type(Job
*j
, JobType newtype
) {
494 log_unit_debug(j
->unit
,
495 "Converting job %s/%s -> %s/%s",
496 j
->unit
->id
, job_type_to_string(j
->type
),
497 j
->unit
->id
, job_type_to_string(newtype
));
502 static int job_perform_on_unit(Job
**j
) {
503 /* While we execute this operation the job might go away (for
504 * example: because it finishes immediately or is replaced by a new,
505 * conflicting job.) To make sure we don't access a freed job later on
506 * we store the id here, so that we can verify the job is still
508 Manager
*m
= (*j
)->manager
;
509 Unit
*u
= (*j
)->unit
;
510 JobType t
= (*j
)->type
;
511 uint32_t id
= (*j
)->id
;
530 assert_not_reached("Invalid job type");
533 /* Log if the job still exists and the start/stop/reload function
534 * actually did something. */
535 *j
= manager_get_job(m
, id
);
537 unit_status_emit_starting_stopping_reloading(u
, t
);
542 int job_run_and_invalidate(Job
*j
) {
546 assert(j
->installed
);
547 assert(j
->type
< _JOB_TYPE_MAX_IN_TRANSACTION
);
548 assert(j
->in_run_queue
);
550 LIST_REMOVE(run_queue
, j
->manager
->run_queue
, j
);
551 j
->in_run_queue
= false;
553 if (j
->state
!= JOB_WAITING
)
556 if (!job_is_runnable(j
))
559 job_set_state(j
, JOB_RUNNING
);
560 job_add_to_dbus_queue(j
);
565 case JOB_VERIFY_ACTIVE
: {
566 UnitActiveState t
= unit_active_state(j
->unit
);
567 if (UNIT_IS_ACTIVE_OR_RELOADING(t
))
569 else if (t
== UNIT_ACTIVATING
)
579 r
= job_perform_on_unit(&j
);
581 /* If the unit type does not support starting/stopping,
582 * then simply wait. */
588 r
= job_perform_on_unit(&j
);
596 assert_not_reached("Unknown job type");
601 r
= job_finish_and_invalidate(j
, JOB_DONE
, true);
602 else if (r
== -EBADR
)
603 r
= job_finish_and_invalidate(j
, JOB_SKIPPED
, true);
604 else if (r
== -ENOEXEC
)
605 r
= job_finish_and_invalidate(j
, JOB_INVALID
, true);
606 else if (r
== -EPROTO
)
607 r
= job_finish_and_invalidate(j
, JOB_ASSERT
, true);
608 else if (r
== -EOPNOTSUPP
)
609 r
= job_finish_and_invalidate(j
, JOB_UNSUPPORTED
, true);
610 else if (r
== -EAGAIN
)
611 job_set_state(j
, JOB_WAITING
);
613 r
= job_finish_and_invalidate(j
, JOB_FAILED
, true);
619 _pure_
static const char *job_get_status_message_format(Unit
*u
, JobType t
, JobResult result
) {
621 const UnitStatusMessageFormats
*format_table
;
622 static const char *const generic_finished_start_job
[_JOB_RESULT_MAX
] = {
623 [JOB_DONE
] = "Started %s.",
624 [JOB_TIMEOUT
] = "Timed out starting %s.",
625 [JOB_FAILED
] = "Failed to start %s.",
626 [JOB_DEPENDENCY
] = "Dependency failed for %s.",
627 [JOB_ASSERT
] = "Assertion failed for %s.",
628 [JOB_UNSUPPORTED
] = "Starting of %s not supported.",
630 static const char *const generic_finished_stop_job
[_JOB_RESULT_MAX
] = {
631 [JOB_DONE
] = "Stopped %s.",
632 [JOB_FAILED
] = "Stopped (with error) %s.",
633 [JOB_TIMEOUT
] = "Timed out stoppping %s.",
635 static const char *const generic_finished_reload_job
[_JOB_RESULT_MAX
] = {
636 [JOB_DONE
] = "Reloaded %s.",
637 [JOB_FAILED
] = "Reload failed for %s.",
638 [JOB_TIMEOUT
] = "Timed out reloading %s.",
640 /* When verify-active detects the unit is inactive, report it.
641 * Most likely a DEPEND warning from a requisiting unit will
642 * occur next and it's nice to see what was requisited. */
643 static const char *const generic_finished_verify_active_job
[_JOB_RESULT_MAX
] = {
644 [JOB_SKIPPED
] = "%s is not active.",
649 assert(t
< _JOB_TYPE_MAX
);
651 if (t
== JOB_START
|| t
== JOB_STOP
|| t
== JOB_RESTART
) {
652 format_table
= &UNIT_VTABLE(u
)->status_message_formats
;
654 format
= t
== JOB_START
? format_table
->finished_start_job
[result
] :
655 format_table
->finished_stop_job
[result
];
661 /* Return generic strings */
663 return generic_finished_start_job
[result
];
664 else if (t
== JOB_STOP
|| t
== JOB_RESTART
)
665 return generic_finished_stop_job
[result
];
666 else if (t
== JOB_RELOAD
)
667 return generic_finished_reload_job
[result
];
668 else if (t
== JOB_VERIFY_ACTIVE
)
669 return generic_finished_verify_active_job
[result
];
674 static void job_print_status_message(Unit
*u
, JobType t
, JobResult result
) {
676 static const char* const job_result_status_table
[_JOB_RESULT_MAX
] = {
677 [JOB_DONE
] = ANSI_GREEN
" OK " ANSI_NORMAL
,
678 [JOB_TIMEOUT
] = ANSI_HIGHLIGHT_RED
" TIME " ANSI_NORMAL
,
679 [JOB_FAILED
] = ANSI_HIGHLIGHT_RED
"FAILED" ANSI_NORMAL
,
680 [JOB_DEPENDENCY
] = ANSI_HIGHLIGHT_YELLOW
"DEPEND" ANSI_NORMAL
,
681 [JOB_SKIPPED
] = ANSI_HIGHLIGHT
" INFO " ANSI_NORMAL
,
682 [JOB_ASSERT
] = ANSI_HIGHLIGHT_YELLOW
"ASSERT" ANSI_NORMAL
,
683 [JOB_UNSUPPORTED
] = ANSI_HIGHLIGHT_YELLOW
"UNSUPP" ANSI_NORMAL
,
688 assert(t
< _JOB_TYPE_MAX
);
690 format
= job_get_status_message_format(u
, t
, result
);
694 if (result
!= JOB_DONE
)
695 manager_flip_auto_status(u
->manager
, true);
697 DISABLE_WARNING_FORMAT_NONLITERAL
;
698 unit_status_printf(u
, job_result_status_table
[result
], format
);
701 if (t
== JOB_START
&& result
== JOB_FAILED
) {
702 _cleanup_free_
char *quoted
= shell_maybe_quote(u
->id
);
704 manager_status_printf(u
->manager
, STATUS_TYPE_NORMAL
, NULL
,
705 "See 'systemctl status %s' for details.", strna(quoted
));
709 static void job_log_status_message(Unit
*u
, JobType t
, JobResult result
) {
713 static const int job_result_log_level
[_JOB_RESULT_MAX
] = {
714 [JOB_DONE
] = LOG_INFO
,
715 [JOB_CANCELED
] = LOG_INFO
,
716 [JOB_TIMEOUT
] = LOG_ERR
,
717 [JOB_FAILED
] = LOG_ERR
,
718 [JOB_DEPENDENCY
] = LOG_WARNING
,
719 [JOB_SKIPPED
] = LOG_NOTICE
,
720 [JOB_INVALID
] = LOG_INFO
,
721 [JOB_ASSERT
] = LOG_WARNING
,
722 [JOB_UNSUPPORTED
] = LOG_WARNING
,
727 assert(t
< _JOB_TYPE_MAX
);
729 /* Skip this if it goes to the console. since we already print
730 * to the console anyway... */
732 if (log_on_console())
735 format
= job_get_status_message_format(u
, t
, result
);
739 DISABLE_WARNING_FORMAT_NONLITERAL
;
740 snprintf(buf
, sizeof(buf
), format
, unit_description(u
));
744 mid
= result
== JOB_DONE
? SD_MESSAGE_UNIT_STARTED
: SD_MESSAGE_UNIT_FAILED
;
745 else if (t
== JOB_STOP
|| t
== JOB_RESTART
)
746 mid
= SD_MESSAGE_UNIT_STOPPED
;
747 else if (t
== JOB_RELOAD
)
748 mid
= SD_MESSAGE_UNIT_RELOADED
;
750 log_struct(job_result_log_level
[result
],
752 LOG_MESSAGE("%s", buf
),
753 "RESULT=%s", job_result_to_string(result
),
758 log_struct(job_result_log_level
[result
],
761 LOG_MESSAGE("%s", buf
),
762 "RESULT=%s", job_result_to_string(result
),
766 static void job_emit_status_message(Unit
*u
, JobType t
, JobResult result
) {
768 /* No message if the job did not actually do anything due to failed condition. */
769 if (t
== JOB_START
&& result
== JOB_DONE
&& !u
->condition_result
)
772 job_log_status_message(u
, t
, result
);
774 /* Reload status messages have traditionally not been printed to console. */
776 job_print_status_message(u
, t
, result
);
779 static void job_fail_dependencies(Unit
*u
, UnitDependency d
) {
785 SET_FOREACH(other
, u
->dependencies
[d
], i
) {
790 if (!IN_SET(j
->type
, JOB_START
, JOB_VERIFY_ACTIVE
))
793 job_finish_and_invalidate(j
, JOB_DEPENDENCY
, true);
797 int job_finish_and_invalidate(Job
*j
, JobResult result
, bool recursive
) {
804 assert(j
->installed
);
805 assert(j
->type
< _JOB_TYPE_MAX_IN_TRANSACTION
);
812 log_unit_debug(u
, "Job %s/%s finished, result=%s", u
->id
, job_type_to_string(t
), job_result_to_string(result
));
814 job_emit_status_message(u
, t
, result
);
816 job_add_to_dbus_queue(j
);
818 /* Patch restart jobs so that they become normal start jobs */
819 if (result
== JOB_DONE
&& t
== JOB_RESTART
) {
821 job_change_type(j
, JOB_START
);
822 job_set_state(j
, JOB_WAITING
);
824 job_add_to_run_queue(j
);
829 if (result
== JOB_FAILED
|| result
== JOB_INVALID
)
830 j
->manager
->n_failed_jobs
++;
835 /* Fail depending jobs on failure */
836 if (result
!= JOB_DONE
&& recursive
) {
837 if (IN_SET(t
, JOB_START
, JOB_VERIFY_ACTIVE
)) {
838 job_fail_dependencies(u
, UNIT_REQUIRED_BY
);
839 job_fail_dependencies(u
, UNIT_REQUISITE_OF
);
840 job_fail_dependencies(u
, UNIT_BOUND_BY
);
841 job_fail_dependencies(u
, UNIT_REQUIRED_BY_OVERRIDABLE
);
842 job_fail_dependencies(u
, UNIT_REQUISITE_OF_OVERRIDABLE
);
843 } else if (t
== JOB_STOP
)
844 job_fail_dependencies(u
, UNIT_CONFLICTED_BY
);
847 /* Trigger OnFailure dependencies that are not generated by
848 * the unit itself. We don't treat JOB_CANCELED as failure in
849 * this context. And JOB_FAILURE is already handled by the
851 if (result
== JOB_TIMEOUT
|| result
== JOB_DEPENDENCY
) {
852 log_struct(LOG_NOTICE
,
853 "JOB_TYPE=%s", job_type_to_string(t
),
854 "JOB_RESULT=%s", job_result_to_string(result
),
856 LOG_UNIT_MESSAGE(u
, "Job %s/%s failed with result '%s'.",
858 job_type_to_string(t
),
859 job_result_to_string(result
)),
862 unit_start_on_failure(u
);
865 unit_trigger_notify(u
);
868 /* Try to start the next jobs that can be started */
869 SET_FOREACH(other
, u
->dependencies
[UNIT_AFTER
], i
)
871 job_add_to_run_queue(other
->job
);
872 SET_FOREACH(other
, u
->dependencies
[UNIT_BEFORE
], i
)
874 job_add_to_run_queue(other
->job
);
876 manager_check_finished(u
->manager
);
881 static int job_dispatch_timer(sd_event_source
*s
, uint64_t monotonic
, void *userdata
) {
886 assert(s
== j
->timer_event_source
);
888 log_unit_warning(j
->unit
, "Job %s/%s timed out.", j
->unit
->id
, job_type_to_string(j
->type
));
891 job_finish_and_invalidate(j
, JOB_TIMEOUT
, true);
893 failure_action(u
->manager
, u
->job_timeout_action
, u
->job_timeout_reboot_arg
);
898 int job_start_timer(Job
*j
) {
901 if (j
->timer_event_source
)
904 j
->begin_usec
= now(CLOCK_MONOTONIC
);
906 if (j
->unit
->job_timeout
<= 0)
909 r
= sd_event_add_time(
911 &j
->timer_event_source
,
913 j
->begin_usec
+ j
->unit
->job_timeout
, 0,
914 job_dispatch_timer
, j
);
918 (void) sd_event_source_set_description(j
->timer_event_source
, "job-start");
923 void job_add_to_run_queue(Job
*j
) {
925 assert(j
->installed
);
930 if (!j
->manager
->run_queue
)
931 sd_event_source_set_enabled(j
->manager
->run_queue_event_source
, SD_EVENT_ONESHOT
);
933 LIST_PREPEND(run_queue
, j
->manager
->run_queue
, j
);
934 j
->in_run_queue
= true;
937 void job_add_to_dbus_queue(Job
*j
) {
939 assert(j
->installed
);
941 if (j
->in_dbus_queue
)
944 /* We don't check if anybody is subscribed here, since this
945 * job might just have been created and not yet assigned to a
946 * connection/client. */
948 LIST_PREPEND(dbus_queue
, j
->manager
->dbus_job_queue
, j
);
949 j
->in_dbus_queue
= true;
952 char *job_dbus_path(Job
*j
) {
957 if (asprintf(&p
, "/org/freedesktop/systemd1/job/%"PRIu32
, j
->id
) < 0)
963 int job_serialize(Job
*j
, FILE *f
, FDSet
*fds
) {
964 fprintf(f
, "job-id=%u\n", j
->id
);
965 fprintf(f
, "job-type=%s\n", job_type_to_string(j
->type
));
966 fprintf(f
, "job-state=%s\n", job_state_to_string(j
->state
));
967 fprintf(f
, "job-override=%s\n", yes_no(j
->override
));
968 fprintf(f
, "job-irreversible=%s\n", yes_no(j
->irreversible
));
969 fprintf(f
, "job-sent-dbus-new-signal=%s\n", yes_no(j
->sent_dbus_new_signal
));
970 fprintf(f
, "job-ignore-order=%s\n", yes_no(j
->ignore_order
));
972 if (j
->begin_usec
> 0)
973 fprintf(f
, "job-begin="USEC_FMT
"\n", j
->begin_usec
);
975 bus_track_serialize(j
->clients
, f
);
982 int job_deserialize(Job
*j
, FILE *f
, FDSet
*fds
) {
986 char line
[LINE_MAX
], *l
, *v
;
989 if (!fgets(line
, sizeof(line
), f
)) {
1002 k
= strcspn(l
, "=");
1010 if (streq(l
, "job-id")) {
1012 if (safe_atou32(v
, &j
->id
) < 0)
1013 log_debug("Failed to parse job id value %s", v
);
1015 } else if (streq(l
, "job-type")) {
1018 t
= job_type_from_string(v
);
1020 log_debug("Failed to parse job type %s", v
);
1021 else if (t
>= _JOB_TYPE_MAX_IN_TRANSACTION
)
1022 log_debug("Cannot deserialize job of type %s", v
);
1026 } else if (streq(l
, "job-state")) {
1029 s
= job_state_from_string(v
);
1031 log_debug("Failed to parse job state %s", v
);
1033 job_set_state(j
, s
);
1035 } else if (streq(l
, "job-override")) {
1038 b
= parse_boolean(v
);
1040 log_debug("Failed to parse job override flag %s", v
);
1042 j
->override
= j
->override
|| b
;
1044 } else if (streq(l
, "job-irreversible")) {
1047 b
= parse_boolean(v
);
1049 log_debug("Failed to parse job irreversible flag %s", v
);
1051 j
->irreversible
= j
->irreversible
|| b
;
1053 } else if (streq(l
, "job-sent-dbus-new-signal")) {
1056 b
= parse_boolean(v
);
1058 log_debug("Failed to parse job sent_dbus_new_signal flag %s", v
);
1060 j
->sent_dbus_new_signal
= j
->sent_dbus_new_signal
|| b
;
1062 } else if (streq(l
, "job-ignore-order")) {
1065 b
= parse_boolean(v
);
1067 log_debug("Failed to parse job ignore_order flag %s", v
);
1069 j
->ignore_order
= j
->ignore_order
|| b
;
1071 } else if (streq(l
, "job-begin")) {
1072 unsigned long long ull
;
1074 if (sscanf(v
, "%llu", &ull
) != 1)
1075 log_debug("Failed to parse job-begin value %s", v
);
1077 j
->begin_usec
= ull
;
1079 } else if (streq(l
, "subscribed")) {
1081 if (strv_extend(&j
->deserialized_clients
, v
) < 0)
1087 int job_coldplug(Job
*j
) {
1092 /* After deserialization is complete and the bus connection
1093 * set up again, let's start watching our subscribers again */
1094 r
= bus_track_coldplug(j
->manager
, &j
->clients
, &j
->deserialized_clients
);
1098 if (j
->state
== JOB_WAITING
)
1099 job_add_to_run_queue(j
);
1101 if (j
->begin_usec
== 0 || j
->unit
->job_timeout
== 0)
1104 if (j
->timer_event_source
)
1105 j
->timer_event_source
= sd_event_source_unref(j
->timer_event_source
);
1107 r
= sd_event_add_time(
1109 &j
->timer_event_source
,
1111 j
->begin_usec
+ j
->unit
->job_timeout
, 0,
1112 job_dispatch_timer
, j
);
1114 log_debug_errno(r
, "Failed to restart timeout for job: %m");
1116 (void) sd_event_source_set_description(j
->timer_event_source
, "job-timeout");
1121 void job_shutdown_magic(Job
*j
) {
1124 /* The shutdown target gets some special treatment here: we
1125 * tell the kernel to begin with flushing its disk caches, to
1126 * optimize shutdown time a bit. Ideally we wouldn't hardcode
1127 * this magic into PID 1. However all other processes aren't
1128 * options either since they'd exit much sooner than PID 1 and
1129 * asynchronous sync() would cause their exit to be
1132 if (j
->type
!= JOB_START
)
1135 if (j
->unit
->manager
->running_as
!= MANAGER_SYSTEM
)
1138 if (!unit_has_name(j
->unit
, SPECIAL_SHUTDOWN_TARGET
))
1141 /* In case messages on console has been disabled on boot */
1142 j
->unit
->manager
->no_console_output
= false;
1144 if (detect_container() > 0)
1147 asynchronous_sync();
1150 int job_get_timeout(Job
*j
, uint64_t *timeout
) {
1152 uint64_t x
= -1, y
= -1;
1157 if (j
->timer_event_source
) {
1158 r
= sd_event_source_get_time(j
->timer_event_source
, &x
);
1164 if (UNIT_VTABLE(u
)->get_timeout
) {
1165 q
= UNIT_VTABLE(u
)->get_timeout(u
, &y
);
1170 if (r
== 0 && q
== 0)
1173 *timeout
= MIN(x
, y
);
1178 static const char* const job_state_table
[_JOB_STATE_MAX
] = {
1179 [JOB_WAITING
] = "waiting",
1180 [JOB_RUNNING
] = "running"
1183 DEFINE_STRING_TABLE_LOOKUP(job_state
, JobState
);
1185 static const char* const job_type_table
[_JOB_TYPE_MAX
] = {
1186 [JOB_START
] = "start",
1187 [JOB_VERIFY_ACTIVE
] = "verify-active",
1188 [JOB_STOP
] = "stop",
1189 [JOB_RELOAD
] = "reload",
1190 [JOB_RELOAD_OR_START
] = "reload-or-start",
1191 [JOB_RESTART
] = "restart",
1192 [JOB_TRY_RESTART
] = "try-restart",
1196 DEFINE_STRING_TABLE_LOOKUP(job_type
, JobType
);
1198 static const char* const job_mode_table
[_JOB_MODE_MAX
] = {
1199 [JOB_FAIL
] = "fail",
1200 [JOB_REPLACE
] = "replace",
1201 [JOB_REPLACE_IRREVERSIBLY
] = "replace-irreversibly",
1202 [JOB_ISOLATE
] = "isolate",
1203 [JOB_FLUSH
] = "flush",
1204 [JOB_IGNORE_DEPENDENCIES
] = "ignore-dependencies",
1205 [JOB_IGNORE_REQUIREMENTS
] = "ignore-requirements",
1208 DEFINE_STRING_TABLE_LOOKUP(job_mode
, JobMode
);
1210 static const char* const job_result_table
[_JOB_RESULT_MAX
] = {
1211 [JOB_DONE
] = "done",
1212 [JOB_CANCELED
] = "canceled",
1213 [JOB_TIMEOUT
] = "timeout",
1214 [JOB_FAILED
] = "failed",
1215 [JOB_DEPENDENCY
] = "dependency",
1216 [JOB_SKIPPED
] = "skipped",
1217 [JOB_INVALID
] = "invalid",
1218 [JOB_ASSERT
] = "assert",
1219 [JOB_UNSUPPORTED
] = "unsupported",
1222 DEFINE_STRING_TABLE_LOOKUP(job_result
, JobResult
);