diff options
Diffstat (limited to 'rt-plot-vcpu.c')
-rw-r--r-- | rt-plot-vcpu.c | 279 |
1 files changed, 151 insertions, 128 deletions
diff --git a/rt-plot-vcpu.c b/rt-plot-vcpu.c index 7951ad4..0ec55da 100644 --- a/rt-plot-vcpu.c +++ b/rt-plot-vcpu.c | |||
@@ -2,7 +2,7 @@ | |||
2 | #include <string.h> | 2 | #include <string.h> |
3 | #include "trace-graph.h" | 3 | #include "trace-graph.h" |
4 | 4 | ||
5 | #define DEBUG_LEVEL 4 | 5 | #define DEBUG_LEVEL 0 |
6 | #if DEBUG_LEVEL > 0 | 6 | #if DEBUG_LEVEL > 0 |
7 | #define dprintf(l, x...) \ | 7 | #define dprintf(l, x...) \ |
8 | do { \ | 8 | do { \ |
@@ -22,95 +22,6 @@ static void update_tid(struct vcpu_info *info, int tid) | |||
22 | } | 22 | } |
23 | } | 23 | } |
24 | 24 | ||
25 | |||
26 | static int try_release(struct graph_info *ginfo, struct vcpu_info *vcpu_info, | ||
27 | struct record *record, struct plot_info *info) | ||
28 | { | ||
29 | int sid, job, match, ret = 0; | ||
30 | unsigned long long release, deadline; | ||
31 | |||
32 | match = rt_graph_check_server_release(ginfo, record, &sid, &job, | ||
33 | &release, &deadline); | ||
34 | if (match && sid == vcpu_info->sid) { | ||
35 | info->release = TRUE; | ||
36 | info->rtime = release; | ||
37 | |||
38 | info->deadline = TRUE; | ||
39 | info->dtime = deadline; | ||
40 | |||
41 | dprintf(3, "VCPU release for %d:%d on %d, rel: %llu, dead: %llu\n", | ||
42 | sid, job, record->cpu, release, deadline); | ||
43 | |||
44 | ret = 1; | ||
45 | } | ||
46 | return ret; | ||
47 | } | ||
48 | |||
49 | static int try_completion(struct graph_info *ginfo, | ||
50 | struct vcpu_info *vcpu_info, | ||
51 | struct record *record, struct plot_info *info) | ||
52 | { | ||
53 | int sid, job, match, ret = 0; | ||
54 | unsigned long long ts; | ||
55 | |||
56 | match = rt_graph_check_server_completion(ginfo, record, &sid, &job, &ts); | ||
57 | if (match && sid == vcpu_info->sid) { | ||
58 | |||
59 | info->completion = TRUE; | ||
60 | info->ctime = ts; | ||
61 | |||
62 | dprintf(3, "VCPU completion for %d:%d on %d at %llu\n", | ||
63 | sid, job, record->cpu, ts); | ||
64 | ret = 1; | ||
65 | } | ||
66 | return ret; | ||
67 | } | ||
68 | |||
69 | static int try_block(struct graph_info *ginfo, struct vcpu_info *vcpu_info, | ||
70 | struct record *record, struct plot_info *info) | ||
71 | { | ||
72 | int sid, match, ret = 0; | ||
73 | unsigned long long ts; | ||
74 | |||
75 | match = rt_graph_check_server_block(ginfo, record, &sid, &ts); | ||
76 | if (match && sid == vcpu_info->sid) { | ||
77 | vcpu_info->fresh = FALSE; | ||
78 | vcpu_info->block_time = ts; | ||
79 | vcpu_info->block_cpu = NO_CPU; | ||
80 | dprintf(3, "VCPU resume for %d on %d at %llu\n", | ||
81 | sid, record->cpu, ts); | ||
82 | ret = 1; | ||
83 | } | ||
84 | return ret; | ||
85 | } | ||
86 | |||
87 | static int try_resume(struct graph_info *ginfo, struct vcpu_info *vcpu_info, | ||
88 | struct record *record, struct plot_info *info) | ||
89 | { | ||
90 | int sid, match, ret = 0; | ||
91 | unsigned long long ts; | ||
92 | |||
93 | match = rt_graph_check_server_resume(ginfo, record, &sid, &ts); | ||
94 | |||
95 | if (match && sid == vcpu_info->sid) { | ||
96 | info->box = TRUE; | ||
97 | info->bcolor = 0x0; | ||
98 | info->bfill = TRUE; | ||
99 | info->bthin = TRUE; | ||
100 | info->bstart = vcpu_info->block_time; | ||
101 | info->bend = ts; | ||
102 | vcpu_info->fresh = FALSE; | ||
103 | |||
104 | vcpu_info->block_time = 0ULL; | ||
105 | vcpu_info->block_cpu = NO_CPU; | ||
106 | dprintf(3, "VCPU resume for %d on %d at %llu\n", | ||
107 | sid, record->cpu, ts); | ||
108 | |||
109 | ret = 1; | ||
110 | } | ||
111 | return ret; | ||
112 | } | ||
113 | |||
114 | static int | 25 | static int |
115 | try_server_switch_away(struct graph_info *ginfo, struct vcpu_info *vcpu_info, | 26 | try_server_switch_away(struct graph_info *ginfo, struct vcpu_info *vcpu_info, |
116 | struct record *record, struct plot_info *info) | 27 | struct record *record, struct plot_info *info) |
@@ -259,16 +170,55 @@ static int rt_vcpu_plot_event(struct graph_info *ginfo, struct graph_plot *plot, | |||
259 | 170 | ||
260 | match = try_server_switch_away(ginfo, vcpu_info, record, info) || | 171 | match = try_server_switch_away(ginfo, vcpu_info, record, info) || |
261 | try_server_switch_to(ginfo, vcpu_info, record, info) || | 172 | try_server_switch_to(ginfo, vcpu_info, record, info) || |
262 | try_block(ginfo, vcpu_info, record, info) || | 173 | vcpu_try_block(ginfo, vcpu_info, record, info) || |
263 | try_resume(ginfo, vcpu_info, record, info) || | 174 | vcpu_try_resume(ginfo, vcpu_info, record, info) || |
264 | try_release(ginfo, vcpu_info, record, info) || | 175 | vcpu_try_release(ginfo, vcpu_info, record, info) || |
265 | try_completion(ginfo, vcpu_info, record, info) || | 176 | vcpu_try_completion(ginfo, vcpu_info, record, info) || |
266 | try_switch_to(ginfo, vcpu_info, record, info) || | 177 | try_switch_to(ginfo, vcpu_info, record, info) || |
267 | try_switch_away(ginfo, vcpu_info, record, info); | 178 | try_switch_away(ginfo, vcpu_info, record, info); |
268 | return match; | 179 | return match; |
269 | } | 180 | } |
270 | 181 | ||
271 | static void rt_vcpu_plot_start(struct graph_info *ginfo, struct graph_plot *plot, | 182 | |
183 | const struct plot_callbacks rt_vcpu_cb = { | ||
184 | .start = rt_vcpu_plot_start, | ||
185 | .destroy = rt_vcpu_plot_destroy, | ||
186 | .plot_event = rt_vcpu_plot_event, | ||
187 | .display_last_event = rt_plot_display_last_event, | ||
188 | .display_info = rt_plot_display_info, | ||
189 | .match_time = rt_plot_match_time, | ||
190 | .find_record = rt_plot_find_record, | ||
191 | }; | ||
192 | |||
193 | void insert_vcpu(struct graph_info *ginfo, struct cont_list *cont, | ||
194 | struct vcpu_list *vcpu_info) | ||
195 | { | ||
196 | struct graph_plot *plot; | ||
197 | struct vcpu_info *vcpu; | ||
198 | char *label; | ||
199 | |||
200 | vcpu = malloc_or_die(sizeof(*vcpu)); | ||
201 | vcpu->sid = vcpu_info->sid; | ||
202 | vcpu->cont = cont; | ||
203 | vcpu->label = malloc_or_die(LLABEL); | ||
204 | |||
205 | vcpu->common.record_matches = rt_vcpu_plot_record_matches; | ||
206 | vcpu->common.is_drawn = rt_vcpu_plot_is_drawn; | ||
207 | vcpu->common.write_header = rt_vcpu_plot_write_header; | ||
208 | |||
209 | g_assert(cont); | ||
210 | |||
211 | label = malloc_or_die(1); | ||
212 | snprintf(label, 2, " "); | ||
213 | plot = trace_graph_plot_append(ginfo, label, PLOT_TYPE_SERVER_CPU, | ||
214 | TIME_TYPE_RT, &rt_vcpu_cb, vcpu); | ||
215 | trace_graph_plot_add_all_recs(ginfo, plot); | ||
216 | } | ||
217 | |||
218 | /** | ||
219 | * | ||
220 | */ | ||
221 | void rt_vcpu_plot_start(struct graph_info *ginfo, struct graph_plot *plot, | ||
272 | unsigned long long time) | 222 | unsigned long long time) |
273 | { | 223 | { |
274 | struct vcpu_info *vcpu_info = plot->private; | 224 | struct vcpu_info *vcpu_info = plot->private; |
@@ -284,11 +234,15 @@ static void rt_vcpu_plot_start(struct graph_info *ginfo, struct graph_plot *plot | |||
284 | 234 | ||
285 | vcpu_info->fresh = TRUE; | 235 | vcpu_info->fresh = TRUE; |
286 | vcpu_info->running = FALSE; | 236 | vcpu_info->running = FALSE; |
237 | vcpu_info->last_job = -1; | ||
287 | 238 | ||
288 | vcpu_info->run_tid = 0; | 239 | vcpu_info->run_tid = 0; |
289 | } | 240 | } |
290 | 241 | ||
291 | static void rt_vcpu_plot_destroy(struct graph_info *ginfo, struct graph_plot *plot) | 242 | /** |
243 | * | ||
244 | */ | ||
245 | void rt_vcpu_plot_destroy(struct graph_info *ginfo, struct graph_plot *plot) | ||
292 | { | 246 | { |
293 | struct vcpu_info *vcpu_info = plot->private; | 247 | struct vcpu_info *vcpu_info = plot->private; |
294 | trace_graph_plot_remove_all_recs(ginfo, plot); | 248 | trace_graph_plot_remove_all_recs(ginfo, plot); |
@@ -296,10 +250,10 @@ static void rt_vcpu_plot_destroy(struct graph_info *ginfo, struct graph_plot *pl | |||
296 | free(vcpu_info); | 250 | free(vcpu_info); |
297 | } | 251 | } |
298 | 252 | ||
299 | /* | 253 | /** |
300 | * Return 1 if @record is relevant to @match_sid. | 254 | * Return 1 if @record is relevant to @match_sid. |
301 | */ | 255 | */ |
302 | static int rt_vcpu_plot_record_matches(struct rt_plot_common *rt, | 256 | int rt_vcpu_plot_record_matches(struct rt_plot_common *rt, |
303 | struct graph_info *ginfo, | 257 | struct graph_info *ginfo, |
304 | struct record *record) | 258 | struct record *record) |
305 | { | 259 | { |
@@ -318,11 +272,11 @@ static int rt_vcpu_plot_record_matches(struct rt_plot_common *rt, | |||
318 | return (sid == vcpu_info->sid); | 272 | return (sid == vcpu_info->sid); |
319 | } | 273 | } |
320 | 274 | ||
321 | /* | 275 | /** |
322 | * Return true if the given record type is drawn on screen. This does not | 276 | * Return true if the given record type is drawn on screen. This does not |
323 | * include event line markes. | 277 | * include event line markes. |
324 | */ | 278 | */ |
325 | static int | 279 | int |
326 | rt_vcpu_plot_is_drawn(struct graph_info *ginfo, int eid) | 280 | rt_vcpu_plot_is_drawn(struct graph_info *ginfo, int eid) |
327 | { | 281 | { |
328 | struct rt_graph_info *rtg_info = &ginfo->rtg_info; | 282 | struct rt_graph_info *rtg_info = &ginfo->rtg_info; |
@@ -334,7 +288,10 @@ rt_vcpu_plot_is_drawn(struct graph_info *ginfo, int eid) | |||
334 | eid == rtg_info->server_resume_id); | 288 | eid == rtg_info->server_resume_id); |
335 | } | 289 | } |
336 | 290 | ||
337 | static struct record* | 291 | /** |
292 | * | ||
293 | */ | ||
294 | struct record* | ||
338 | rt_vcpu_plot_write_header(struct rt_plot_common *rt, | 295 | rt_vcpu_plot_write_header(struct rt_plot_common *rt, |
339 | struct graph_info *ginfo, | 296 | struct graph_info *ginfo, |
340 | struct trace_seq *s, | 297 | struct trace_seq *s, |
@@ -358,38 +315,104 @@ rt_vcpu_plot_write_header(struct rt_plot_common *rt, | |||
358 | return record; | 315 | return record; |
359 | } | 316 | } |
360 | 317 | ||
318 | /** | ||
319 | * vcpu_try_release - draw release and deadline arrows if record matches | ||
320 | */ | ||
321 | int vcpu_try_release(struct graph_info *ginfo, struct vcpu_info *vcpu_info, | ||
322 | struct record *record, struct plot_info *info) | ||
323 | { | ||
324 | int sid, job, match, ret = 0; | ||
325 | unsigned long long release, deadline; | ||
361 | 326 | ||
362 | const struct plot_callbacks rt_vcpu_cb = { | 327 | match = rt_graph_check_server_release(ginfo, record, &sid, &job, |
363 | .start = rt_vcpu_plot_start, | 328 | &release, &deadline); |
364 | .destroy = rt_vcpu_plot_destroy, | 329 | if (match && sid == vcpu_info->sid) { |
365 | .plot_event = rt_vcpu_plot_event, | 330 | info->release = TRUE; |
366 | .display_last_event = rt_plot_display_last_event, | 331 | info->rtime = release; |
367 | .display_info = rt_plot_display_info, | ||
368 | .match_time = rt_plot_match_time, | ||
369 | .find_record = rt_plot_find_record, | ||
370 | }; | ||
371 | 332 | ||
372 | void insert_vcpu(struct graph_info *ginfo, struct cont_list *cont, | 333 | info->deadline = TRUE; |
373 | struct vcpu_list *vcpu_info) | 334 | info->dtime = deadline; |
335 | |||
336 | dprintf(3, "VCPU release for %d:%d on %d, rel: %llu, dead: %llu\n", | ||
337 | sid, job, record->cpu, release, deadline); | ||
338 | |||
339 | ret = 1; | ||
340 | } | ||
341 | return ret; | ||
342 | } | ||
343 | |||
344 | /** | ||
345 | * vcpu_try_completion - draw completion if record matches | ||
346 | */ | ||
347 | int vcpu_try_completion(struct graph_info *ginfo, | ||
348 | struct vcpu_info *vcpu_info, | ||
349 | struct record *record, struct plot_info *info) | ||
374 | { | 350 | { |
375 | struct graph_plot *plot; | 351 | int sid, job, match, ret = 0; |
376 | struct vcpu_info *vcpu; | 352 | unsigned long long ts; |
377 | char *label; | ||
378 | 353 | ||
379 | vcpu = malloc_or_die(sizeof(*vcpu)); | 354 | match = rt_graph_check_server_completion(ginfo, record, &sid, &job, &ts); |
380 | vcpu->sid = vcpu_info->sid; | 355 | if (match && sid == vcpu_info->sid) { |
381 | vcpu->cont = cont; | ||
382 | vcpu->label = malloc_or_die(LLABEL); | ||
383 | 356 | ||
384 | vcpu->common.record_matches = rt_vcpu_plot_record_matches; | 357 | info->completion = TRUE; |
385 | vcpu->common.is_drawn = rt_vcpu_plot_is_drawn; | 358 | info->ctime = ts; |
386 | vcpu->common.write_header = rt_vcpu_plot_write_header; | ||
387 | 359 | ||
388 | g_assert(cont); | 360 | dprintf(3, "VCPU completion for %d:%d on %d at %llu\n", |
361 | sid, job, record->cpu, ts); | ||
362 | ret = 1; | ||
363 | } | ||
364 | return ret; | ||
365 | } | ||
389 | 366 | ||
390 | label = malloc_or_die(1); | 367 | /** |
391 | snprintf(label, 2, " "); | 368 | * vcpu_try_block - start block box if record matches |
392 | plot = trace_graph_plot_append(ginfo, label, PLOT_TYPE_SERVER_CPU, | 369 | */ |
393 | TIME_TYPE_RT, &rt_vcpu_cb, vcpu); | 370 | int vcpu_try_block(struct graph_info *ginfo, struct vcpu_info *vcpu_info, |
394 | trace_graph_plot_add_all_recs(ginfo, plot); | 371 | struct record *record, struct plot_info *info) |
372 | { | ||
373 | int sid, match, ret = 0; | ||
374 | unsigned long long ts; | ||
375 | |||
376 | match = rt_graph_check_server_block(ginfo, record, &sid, &ts); | ||
377 | if (match && sid == vcpu_info->sid) { | ||
378 | vcpu_info->fresh = FALSE; | ||
379 | vcpu_info->block_time = ts; | ||
380 | vcpu_info->block_cpu = NO_CPU; | ||
381 | dprintf(3, "VCPU resume for %d on %d at %llu\n", | ||
382 | sid, record->cpu, ts); | ||
383 | ret = 1; | ||
384 | } | ||
385 | return ret; | ||
395 | } | 386 | } |
387 | |||
388 | /** | ||
389 | * vcpu_try_resume - end block box if record matches | ||
390 | */ | ||
391 | int vcpu_try_resume(struct graph_info *ginfo, struct vcpu_info *vcpu_info, | ||
392 | struct record *record, struct plot_info *info) | ||
393 | { | ||
394 | int sid, match, ret = 0; | ||
395 | unsigned long long ts; | ||
396 | |||
397 | match = rt_graph_check_server_resume(ginfo, record, &sid, &ts); | ||
398 | |||
399 | if (match && sid == vcpu_info->sid) { | ||
400 | info->box = TRUE; | ||
401 | info->bcolor = 0x0; | ||
402 | info->bfill = TRUE; | ||
403 | info->bthin = TRUE; | ||
404 | info->bstart = vcpu_info->block_time; | ||
405 | info->bend = ts; | ||
406 | vcpu_info->fresh = FALSE; | ||
407 | |||
408 | vcpu_info->block_time = 0ULL; | ||
409 | vcpu_info->block_cpu = NO_CPU; | ||
410 | dprintf(3, "VCPU resume for %d on %d at %llu\n", | ||
411 | sid, record->cpu, ts); | ||
412 | |||
413 | ret = 1; | ||
414 | } | ||
415 | return ret; | ||
416 | } | ||
417 | |||
418 | |||