aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorChristopher Kenna <cjk@cs.unc.edu>2012-09-29 19:21:50 -0400
committerChristopher Kenna <cjk@cs.unc.edu>2012-09-29 19:21:59 -0400
commit6dde5b36ab5da446976d529d2038a2451a77e347 (patch)
treef6aaa99b3d908dbbc8b0fe2273d84d114a3fcca7
parentfe23bc6b4d29552409354ed74a0b066a6fc647cb (diff)
parentfb90f3b6a8a604a9aed7249045bfed77ce42de5b (diff)
Merge in Jonathan's tracing fixes from branch wip-rt-kshark.
-rw-r--r--include/litmus/litmus.h5
-rw-r--r--include/litmus/rt_param.h6
-rw-r--r--include/litmus/sched_trace.h103
-rw-r--r--include/trace/events/litmus.h254
-rw-r--r--include/trace/ftrace.h5
-rw-r--r--litmus/jobs.c26
-rw-r--r--litmus/litmus.c2
-rw-r--r--litmus/preempt.c8
-rw-r--r--litmus/sched_task_trace.c30
9 files changed, 394 insertions, 45 deletions
diff --git a/include/litmus/litmus.h b/include/litmus/litmus.h
index 807b7888695..3e78b9c6158 100644
--- a/include/litmus/litmus.h
+++ b/include/litmus/litmus.h
@@ -57,10 +57,11 @@ void litmus_exit_task(struct task_struct *tsk);
57#define get_rt_phase(t) (tsk_rt(t)->task_params.phase) 57#define get_rt_phase(t) (tsk_rt(t)->task_params.phase)
58#define get_partition(t) (tsk_rt(t)->task_params.cpu) 58#define get_partition(t) (tsk_rt(t)->task_params.cpu)
59#define get_priority(t) (tsk_rt(t)->task_params.priority) 59#define get_priority(t) (tsk_rt(t)->task_params.priority)
60#define get_class(t) (tsk_rt(t)->task_params.cls) 60#define get_class(t) (tsk_rt(t)->task_params.cls)
61 61
62/* job_param macros */ 62/* job_param macros */
63#define get_exec_time(t) (tsk_rt(t)->job_params.exec_time) 63#define get_job_no(t) (tsk_rt(t)->job_params.job_no)
64#define get_exec_time(t) (tsk_rt(t)->job_params.exec_time)
64#define get_deadline(t) (tsk_rt(t)->job_params.deadline) 65#define get_deadline(t) (tsk_rt(t)->job_params.deadline)
65#define get_release(t) (tsk_rt(t)->job_params.release) 66#define get_release(t) (tsk_rt(t)->job_params.release)
66#define get_lateness(t) (tsk_rt(t)->job_params.lateness) 67#define get_lateness(t) (tsk_rt(t)->job_params.lateness)
diff --git a/include/litmus/rt_param.h b/include/litmus/rt_param.h
index fac939dbd33..20268190757 100644
--- a/include/litmus/rt_param.h
+++ b/include/litmus/rt_param.h
@@ -225,6 +225,12 @@ struct rt_param {
225 225
226 /* Pointer to the page shared between userspace and kernel. */ 226 /* Pointer to the page shared between userspace and kernel. */
227 struct control_page * ctrl_page; 227 struct control_page * ctrl_page;
228
229 lt_t total_tardy;
230 lt_t max_tardy;
231 unsigned int missed;
232 lt_t max_exec_time;
233 lt_t tot_exec_time;
228}; 234};
229 235
230/* Possible RT flags */ 236/* Possible RT flags */
diff --git a/include/litmus/sched_trace.h b/include/litmus/sched_trace.h
index 82bde824129..2f992789aff 100644
--- a/include/litmus/sched_trace.h
+++ b/include/litmus/sched_trace.h
@@ -80,6 +80,17 @@ struct st_sys_release_data {
80 u64 release; 80 u64 release;
81}; 81};
82 82
83struct st_task_exit_data {
84 u64 avg_exec_time;
85 u64 max_exec_time;
86};
87
88struct st_task_tardy_data {
89 u64 total_tardy;
90 u32 max_tardy;
91 u32 missed;
92};
93
83#define DATA(x) struct st_ ## x ## _data x; 94#define DATA(x) struct st_ ## x ## _data x;
84 95
85typedef enum { 96typedef enum {
@@ -94,7 +105,9 @@ typedef enum {
94 ST_BLOCK, 105 ST_BLOCK,
95 ST_RESUME, 106 ST_RESUME,
96 ST_ACTION, 107 ST_ACTION,
97 ST_SYS_RELEASE 108 ST_SYS_RELEASE,
109 ST_TASK_EXIT,
110 ST_TASK_TARDY,
98} st_event_record_type_t; 111} st_event_record_type_t;
99 112
100struct st_event_record { 113struct st_event_record {
@@ -113,6 +126,8 @@ struct st_event_record {
113 DATA(resume); 126 DATA(resume);
114 DATA(action); 127 DATA(action);
115 DATA(sys_release); 128 DATA(sys_release);
129 DATA(task_exit);
130 DATA(task_tardy);
116 } data; 131 } data;
117}; 132};
118 133
@@ -154,6 +169,10 @@ feather_callback void do_sched_trace_action(unsigned long id,
154 unsigned long action); 169 unsigned long action);
155feather_callback void do_sched_trace_sys_release(unsigned long id, 170feather_callback void do_sched_trace_sys_release(unsigned long id,
156 lt_t* start); 171 lt_t* start);
172feather_callback void do_sched_trace_task_exit(unsigned long id,
173 struct task_struct* task);
174feather_callback void do_sched_trace_task_tardy(unsigned long id,
175 struct task_struct* task);
157 176
158#endif 177#endif
159 178
@@ -179,6 +198,15 @@ feather_callback void do_sched_trace_sys_release(unsigned long id,
179#define trace_litmus_task_block(t) 198#define trace_litmus_task_block(t)
180#define trace_litmus_task_resume(t) 199#define trace_litmus_task_resume(t)
181#define trace_litmus_sys_release(start) 200#define trace_litmus_sys_release(start)
201#define trace_litmus_task_exit(t)
202#define trace_litmus_task_tardy(t)
203
204#define trace_litmus_container_param(cid, name)
205#define trace_litmus_server_param(sid, cid, wcet, time)
206#define trace_litmus_server_switch_to(sid, job, tid)
207#define trace_litmus_server_switch_away(sid, job, tid)
208#define trace_litmus_server_release(sid, job, release, deadline)
209#define trace_litmus_server_completion(sid, job)
182 210
183#endif 211#endif
184 212
@@ -226,18 +254,34 @@ feather_callback void do_sched_trace_sys_release(unsigned long id,
226 trace_litmus_task_completion(t, forced); \ 254 trace_litmus_task_completion(t, forced); \
227 } while (0) 255 } while (0)
228 256
229#define sched_trace_task_block(t) \ 257#define sched_trace_task_block_on(t, i) \
230 do { \ 258 do { \
231 SCHED_TRACE(SCHED_TRACE_BASE_ID + 7, \ 259 SCHED_TRACE(SCHED_TRACE_BASE_ID + 7, \
232 do_sched_trace_task_block, t); \ 260 do_sched_trace_task_block, t); \
233 trace_litmus_task_block(t); \ 261 trace_litmus_task_block(t, i); \
234 } while (0) 262 } while (0)
235 263
236#define sched_trace_task_resume(t) \ 264#define sched_trace_task_block(t) \
265 sched_trace_task_block_on(t, 0)
266
267#define sched_trace_task_resume_on(t, i) \
237 do { \ 268 do { \
238 SCHED_TRACE(SCHED_TRACE_BASE_ID + 8, \ 269 SCHED_TRACE(SCHED_TRACE_BASE_ID + 8, \
239 do_sched_trace_task_resume, t); \ 270 do_sched_trace_task_resume, t); \
240 trace_litmus_task_resume(t); \ 271 trace_litmus_task_resume(t, i); \
272 } while (0)
273
274#define sched_trace_task_resume(t) \
275 sched_trace_task_resume_on(t, 0)
276
277#define sched_trace_resource_acquire(t, i) \
278 do { \
279 trace_litmus_resource_acquire(t, i); \
280 } while (0)
281
282#define sched_trace_resource_released(t, i) \
283 do { \
284 trace_litmus_resource_released(t, i); \
241 } while (0) 285 } while (0)
242 286
243#define sched_trace_action(t, action) \ 287#define sched_trace_action(t, action) \
@@ -252,6 +296,55 @@ feather_callback void do_sched_trace_sys_release(unsigned long id,
252 trace_litmus_sys_release(when); \ 296 trace_litmus_sys_release(when); \
253 } while (0) 297 } while (0)
254 298
299#define sched_trace_task_exit(t) \
300 do { \
301 SCHED_TRACE(SCHED_TRACE_BASE_ID + 11, \
302 do_sched_trace_task_exit, t); \
303 trace_litmus_task_exit(t); \
304 } while (0)
305
306
307#define sched_trace_task_tardy(t) \
308 do { \
309 SCHED_TRACE(SCHED_TRACE_BASE_ID + 12, \
310 do_sched_trace_task_tardy, t); \
311 } while (0)
312
313#define QT_START lt_t _qt_start = litmus_clock()
314#define QT_END \
315 sched_trace_log_message("%d P%d [%s@%s:%d]: Took %llu\n\n", \
316 TRACE_ARGS, litmus_clock() - _qt_start)
317
318#define sched_trace_container_param(cid, name) \
319 do { \
320 trace_litmus_container_param(cid, name); \
321 } while (0)
322
323#define sched_trace_server_param(sid, cid, wcet, period) \
324 do { \
325 trace_litmus_server_param(sid, cid, wcet, period); \
326 } while(0)
327
328#define sched_trace_server_switch_to(sid, job, tid) \
329 do { \
330 trace_litmus_server_switch_to(sid, job, tid); \
331 } while(0)
332
333#define sched_trace_server_switch_away(sid, job, tid) \
334 do { \
335 trace_litmus_server_switch_away(sid, job, tid); \
336 } while (0)
337
338#define sched_trace_server_release(sid, job, rel, dead) \
339 do { \
340 trace_litmus_server_release(sid, job, rel, dead); \
341 } while (0)
342
343#define sched_trace_server_completion(sid, job) \
344 do { \
345 trace_litmus_server_completion(sid, job); \
346 } while (0)
347
255#define sched_trace_quantum_boundary() /* NOT IMPLEMENTED */ 348#define sched_trace_quantum_boundary() /* NOT IMPLEMENTED */
256 349
257#endif /* __KERNEL__ */ 350#endif /* __KERNEL__ */
diff --git a/include/trace/events/litmus.h b/include/trace/events/litmus.h
index 0fffcee02be..c3a92f8ec6e 100644
--- a/include/trace/events/litmus.h
+++ b/include/trace/events/litmus.h
@@ -11,10 +11,6 @@
11 11
12#include <litmus/litmus.h> 12#include <litmus/litmus.h>
13#include <litmus/rt_param.h> 13#include <litmus/rt_param.h>
14
15/*
16 * Tracing task admission
17 */
18TRACE_EVENT(litmus_task_param, 14TRACE_EVENT(litmus_task_param,
19 15
20 TP_PROTO(struct task_struct *t), 16 TP_PROTO(struct task_struct *t),
@@ -24,9 +20,9 @@ TRACE_EVENT(litmus_task_param,
24 TP_STRUCT__entry( 20 TP_STRUCT__entry(
25 __field( pid_t, pid ) 21 __field( pid_t, pid )
26 __field( unsigned int, job ) 22 __field( unsigned int, job )
27 __field( lt_t, wcet ) 23 __field( unsigned long long, wcet )
28 __field( lt_t, period ) 24 __field( unsigned long long, period )
29 __field( lt_t, phase ) 25 __field( unsigned long long, phase )
30 __field( int, partition ) 26 __field( int, partition )
31 ), 27 ),
32 28
@@ -56,8 +52,8 @@ TRACE_EVENT(litmus_task_release,
56 TP_STRUCT__entry( 52 TP_STRUCT__entry(
57 __field( pid_t, pid ) 53 __field( pid_t, pid )
58 __field( unsigned int, job ) 54 __field( unsigned int, job )
59 __field( lt_t, release ) 55 __field( unsigned long long, release )
60 __field( lt_t, deadline ) 56 __field( unsigned long long, deadline )
61 ), 57 ),
62 58
63 TP_fast_assign( 59 TP_fast_assign(
@@ -84,8 +80,8 @@ TRACE_EVENT(litmus_switch_to,
84 TP_STRUCT__entry( 80 TP_STRUCT__entry(
85 __field( pid_t, pid ) 81 __field( pid_t, pid )
86 __field( unsigned int, job ) 82 __field( unsigned int, job )
87 __field( lt_t, when ) 83 __field( unsigned long long, when )
88 __field( lt_t, exec_time ) 84 __field( unsigned long long, exec_time )
89 ), 85 ),
90 86
91 TP_fast_assign( 87 TP_fast_assign(
@@ -112,8 +108,8 @@ TRACE_EVENT(litmus_switch_away,
112 TP_STRUCT__entry( 108 TP_STRUCT__entry(
113 __field( pid_t, pid ) 109 __field( pid_t, pid )
114 __field( unsigned int, job ) 110 __field( unsigned int, job )
115 __field( lt_t, when ) 111 __field( unsigned long long, when )
116 __field( lt_t, exec_time ) 112 __field( unsigned long long, exec_time )
117 ), 113 ),
118 114
119 TP_fast_assign( 115 TP_fast_assign(
@@ -140,7 +136,7 @@ TRACE_EVENT(litmus_task_completion,
140 TP_STRUCT__entry( 136 TP_STRUCT__entry(
141 __field( pid_t, pid ) 137 __field( pid_t, pid )
142 __field( unsigned int, job ) 138 __field( unsigned int, job )
143 __field( lt_t, when ) 139 __field( unsigned long long, when )
144 __field( unsigned long, forced ) 140 __field( unsigned long, forced )
145 ), 141 ),
146 142
@@ -161,21 +157,71 @@ TRACE_EVENT(litmus_task_completion,
161 */ 157 */
162TRACE_EVENT(litmus_task_block, 158TRACE_EVENT(litmus_task_block,
163 159
164 TP_PROTO(struct task_struct *t), 160 TP_PROTO(struct task_struct *t, int lid),
165 161
166 TP_ARGS(t), 162 TP_ARGS(t, lid),
163
164 TP_STRUCT__entry(
165 __field( pid_t, pid )
166 __field( int, lid )
167 __field( unsigned long long, when )
168 ),
169
170 TP_fast_assign(
171 __entry->pid = t ? t->pid : 0;
172 __entry->lid = lid;
173 __entry->when = litmus_clock();
174 ),
175
176 TP_printk("(%u) blocks on %d: %Lu\n", __entry->pid,
177 __entry->lid, __entry->when)
178);
179
180/*
181 * Lock events
182 */
183TRACE_EVENT(litmus_resource_acquire,
184
185 TP_PROTO(struct task_struct *t, int lid),
186
187 TP_ARGS(t, lid),
188
189 TP_STRUCT__entry(
190 __field( pid_t, pid )
191 __field( int, lid )
192 __field( unsigned long long, when )
193 ),
194
195 TP_fast_assign(
196 __entry->pid = t ? t->pid : 0;
197 __entry->lid = lid;
198 __entry->when = litmus_clock();
199 ),
200
201 TP_printk("(%u) acquires %d: %Lu\n", __entry->pid,
202 __entry->lid, __entry->when)
203);
204
205TRACE_EVENT(litmus_resource_release,
206
207 TP_PROTO(struct task_struct *t, int lid),
208
209 TP_ARGS(t, lid),
167 210
168 TP_STRUCT__entry( 211 TP_STRUCT__entry(
169 __field( pid_t, pid ) 212 __field( pid_t, pid )
170 __field( lt_t, when ) 213 __field( int, lid )
214 __field( unsigned long long, when )
171 ), 215 ),
172 216
173 TP_fast_assign( 217 TP_fast_assign(
174 __entry->pid = t ? t->pid : 0; 218 __entry->pid = t ? t->pid : 0;
219 __entry->lid = lid;
175 __entry->when = litmus_clock(); 220 __entry->when = litmus_clock();
176 ), 221 ),
177 222
178 TP_printk("(%u) blocks: %Lu\n", __entry->pid, __entry->when) 223 TP_printk("(%u) releases %d: %Lu\n", __entry->pid,
224 __entry->lid, __entry->when)
179); 225);
180 226
181/* 227/*
@@ -183,24 +229,27 @@ TRACE_EVENT(litmus_task_block,
183 */ 229 */
184TRACE_EVENT(litmus_task_resume, 230TRACE_EVENT(litmus_task_resume,
185 231
186 TP_PROTO(struct task_struct *t), 232 TP_PROTO(struct task_struct *t, int lid),
187 233
188 TP_ARGS(t), 234 TP_ARGS(t, lid),
189 235
190 TP_STRUCT__entry( 236 TP_STRUCT__entry(
191 __field( pid_t, pid ) 237 __field( pid_t, pid )
238 __field( int, lid )
192 __field( unsigned int, job ) 239 __field( unsigned int, job )
193 __field( lt_t, when ) 240 __field( unsigned long long, when )
194 ), 241 ),
195 242
196 TP_fast_assign( 243 TP_fast_assign(
197 __entry->pid = t ? t->pid : 0; 244 __entry->pid = t ? t->pid : 0;
198 __entry->job = t ? t->rt_param.job_params.job_no : 0; 245 __entry->job = t ? t->rt_param.job_params.job_no : 0;
199 __entry->when = litmus_clock(); 246 __entry->when = litmus_clock();
247 __entry->lid = lid;
200 ), 248 ),
201 249
202 TP_printk("resume(job(%u, %u)): %Lu\n", 250 TP_printk("resume(job(%u, %u)) on %d: %Lu\n",
203 __entry->pid, __entry->job, __entry->when) 251 __entry->pid, __entry->job,
252 __entry->lid, __entry->when)
204); 253);
205 254
206/* 255/*
@@ -208,13 +257,13 @@ TRACE_EVENT(litmus_task_resume,
208 */ 257 */
209TRACE_EVENT(litmus_sys_release, 258TRACE_EVENT(litmus_sys_release,
210 259
211 TP_PROTO(lt_t *start), 260 TP_PROTO(unsigned long long *start),
212 261
213 TP_ARGS(start), 262 TP_ARGS(start),
214 263
215 TP_STRUCT__entry( 264 TP_STRUCT__entry(
216 __field( lt_t, rel ) 265 __field( unsigned long long, rel )
217 __field( lt_t, when ) 266 __field( unsigned long long, when )
218 ), 267 ),
219 268
220 TP_fast_assign( 269 TP_fast_assign(
@@ -225,6 +274,159 @@ TRACE_EVENT(litmus_sys_release,
225 TP_printk("SynRelease(%Lu) at %Lu\n", __entry->rel, __entry->when) 274 TP_printk("SynRelease(%Lu) at %Lu\n", __entry->rel, __entry->when)
226); 275);
227 276
277/*
278 * Trace task exit
279 */
280TRACE_EVENT(litmus_task_exit,
281
282 TP_PROTO(struct task_struct *t),
283
284 TP_ARGS(t),
285
286 TP_STRUCT__entry(
287 __field( pid_t, pid )
288 __field( unsigned long long, max_exec_time )
289 ),
290
291 TP_fast_assign(
292 __entry->pid = t ? t->pid : 0;
293 __entry->max_exec_time = t ? t->rt_param.max_exec_time : 0;
294 ),
295
296 TP_printk("(%u) exit\n", __entry->pid)
297);
298
299/*
300 * Containers
301 */
302TRACE_EVENT(litmus_container_param,
303
304 TP_PROTO(int cid, const char *name),
305
306 TP_ARGS(cid, name),
307
308 TP_STRUCT__entry(
309 __field( int, cid )
310 __array( char, name, TASK_COMM_LEN )
311 ),
312
313 TP_fast_assign(
314 memcpy(__entry->name, name, TASK_COMM_LEN);
315 __entry->cid = cid;
316 ),
317
318 TP_printk("container, name: %s, id: %d\n", __entry->name, __entry->cid)
319);
320
321TRACE_EVENT(litmus_server_param,
322
323 TP_PROTO(int sid, int cid, unsigned long long wcet, unsigned long long period),
324
325 TP_ARGS(sid, cid, wcet, period),
326
327 TP_STRUCT__entry(
328 __field( int, sid )
329 __field( int, cid )
330 __field( unsigned long long, wcet )
331 __field( unsigned long long, period )
332 ),
333
334 TP_fast_assign(
335 __entry->cid = cid;
336 __entry->sid = sid;
337 __entry->wcet = wcet;
338 __entry->period = period;
339 ),
340
341 TP_printk("server(%llu, %llu), sid: %llu, cont: %llu\n",
342 __entry->wcet, __entry->period, __entry->sid, __entry->cid)
343);
344
345TRACE_EVENT(litmus_server_switch_to,
346
347 TP_PROTO(int sid, unsigned int job, int tid),
348
349 TP_ARGS(sid, job, tid),
350
351 TP_STRUCT__entry(
352 __field( int, sid)
353 __field( unsigned int, job)
354 __field( int, tid)
355 ),
356
357 TP_fast_assign(
358 __entry->sid = sid;
359 __entry->tid = tid;
360 __entry->job = job;
361 ),
362
363 TP_printk("switch_to(server(%d, %u)): %d\n", __entry->sid, __entry->job, __entry->tid)
364);
365
366TRACE_EVENT(litmus_server_switch_away,
367
368 TP_PROTO(int sid, unsigned int job, int tid),
369
370 TP_ARGS(sid, job, tid),
371
372 TP_STRUCT__entry(
373 __field( int, sid)
374 __field( unsigned int, job)
375 __field( int, tid)
376 ),
377
378 TP_fast_assign(
379 __entry->sid = sid;
380 __entry->tid = tid;
381 ),
382
383 TP_printk("switch_away(server(%d, %u)): %d\n", __entry->sid, __entry->job, __entry->tid)
384);
385
386TRACE_EVENT(litmus_server_release,
387
388 TP_PROTO(int sid, unsigned int job,
389 unsigned long long release,
390 unsigned long long deadline),
391
392 TP_ARGS(sid, job, release, deadline),
393
394 TP_STRUCT__entry(
395 __field( int, sid)
396 __field( unsigned int, job)
397 __field( unsigned long long, release)
398 __field( unsigned long long, deadline)
399 ),
400
401 TP_fast_assign(
402 __entry->sid = sid;
403 __entry->job = job;
404 __entry->release = release;
405 __entry->deadline = deadline;
406 ),
407
408 TP_printk("release(server(%d, %u)), release: %llu, deadline: %llu\n", __entry->sid, __entry->job, __entry->release, __entry->deadline)
409);
410
411TRACE_EVENT(litmus_server_completion,
412
413 TP_PROTO(int sid, int job),
414
415 TP_ARGS(sid, job),
416
417 TP_STRUCT__entry(
418 __field( int, sid)
419 __field( unsigned int, job)
420 ),
421
422 TP_fast_assign(
423 __entry->sid = sid;
424 __entry->job = job;
425 ),
426
427 TP_printk("completion(server(%d, %d))\n", __entry->sid, __entry->job)
428);
429
228#endif /* _SCHED_TASK_TRACEPOINT_H */ 430#endif /* _SCHED_TASK_TRACEPOINT_H */
229 431
230/* Must stay outside the protection */ 432/* Must stay outside the protection */
diff --git a/include/trace/ftrace.h b/include/trace/ftrace.h
index 533c49f4804..4d6f3474e8f 100644
--- a/include/trace/ftrace.h
+++ b/include/trace/ftrace.h
@@ -17,6 +17,7 @@
17 */ 17 */
18 18
19#include <linux/ftrace_event.h> 19#include <linux/ftrace_event.h>
20#include <litmus/litmus.h>
20 21
21/* 22/*
22 * DECLARE_EVENT_CLASS can be used to add a generic function 23 * DECLARE_EVENT_CLASS can be used to add a generic function
@@ -54,7 +55,7 @@
54#define __string(item, src) __dynamic_array(char, item, -1) 55#define __string(item, src) __dynamic_array(char, item, -1)
55 56
56#undef TP_STRUCT__entry 57#undef TP_STRUCT__entry
57#define TP_STRUCT__entry(args...) args 58#define TP_STRUCT__entry(args...) args __field( unsigned long long, __rt_ts )
58 59
59#undef DECLARE_EVENT_CLASS 60#undef DECLARE_EVENT_CLASS
60#define DECLARE_EVENT_CLASS(name, proto, args, tstruct, assign, print) \ 61#define DECLARE_EVENT_CLASS(name, proto, args, tstruct, assign, print) \
@@ -507,7 +508,7 @@ static inline notrace int ftrace_get_offsets_##call( \
507 strcpy(__get_str(dst), src); 508 strcpy(__get_str(dst), src);
508 509
509#undef TP_fast_assign 510#undef TP_fast_assign
510#define TP_fast_assign(args...) args 511#define TP_fast_assign(args...) args; __entry->__rt_ts = litmus_clock();
511 512
512#undef TP_perf_assign 513#undef TP_perf_assign
513#define TP_perf_assign(args...) 514#define TP_perf_assign(args...)
diff --git a/litmus/jobs.c b/litmus/jobs.c
index fb093c03d53..8a0c889e2cb 100644
--- a/litmus/jobs.c
+++ b/litmus/jobs.c
@@ -5,16 +5,16 @@
5 5
6#include <litmus/litmus.h> 6#include <litmus/litmus.h>
7#include <litmus/jobs.h> 7#include <litmus/jobs.h>
8#include <litmus/trace.h>
8 9
9static inline void setup_release(struct task_struct *t, lt_t release) 10static inline void setup_release(struct task_struct *t, lt_t release)
10{ 11{
11 /* prepare next release */ 12 /* prepare next release */
12 t->rt_param.job_params.release = release; 13 tsk_rt(t)->job_params.release = release;
13 t->rt_param.job_params.deadline = release + get_rt_relative_deadline(t); 14 tsk_rt(t)->job_params.deadline += release + get_rt_period(t);
14 t->rt_param.job_params.exec_time = 0; 15 tsk_rt(t)->job_params.exec_time = 0;
15
16 /* update job sequence number */ 16 /* update job sequence number */
17 t->rt_param.job_params.job_no++; 17 tsk_rt(t)->job_params.job_no++;
18 18
19 /* don't confuse Linux */ 19 /* don't confuse Linux */
20 t->rt.time_slice = 1; 20 t->rt.time_slice = 1;
@@ -47,6 +47,22 @@ void release_at(struct task_struct *t, lt_t start)
47 */ 47 */
48long complete_job(void) 48long complete_job(void)
49{ 49{
50 lt_t amount;
51 lt_t now = litmus_clock();
52 lt_t exec_time = tsk_rt(current)->job_params.exec_time;
53
54 tsk_rt(current)->tot_exec_time += exec_time;
55 if (lt_before(tsk_rt(current)->max_exec_time, exec_time))
56 tsk_rt(current)->max_exec_time = exec_time;
57
58 if (is_tardy(current, now)) {
59 amount = now - get_deadline(current);
60 if (lt_after(amount, tsk_rt(current)->max_tardy))
61 tsk_rt(current)->max_tardy = amount;
62 tsk_rt(current)->total_tardy += amount;
63 ++tsk_rt(current)->missed;
64 }
65
50 /* Mark that we do not excute anymore */ 66 /* Mark that we do not excute anymore */
51 set_rt_flags(current, RT_F_SLEEP); 67 set_rt_flags(current, RT_F_SLEEP);
52 /* call schedule, this will return when a new job arrives 68 /* call schedule, this will return when a new job arrives
diff --git a/litmus/litmus.c b/litmus/litmus.c
index 81384327e85..5e8221da35e 100644
--- a/litmus/litmus.c
+++ b/litmus/litmus.c
@@ -383,6 +383,8 @@ void litmus_exit_task(struct task_struct* tsk)
383{ 383{
384 if (is_realtime(tsk)) { 384 if (is_realtime(tsk)) {
385 sched_trace_task_completion(tsk, 1); 385 sched_trace_task_completion(tsk, 1);
386 sched_trace_task_exit(tsk);
387 sched_trace_task_tardy(tsk);
386 388
387 litmus->task_exit(tsk); 389 litmus->task_exit(tsk);
388 390
diff --git a/litmus/preempt.c b/litmus/preempt.c
index 5704d0bf4c0..92c5d1b26a1 100644
--- a/litmus/preempt.c
+++ b/litmus/preempt.c
@@ -26,10 +26,10 @@ void sched_state_will_schedule(struct task_struct* tsk)
26 set_sched_state(PICKED_WRONG_TASK); 26 set_sched_state(PICKED_WRONG_TASK);
27 else 27 else
28 set_sched_state(WILL_SCHEDULE); 28 set_sched_state(WILL_SCHEDULE);
29 } else 29 } /* else */
30 /* Litmus tasks should never be subject to a remote 30 /* /\* Litmus tasks should never be subject to a remote */
31 * set_tsk_need_resched(). */ 31 /* * set_tsk_need_resched(). *\/ */
32 BUG_ON(is_realtime(tsk)); 32 /* BUG_ON(is_realtime(tsk)); */
33#ifdef CONFIG_PREEMPT_STATE_TRACE 33#ifdef CONFIG_PREEMPT_STATE_TRACE
34 TRACE_TASK(tsk, "set_tsk_need_resched() ret:%p\n", 34 TRACE_TASK(tsk, "set_tsk_need_resched() ret:%p\n",
35 __builtin_return_address(0)); 35 __builtin_return_address(0));
diff --git a/litmus/sched_task_trace.c b/litmus/sched_task_trace.c
index 5ef8d09ab41..7194d2fe6c6 100644
--- a/litmus/sched_task_trace.c
+++ b/litmus/sched_task_trace.c
@@ -186,7 +186,7 @@ feather_callback void do_sched_trace_task_completion(unsigned long id,
186 struct task_struct *t = (struct task_struct*) _task; 186 struct task_struct *t = (struct task_struct*) _task;
187 struct st_event_record* rec = get_record(ST_COMPLETION, t); 187 struct st_event_record* rec = get_record(ST_COMPLETION, t);
188 if (rec) { 188 if (rec) {
189 rec->data.completion.when = now(); 189 rec->data.completion.when = get_exec_time(t);
190 rec->data.completion.forced = forced; 190 rec->data.completion.forced = forced;
191 put_record(rec); 191 put_record(rec);
192 } 192 }
@@ -226,6 +226,34 @@ feather_callback void do_sched_trace_sys_release(unsigned long id,
226 } 226 }
227} 227}
228 228
229feather_callback void do_sched_trace_task_exit(unsigned long id,
230 unsigned long _task)
231{
232 struct task_struct *t = (struct task_struct*) _task;
233 const lt_t max_exec_time = tsk_rt(t)->max_exec_time;
234 const lt_t avg_exec_time = tsk_rt(t)->tot_exec_time / (get_job_no(t) - 1);
235
236 struct st_event_record *rec = get_record(ST_TASK_EXIT, t);
237 if (rec) {
238 rec->data.task_exit.avg_exec_time = avg_exec_time;
239 rec->data.task_exit.max_exec_time = max_exec_time;
240 put_record(rec);
241 }
242}
243
244feather_callback void do_sched_trace_task_tardy(unsigned long id,
245 unsigned long _task)
246{
247 struct task_struct *t = (struct task_struct*) _task;
248 struct st_event_record *rec = get_record(ST_TASK_TARDY, t);
249 if (rec) {
250 rec->data.task_tardy.max_tardy = tsk_rt(t)->max_tardy;
251 rec->data.task_tardy.total_tardy = tsk_rt(t)->total_tardy;
252 rec->data.task_tardy.missed = tsk_rt(t)->missed;
253 put_record(rec);
254 }
255}
256
229feather_callback void do_sched_trace_action(unsigned long id, 257feather_callback void do_sched_trace_action(unsigned long id,
230 unsigned long _task, 258 unsigned long _task,
231 unsigned long action) 259 unsigned long action)