summaryrefslogtreecommitdiff
path: root/src/core/job.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/core/job.c')
-rw-r--r--src/core/job.c38
1 files changed, 31 insertions, 7 deletions
diff --git a/src/core/job.c b/src/core/job.c
index a02f1bb2bc..5067006d63 100644
--- a/src/core/job.c
+++ b/src/core/job.c
@@ -576,6 +576,7 @@ int job_run_and_invalidate(Job *j) {
if (!job_is_runnable(j))
return -EAGAIN;
+ job_start_timer(j, true);
job_set_state(j, JOB_RUNNING);
job_add_to_dbus_queue(j);
@@ -949,22 +950,45 @@ static int job_dispatch_timer(sd_event_source *s, uint64_t monotonic, void *user
return 0;
}
-int job_start_timer(Job *j) {
+int job_start_timer(Job *j, bool job_running) {
int r;
+ usec_t run_begin, timeout_time, old_timeout_time;
- if (j->timer_event_source)
- return 0;
+ if (job_running) {
+ if (j->unit->job_running_timeout == USEC_INFINITY)
+ return 0;
- j->begin_usec = now(CLOCK_MONOTONIC);
+ run_begin = now(CLOCK_MONOTONIC);
+ timeout_time = usec_add(run_begin, j->unit->job_running_timeout);
- if (j->unit->job_timeout == USEC_INFINITY)
- return 0;
+ if (j->timer_event_source) {
+ /* Update only if JobRunningTimeoutSec= results in earlier timeout */
+ r = sd_event_source_get_time(j->timer_event_source, &old_timeout_time);
+ if (r < 0)
+ return r;
+
+ if (old_timeout_time <= timeout_time)
+ return 0;
+
+ return sd_event_source_set_time(j->timer_event_source, timeout_time);
+ }
+ } else {
+ if (j->timer_event_source)
+ return 0;
+
+ j->begin_usec = now(CLOCK_MONOTONIC);
+
+ if (j->unit->job_timeout == USEC_INFINITY)
+ return 0;
+
+ timeout_time = usec_add(j->begin_usec, j->unit->job_timeout);
+ }
r = sd_event_add_time(
j->manager->event,
&j->timer_event_source,
CLOCK_MONOTONIC,
- usec_add(j->begin_usec, j->unit->job_timeout), 0,
+ timeout_time, 0,
job_dispatch_timer, j);
if (r < 0)
return r;