diff options
Diffstat (limited to 'litmus/jobs.c')
-rw-r--r-- | litmus/jobs.c | 82 |
1 files changed, 82 insertions, 0 deletions
diff --git a/litmus/jobs.c b/litmus/jobs.c new file mode 100644 index 000000000000..0dd36b9343d6 --- /dev/null +++ b/litmus/jobs.c | |||
@@ -0,0 +1,82 @@ | |||
1 | /* litmus/jobs.c - common job control code | ||
2 | */ | ||
3 | |||
4 | #include <linux/sched.h> | ||
5 | |||
6 | #include <litmus/preempt.h> | ||
7 | #include <litmus/litmus.h> | ||
8 | #include <litmus/sched_plugin.h> | ||
9 | #include <litmus/jobs.h> | ||
10 | |||
11 | static inline void setup_release(struct task_struct *t, lt_t release) | ||
12 | { | ||
13 | /* prepare next release */ | ||
14 | t->rt_param.job_params.release = release; | ||
15 | t->rt_param.job_params.deadline = release + get_rt_relative_deadline(t); | ||
16 | t->rt_param.job_params.exec_time = 0; | ||
17 | |||
18 | /* update job sequence number */ | ||
19 | t->rt_param.job_params.job_no++; | ||
20 | } | ||
21 | |||
22 | void prepare_for_next_period(struct task_struct *t) | ||
23 | { | ||
24 | BUG_ON(!t); | ||
25 | |||
26 | /* Record lateness before we set up the next job's | ||
27 | * release and deadline. Lateness may be negative. | ||
28 | */ | ||
29 | t->rt_param.job_params.lateness = | ||
30 | (long long)litmus_clock() - | ||
31 | (long long)t->rt_param.job_params.deadline; | ||
32 | |||
33 | if (tsk_rt(t)->sporadic_release) { | ||
34 | TRACE_TASK(t, "sporadic release at %llu\n", | ||
35 | tsk_rt(t)->sporadic_release_time); | ||
36 | /* sporadic release */ | ||
37 | setup_release(t, tsk_rt(t)->sporadic_release_time); | ||
38 | tsk_rt(t)->sporadic_release = 0; | ||
39 | } else { | ||
40 | /* periodic release => add period */ | ||
41 | setup_release(t, get_release(t) + get_rt_period(t)); | ||
42 | } | ||
43 | } | ||
44 | |||
45 | void release_at(struct task_struct *t, lt_t start) | ||
46 | { | ||
47 | BUG_ON(!t); | ||
48 | setup_release(t, start); | ||
49 | tsk_rt(t)->completed = 0; | ||
50 | } | ||
51 | |||
52 | long default_wait_for_release_at(lt_t release_time) | ||
53 | { | ||
54 | struct task_struct *t = current; | ||
55 | unsigned long flags; | ||
56 | |||
57 | local_irq_save(flags); | ||
58 | tsk_rt(t)->sporadic_release_time = release_time; | ||
59 | smp_wmb(); | ||
60 | tsk_rt(t)->sporadic_release = 1; | ||
61 | local_irq_restore(flags); | ||
62 | |||
63 | return litmus->complete_job(); | ||
64 | } | ||
65 | |||
66 | |||
67 | /* | ||
68 | * Deactivate current task until the beginning of the next period. | ||
69 | */ | ||
70 | long complete_job(void) | ||
71 | { | ||
72 | preempt_disable(); | ||
73 | TRACE_CUR("job completion indicated at %llu\n", litmus_clock()); | ||
74 | /* Mark that we do not excute anymore */ | ||
75 | tsk_rt(current)->completed = 1; | ||
76 | /* call schedule, this will return when a new job arrives | ||
77 | * it also takes care of preparing for the next release | ||
78 | */ | ||
79 | litmus_reschedule_local(); | ||
80 | preempt_enable(); | ||
81 | return 0; | ||
82 | } | ||