stats major rework, with addition of function support
[lttv.git] / ltt / branches / poly / lttv / lttv / stats.c
CommitLineData
9c312311 1/* This file is part of the Linux Trace Toolkit viewer
2 * Copyright (C) 2003-2004 Michel Dagenais
3 *
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License Version 2 as
6 * published by the Free Software Foundation;
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 *
13 * You should have received a copy of the GNU General Public License
14 * along with this program; if not, write to the Free Software
15 * Foundation, Inc., 59 Temple Place - Suite 330, Boston,
16 * MA 02111-1307, USA.
17 */
18
4e4d11b3 19#ifdef HAVE_CONFIG_H
20#include <config.h>
21#endif
b445142a 22
9f797243 23#include <stdio.h>
08b1c66e 24#include <lttv/module.h>
b445142a 25#include <lttv/stats.h>
2a2fa4f0 26#include <lttv/lttv.h>
f95bc830 27#include <lttv/attribute.h>
b445142a 28#include <ltt/facility.h>
29#include <ltt/trace.h>
30#include <ltt/event.h>
826f1ab2 31#include <ltt/type.h>
b445142a 32
9f797243 33#define BUF_SIZE 256
14236daa 34#define MAX_64_HEX_STRING_LEN 19
9f797243 35
b445142a 36GQuark
37 LTTV_STATS_PROCESS_UNKNOWN,
38 LTTV_STATS_PROCESSES,
39 LTTV_STATS_CPU,
40 LTTV_STATS_MODE_TYPES,
41 LTTV_STATS_MODES,
42 LTTV_STATS_SUBMODES,
302efbad 43 LTTV_STATS_FUNCTIONS,
b445142a 44 LTTV_STATS_EVENT_TYPES,
45 LTTV_STATS_CPU_TIME,
46 LTTV_STATS_ELAPSED_TIME,
47 LTTV_STATS_EVENTS,
f95bc830 48 LTTV_STATS_EVENTS_COUNT,
49 LTTV_STATS_USE_COUNT,
50 LTTV_STATS,
51 LTTV_STATS_TRACEFILES,
22b165e9 52 LTTV_STATS_SUMMED,
b445142a 53 LTTV_STATS_BEFORE_HOOKS,
54 LTTV_STATS_AFTER_HOOKS;
55
b445142a 56static void
00e74b69 57find_event_tree(LttvTracefileStats *tfcs, GQuark pid_time, GQuark cpu,
14236daa 58 guint64 function,
b445142a 59 GQuark mode, GQuark sub_mode, LttvAttribute **events_tree,
60 LttvAttribute **event_types_tree);
61
d730b5c8 62
63static void lttv_stats_init(LttvTracesetStats *self)
b445142a 64{
dbb7bb09 65 guint i, j, nb_trace, nb_tracefile;
b445142a 66
67 LttvTraceContext *tc;
68
69 LttvTraceStats *tcs;
70
71 LttvTracefileContext *tfc;
72
3c9bb8b1 73 LttvTracefileContext **tfs;
b445142a 74 LttvTracefileStats *tfcs;
75
76 LttTime timestamp = {0,0};
77
f95bc830 78 LttvAttributeValue v;
79
80 LttvAttribute
81 *stats_tree,
82 *tracefiles_stats;
83
d730b5c8 84 LttvTraceset *ts = self->parent.parent.ts;
b445142a 85
d3e01c7a 86 self->stats = lttv_attribute_find_subdir(
87 lttv_traceset_attribute(self->parent.parent.ts),
88 LTTV_STATS);
89 lttv_attribute_find(lttv_traceset_attribute(self->parent.parent.ts),
90 LTTV_STATS_USE_COUNT,
91 LTTV_UINT, &v);
f95bc830 92
0bd2f89c 93 (*(v.v_uint))++;
f95bc830 94 if(*(v.v_uint) == 1) {
95 g_assert(lttv_attribute_get_number(self->stats) == 0);
96 }
97
b445142a 98 nb_trace = lttv_traceset_number(ts);
99
100 for(i = 0 ; i < nb_trace ; i++) {
021eeb41 101 tc = self->parent.parent.traces[i];
102 tcs = LTTV_TRACE_STATS(tc);
f95bc830 103
104 tcs->stats = lttv_attribute_find_subdir(tcs->parent.parent.t_a,LTTV_STATS);
105 tracefiles_stats = lttv_attribute_find_subdir(tcs->parent.parent.t_a,
106 LTTV_STATS_TRACEFILES);
107 lttv_attribute_find(tcs->parent.parent.t_a, LTTV_STATS_USE_COUNT,
108 LTTV_UINT, &v);
109
0bd2f89c 110 (*(v.v_uint))++;
f95bc830 111 if(*(v.v_uint) == 1) {
112 g_assert(lttv_attribute_get_number(tcs->stats) == 0);
113 }
b445142a 114
eed2ef37 115 nb_tracefile = tc->tracefiles->len;
b445142a 116
dbb7bb09 117 for(j = 0 ; j < nb_tracefile ; j++) {
3c9bb8b1 118 tfs = &g_array_index(tc->tracefiles,
119 LttvTracefileContext*, j);
120 tfcs = LTTV_TRACEFILE_STATS(*tfs);
f95bc830 121 tfcs->stats = lttv_attribute_find_subdir(tracefiles_stats,
348c6ba8 122 ltt_tracefile_long_name(tfcs->parent.parent.tf));
b445142a 123 find_event_tree(tfcs, LTTV_STATS_PROCESS_UNKNOWN,
348c6ba8 124 ltt_tracefile_long_name(tfcs->parent.parent.tf),
14236daa 125 0x0ULL,
348c6ba8 126 LTTV_STATE_MODE_UNKNOWN,
b445142a 127 LTTV_STATE_SUBMODE_UNKNOWN, &tfcs->current_events_tree,
128 &tfcs->current_event_types_tree);
129 }
130 }
d730b5c8 131
b445142a 132}
133
d730b5c8 134static void lttv_stats_fini(LttvTracesetStats *self)
b445142a 135{
136 guint i, j, nb_trace, nb_tracefile;
137
138 LttvTraceset *ts;
139
140 LttvTraceContext *tc;
141
142 LttvTraceStats *tcs;
143
144 LttvTracefileContext *tfc;
145
146 LttvTracefileStats *tfcs;
147
148 LttTime timestamp = {0,0};
149
f95bc830 150 LttvAttributeValue v;
151
152 LttvAttribute *tracefiles_stats;
153
154 lttv_attribute_find(self->parent.parent.ts_a, LTTV_STATS_USE_COUNT,
155 LTTV_UINT, &v);
0bd2f89c 156 (*(v.v_uint))--;
f95bc830 157
158 if(*(v.v_uint) == 0) {
159 lttv_attribute_remove_by_name(self->parent.parent.ts_a, LTTV_STATS);
f95bc830 160 }
161 self->stats = NULL;
162
b445142a 163 ts = self->parent.parent.ts;
164 nb_trace = lttv_traceset_number(ts);
165
166 for(i = 0 ; i < nb_trace ; i++) {
f95bc830 167 tcs = (LttvTraceStats *)(tc = (LTTV_TRACESET_CONTEXT(self)->traces[i]));
168
169 lttv_attribute_find(tcs->parent.parent.t_a, LTTV_STATS_USE_COUNT,
170 LTTV_UINT, &v);
0bd2f89c 171 (*(v.v_uint))--;
f95bc830 172
173 if(*(v.v_uint) == 0) {
174 lttv_attribute_remove_by_name(tcs->parent.parent.t_a,LTTV_STATS);
f95bc830 175 tracefiles_stats = lttv_attribute_find_subdir(tcs->parent.parent.t_a,
176 LTTV_STATS_TRACEFILES);
177 lttv_attribute_remove_by_name(tcs->parent.parent.t_a,
178 LTTV_STATS_TRACEFILES);
f95bc830 179 }
180 tcs->stats = NULL;
b445142a 181
eed2ef37 182 nb_tracefile = tc->tracefiles->len;
b445142a 183
b445142a 184 for(j = 0 ; j < nb_tracefile ; j++) {
cb03932a 185 tfc = g_array_index(tc->tracefiles,
186 LttvTracefileContext*, j);
359b2948 187 tfcs = (LttvTracefileStats *)tfc;
f95bc830 188 tfcs->stats = NULL;
b445142a 189 tfcs->current_events_tree = NULL;
190 tfcs->current_event_types_tree = NULL;
191 }
192 }
d730b5c8 193}
194
195
196void lttv_stats_reset(LttvTracesetStats *self)
197{
198 lttv_stats_fini(self);
199 lttv_stats_init(self);
200}
201
202
203
204static void
205init(LttvTracesetStats *self, LttvTraceset *ts)
206{
207 LTTV_TRACESET_CONTEXT_CLASS(g_type_class_peek(LTTV_TRACESET_STATE_TYPE))->
208 init((LttvTracesetContext *)self, ts);
209
210 lttv_stats_init(self);
211}
212
213
214static void
215fini(LttvTracesetStats *self)
216{
217 lttv_stats_fini(self);
218
b445142a 219 LTTV_TRACESET_CONTEXT_CLASS(g_type_class_peek(LTTV_TRACESET_STATE_TYPE))->
220 fini((LttvTracesetContext *)self);
221}
222
223
224static LttvTracesetContext *
225new_traceset_context(LttvTracesetContext *self)
226{
227 return LTTV_TRACESET_CONTEXT(g_object_new(LTTV_TRACESET_STATS_TYPE, NULL));
228}
229
230
231static LttvTraceContext *
232new_trace_context(LttvTracesetContext *self)
233{
234 return LTTV_TRACE_CONTEXT(g_object_new(LTTV_TRACE_STATS_TYPE, NULL));
235}
236
237
238static LttvTracefileContext *
239new_tracefile_context(LttvTracesetContext *self)
240{
241 return LTTV_TRACEFILE_CONTEXT(g_object_new(LTTV_TRACEFILE_STATS_TYPE, NULL));
242}
243
244
245static void
246traceset_stats_instance_init (GTypeInstance *instance, gpointer g_class)
247{
248}
249
250
251static void
252traceset_stats_finalize (LttvTracesetStats *self)
253{
254 G_OBJECT_CLASS(g_type_class_peek(LTTV_TRACESET_STATE_TYPE))->
255 finalize(G_OBJECT(self));
256}
257
258
259static void
260traceset_stats_class_init (LttvTracesetContextClass *klass)
261{
262 GObjectClass *gobject_class = G_OBJECT_CLASS(klass);
263
264 gobject_class->finalize = (void (*)(GObject *self)) traceset_stats_finalize;
265 klass->init = (void (*)(LttvTracesetContext *self, LttvTraceset *ts))init;
266 klass->fini = (void (*)(LttvTracesetContext *self))fini;
267 klass->new_traceset_context = new_traceset_context;
268 klass->new_trace_context = new_trace_context;
269 klass->new_tracefile_context = new_tracefile_context;
270}
271
272
273GType
274lttv_traceset_stats_get_type(void)
275{
276 static GType type = 0;
277 if (type == 0) {
278 static const GTypeInfo info = {
279 sizeof (LttvTracesetStatsClass),
280 NULL, /* base_init */
281 NULL, /* base_finalize */
282 (GClassInitFunc) traceset_stats_class_init, /* class_init */
283 NULL, /* class_finalize */
284 NULL, /* class_data */
dbb7bb09 285 sizeof (LttvTracesetStats),
b445142a 286 0, /* n_preallocs */
00e74b69 287 (GInstanceInitFunc) traceset_stats_instance_init, /* instance_init */
288 NULL /* Value handling */
b445142a 289 };
290
00e74b69 291 type = g_type_register_static (LTTV_TRACESET_STATE_TYPE,
292 "LttvTracesetStatsType",
293 &info, 0);
b445142a 294 }
295 return type;
296}
297
298
299static void
300trace_stats_instance_init (GTypeInstance *instance, gpointer g_class)
301{
302}
303
304
305static void
306trace_stats_finalize (LttvTraceStats *self)
307{
308 G_OBJECT_CLASS(g_type_class_peek(LTTV_TRACE_STATE_TYPE))->
309 finalize(G_OBJECT(self));
310}
311
312
313static void
314trace_stats_class_init (LttvTraceContextClass *klass)
315{
316 GObjectClass *gobject_class = G_OBJECT_CLASS(klass);
317
318 gobject_class->finalize = (void (*)(GObject *self)) trace_stats_finalize;
319}
320
321
322GType
323lttv_trace_stats_get_type(void)
324{
325 static GType type = 0;
326 if (type == 0) {
327 static const GTypeInfo info = {
328 sizeof (LttvTraceStatsClass),
329 NULL, /* base_init */
330 NULL, /* base_finalize */
331 (GClassInitFunc) trace_stats_class_init, /* class_init */
332 NULL, /* class_finalize */
333 NULL, /* class_data */
334 sizeof (LttvTraceStats),
335 0, /* n_preallocs */
00e74b69 336 (GInstanceInitFunc) trace_stats_instance_init, /* instance_init */
337 NULL /* Value handling */
b445142a 338 };
339
340 type = g_type_register_static (LTTV_TRACE_STATE_TYPE,
341 "LttvTraceStatsType", &info, 0);
342 }
343 return type;
344}
345
346
347static void
348tracefile_stats_instance_init (GTypeInstance *instance, gpointer g_class)
349{
350}
351
352
353static void
354tracefile_stats_finalize (LttvTracefileStats *self)
355{
356 G_OBJECT_CLASS(g_type_class_peek(LTTV_TRACEFILE_STATE_TYPE))->
357 finalize(G_OBJECT(self));
358}
359
360
361static void
362tracefile_stats_class_init (LttvTracefileStatsClass *klass)
363{
364 GObjectClass *gobject_class = G_OBJECT_CLASS(klass);
365
366 gobject_class->finalize = (void (*)(GObject *self)) tracefile_stats_finalize;
367}
368
369
370GType
371lttv_tracefile_stats_get_type(void)
372{
373 static GType type = 0;
374 if (type == 0) {
375 static const GTypeInfo info = {
376 sizeof (LttvTracefileStatsClass),
377 NULL, /* base_init */
378 NULL, /* base_finalize */
379 (GClassInitFunc) tracefile_stats_class_init, /* class_init */
380 NULL, /* class_finalize */
381 NULL, /* class_data */
382 sizeof (LttvTracefileStats),
383 0, /* n_preallocs */
00e74b69 384 (GInstanceInitFunc) tracefile_stats_instance_init, /* instance_init */
385 NULL /* Value handling */
b445142a 386 };
387
388 type = g_type_register_static (LTTV_TRACEFILE_STATE_TYPE,
389 "LttvTracefileStatsType", &info, 0);
390 }
391 return type;
392}
393
394
395static void
00e74b69 396find_event_tree(LttvTracefileStats *tfcs,
397 GQuark pid_time,
398 GQuark cpu,
14236daa 399 guint64 function,
00e74b69 400 GQuark mode,
401 GQuark sub_mode,
402 LttvAttribute **events_tree,
403 LttvAttribute **event_types_tree)
b445142a 404{
405 LttvAttribute *a;
14236daa 406 gchar fstring[MAX_64_HEX_STRING_LEN];
407
408 g_assert(snprintf(fstring, MAX_64_HEX_STRING_LEN-1,
409 "0x%llX", function) > 0);
410 fstring[MAX_64_HEX_STRING_LEN-1] = '\0';
b445142a 411
3c9bb8b1 412 LttvTraceStats *tcs = (LttvTraceStats*)tfcs->parent.parent.t_context;
b445142a 413 a = lttv_attribute_find_subdir(tcs->stats, LTTV_STATS_PROCESSES);
00e74b69 414 a = lttv_attribute_find_subdir(a, pid_time);
b445142a 415 a = lttv_attribute_find_subdir(a, LTTV_STATS_CPU);
00e74b69 416 a = lttv_attribute_find_subdir(a, cpu);
14236daa 417 a = lttv_attribute_find_subdir(a, LTTV_STATS_FUNCTIONS);
418 a = lttv_attribute_find_subdir(a, g_quark_from_string(fstring));
b445142a 419 a = lttv_attribute_find_subdir(a, LTTV_STATS_MODE_TYPES);
00e74b69 420 a = lttv_attribute_find_subdir(a, mode);
b445142a 421 a = lttv_attribute_find_subdir(a, LTTV_STATS_SUBMODES);
00e74b69 422 a = lttv_attribute_find_subdir(a, sub_mode);
b445142a 423 *events_tree = a;
424 a = lttv_attribute_find_subdir(a, LTTV_STATS_EVENT_TYPES);
425 *event_types_tree = a;
426}
427
428
429static void update_event_tree(LttvTracefileStats *tfcs)
430{
348c6ba8 431 LttvTraceState *ts = (LttvTraceState *)tfcs->parent.parent.t_context;
ae3d0f50 432 guint cpu = tfcs->parent.cpu;
348c6ba8 433 LttvProcessState *process = ts->running_process[cpu];
434 LttvExecutionState *es = process->state;
b445142a 435
348c6ba8 436 find_event_tree(tfcs, process->pid_time,
14236daa 437 ltt_tracefile_long_name(tfcs->parent.parent.tf),
438 process->current_function,
b445142a 439 es->t, es->n, &(tfcs->current_events_tree),
440 &(tfcs->current_event_types_tree));
441}
442
443
444static void mode_change(LttvTracefileStats *tfcs)
445{
348c6ba8 446 LttvTraceState *ts = (LttvTraceState *)tfcs->parent.parent.t_context;
ae3d0f50 447 guint cpu = tfcs->parent.cpu;
348c6ba8 448 LttvProcessState *process = ts->running_process[cpu];
b445142a 449 LttvAttributeValue cpu_time;
450
451 LttTime delta;
452
453 lttv_attribute_find(tfcs->current_events_tree, LTTV_STATS_CPU_TIME,
454 LTTV_TIME, &cpu_time);
308711e5 455 delta = ltt_time_sub(tfcs->parent.parent.timestamp,
348c6ba8 456 process->state->change);
308711e5 457 *(cpu_time.v_time) = ltt_time_add(*(cpu_time.v_time), delta);
b445142a 458}
459
460
461static void mode_end(LttvTracefileStats *tfcs)
462{
348c6ba8 463 LttvTraceState *ts = (LttvTraceState *)tfcs->parent.parent.t_context;
ae3d0f50 464 guint cpu = tfcs->parent.cpu;
348c6ba8 465 LttvProcessState *process = ts->running_process[cpu];
b445142a 466 LttvAttributeValue elapsed_time, cpu_time;
467
468 LttTime delta;
469
470 lttv_attribute_find(tfcs->current_events_tree, LTTV_STATS_ELAPSED_TIME,
471 LTTV_TIME, &elapsed_time);
308711e5 472 delta = ltt_time_sub(tfcs->parent.parent.timestamp,
348c6ba8 473 process->state->entry);
308711e5 474 *(elapsed_time.v_time) = ltt_time_add(*(elapsed_time.v_time), delta);
b445142a 475
476 lttv_attribute_find(tfcs->current_events_tree, LTTV_STATS_CPU_TIME,
477 LTTV_TIME, &cpu_time);
308711e5 478 delta = ltt_time_sub(tfcs->parent.parent.timestamp,
348c6ba8 479 process->state->change);
308711e5 480 *(cpu_time.v_time) = ltt_time_add(*(cpu_time.v_time), delta);
b445142a 481}
482
483
484static gboolean before_syscall_entry(void *hook_data, void *call_data)
485{
486 mode_change((LttvTracefileStats *)call_data);
487 return FALSE;
488}
489
490
491static gboolean after_syscall_entry(void *hook_data, void *call_data)
492{
493 update_event_tree((LttvTracefileStats *)call_data);
494 return FALSE;
495}
496
497
498gboolean before_syscall_exit(void *hook_data, void *call_data)
499{
500 mode_end((LttvTracefileStats *)call_data);
501 return FALSE;
502}
503
504
505static gboolean after_syscall_exit(void *hook_data, void *call_data)
506{
507 update_event_tree((LttvTracefileStats *)call_data);
508 return FALSE;
509}
510
511
512gboolean before_trap_entry(void *hook_data, void *call_data)
513{
514 mode_change((LttvTracefileStats *)call_data);
515 return FALSE;
516}
517
518
519static gboolean after_trap_entry(void *hook_data, void *call_data)
520{
521 update_event_tree((LttvTracefileStats *)call_data);
522 return FALSE;
523}
524
525
526gboolean before_trap_exit(void *hook_data, void *call_data)
527{
528 mode_end((LttvTracefileStats *)call_data);
529 return FALSE;
530}
531
532
533gboolean after_trap_exit(void *hook_data, void *call_data)
534{
535 update_event_tree((LttvTracefileStats *)call_data);
536 return FALSE;
537}
538
539
540gboolean before_irq_entry(void *hook_data, void *call_data)
541{
542 mode_change((LttvTracefileStats *)call_data);
543 return FALSE;
544}
545
b445142a 546gboolean after_irq_entry(void *hook_data, void *call_data)
547{
548 update_event_tree((LttvTracefileStats *)call_data);
549 return FALSE;
550}
551
552
553gboolean before_irq_exit(void *hook_data, void *call_data)
554{
555 mode_end((LttvTracefileStats *)call_data);
556 return FALSE;
557}
558
559
560gboolean after_irq_exit(void *hook_data, void *call_data)
561{
562 update_event_tree((LttvTracefileStats *)call_data);
563 return FALSE;
564}
565
566
faf074a3 567gboolean before_soft_irq_entry(void *hook_data, void *call_data)
568{
569 mode_change((LttvTracefileStats *)call_data);
570 return FALSE;
571}
572
573gboolean after_soft_irq_entry(void *hook_data, void *call_data)
574{
575 update_event_tree((LttvTracefileStats *)call_data);
576 return FALSE;
577}
578
579
580gboolean before_soft_irq_exit(void *hook_data, void *call_data)
581{
582 mode_end((LttvTracefileStats *)call_data);
583 return FALSE;
584}
585
586
587gboolean after_soft_irq_exit(void *hook_data, void *call_data)
588{
589 update_event_tree((LttvTracefileStats *)call_data);
590 return FALSE;
591}
592
14236daa 593gboolean before_function_entry(void *hook_data, void *call_data)
594{
595 mode_end((LttvTracefileStats *)call_data);
596 return FALSE;
597}
598
599gboolean after_function_entry(void *hook_data, void *call_data)
600{
601 update_event_tree((LttvTracefileStats *)call_data);
602 return FALSE;
603}
604
605gboolean before_function_exit(void *hook_data, void *call_data)
606{
607 mode_end((LttvTracefileStats *)call_data);
608 return FALSE;
609}
610
611gboolean after_function_exit(void *hook_data, void *call_data)
612{
613 update_event_tree((LttvTracefileStats *)call_data);
614 return FALSE;
615}
616
faf074a3 617
b445142a 618gboolean before_schedchange(void *hook_data, void *call_data)
619{
b445142a 620 LttvTracefileStats *tfcs = (LttvTracefileStats *)call_data;
621
348c6ba8 622 LttvTraceState *ts = (LttvTraceState*)tfcs->parent.parent.t_context;
623
eed2ef37 624 LttEvent *e = ltt_tracefile_get_event(tfcs->parent.parent.tf);
625
d052ffc3 626 LttvTraceHookByFacility *thf = (LttvTraceHookByFacility *)hook_data;
eed2ef37 627
d7cf605c 628 guint pid_in, pid_out;
629
630 gint state_out;
b445142a 631
632 LttvProcessState *process;
633
eed2ef37 634 pid_out = ltt_event_get_unsigned(e, thf->f1);
635 pid_in = ltt_event_get_unsigned(e, thf->f2);
d7cf605c 636 state_out = ltt_event_get_int(e, thf->f3);
b445142a 637
638 /* compute the time for the process to schedule out */
639
640 mode_change(tfcs);
641
642 /* get the information for the process scheduled in */
643
348c6ba8 644 process = lttv_state_find_process_or_create(ts,
645 ANY_CPU, pid_in, &tfcs->parent.parent.timestamp);
b445142a 646
348c6ba8 647 find_event_tree(tfcs, process->pid_time,
648 ltt_tracefile_long_name(tfcs->parent.parent.tf),
14236daa 649 process->current_function,
b445142a 650 process->state->t, process->state->n, &(tfcs->current_events_tree),
651 &(tfcs->current_event_types_tree));
652
653 /* compute the time waiting for the process to schedule in */
654
655 mode_change(tfcs);
656 return FALSE;
657}
658
659
660gboolean process_fork(void *hook_data, void *call_data)
661{
662 /* nothing to do for now */
663 return FALSE;
664}
665
666
667gboolean process_exit(void *hook_data, void *call_data)
668{
669 /* We should probably exit all modes here or we could do that at
670 schedule out. */
671 return FALSE;
672}
673
eed2ef37 674gboolean process_free(void *hook_data, void *call_data)
675{
676 return FALSE;
677}
b445142a 678
679gboolean every_event(void *hook_data, void *call_data)
680{
681 LttvTracefileStats *tfcs = (LttvTracefileStats *)call_data;
682
eed2ef37 683 LttEvent *e = ltt_tracefile_get_event(tfcs->parent.parent.tf);
684
b445142a 685 LttvAttributeValue v;
686
687 /* The current branch corresponds to the tracefile/process/interrupt state.
688 Statistics are added within it, to count the number of events of this
689 type occuring in this context. A quark has been pre-allocated for each
690 event type and is used as name. */
691
692 lttv_attribute_find(tfcs->current_event_types_tree,
eed2ef37 693 ltt_eventtype_name(ltt_event_eventtype(e)),
b445142a 694 LTTV_UINT, &v);
695 (*(v.v_uint))++;
696 return FALSE;
697}
698
699
f95bc830 700void
701lttv_stats_sum_trace(LttvTraceStats *self)
b445142a 702{
d3e01c7a 703 LttvAttribute *sum_container = self->stats;
b445142a 704
b445142a 705 LttvAttributeType type;
706
707 LttvAttributeValue value;
708
709 LttvAttributeName name;
710
711 unsigned sum;
712
f95bc830 713 int i, j, k, l, m, nb_process, nb_cpu, nb_mode_type, nb_submode,
3813c77b 714 nb_event_type, nf, nb_functions;
b445142a 715
716 LttvAttribute *main_tree, *processes_tree, *process_tree, *cpus_tree,
717 *cpu_tree, *mode_tree, *mode_types_tree, *submodes_tree,
718 *submode_tree, *event_types_tree, *mode_events_tree,
3813c77b 719 *cpu_functions_tree,
720 *function_tree,
721 *function_mode_types_tree,
722 *trace_cpu_tree;
f95bc830 723
d3e01c7a 724 main_tree = sum_container;
f95bc830 725
d3e01c7a 726 lttv_attribute_find(sum_container,
727 LTTV_STATS_SUMMED,
728 LTTV_UINT, &value);
f95bc830 729 if(*(value.v_uint) != 0) return;
730 *(value.v_uint) = 1;
731
732 processes_tree = lttv_attribute_find_subdir(main_tree,
d3e01c7a 733 LTTV_STATS_PROCESSES);
f95bc830 734 nb_process = lttv_attribute_get_number(processes_tree);
735
736 for(i = 0 ; i < nb_process ; i++) {
737 type = lttv_attribute_get(processes_tree, i, &name, &value);
738 process_tree = LTTV_ATTRIBUTE(*(value.v_gobject));
739
740 cpus_tree = lttv_attribute_find_subdir(process_tree, LTTV_STATS_CPU);
f95bc830 741 nb_cpu = lttv_attribute_get_number(cpus_tree);
742
743 for(j = 0 ; j < nb_cpu ; j++) {
744 type = lttv_attribute_get(cpus_tree, j, &name, &value);
745 cpu_tree = LTTV_ATTRIBUTE(*(value.v_gobject));
746
f95bc830 747 trace_cpu_tree = lttv_attribute_find_subdir(main_tree, LTTV_STATS_CPU);
748 trace_cpu_tree = lttv_attribute_find_subdir(trace_cpu_tree, name);
3813c77b 749 cpu_functions_tree = lttv_attribute_find_subdir(cpu_tree,
750 LTTV_STATS_FUNCTIONS);
751 nb_functions = lttv_attribute_get_number(cpu_functions_tree);
752
753 for(nf=0; nf < nb_functions; nf++) {
754 type = lttv_attribute_get(cpu_functions_tree, nf, &name, &value);
755 function_tree = LTTV_ATTRIBUTE(*(value.v_gobject));
756 function_mode_types_tree = lttv_attribute_find_subdir(function_tree,
757 LTTV_STATS_MODE_TYPES);
758 nb_mode_type = lttv_attribute_get_number(function_mode_types_tree);
759 for(k = 0 ; k < nb_mode_type ; k++) {
760 type = lttv_attribute_get(function_mode_types_tree, k, &name, &value);
761 mode_tree = LTTV_ATTRIBUTE(*(value.v_gobject));
762
763 submodes_tree = lttv_attribute_find_subdir(mode_tree,
764 LTTV_STATS_SUBMODES);
765 mode_events_tree = lttv_attribute_find_subdir(mode_tree,
766 LTTV_STATS_EVENTS);
767 mode_types_tree = lttv_attribute_find_subdir(mode_tree,
768 LTTV_STATS_MODE_TYPES);
769
770 nb_submode = lttv_attribute_get_number(submodes_tree);
771
772 for(l = 0 ; l < nb_submode ; l++) {
773 type = lttv_attribute_get(submodes_tree, l, &name, &value);
774 submode_tree = LTTV_ATTRIBUTE(*(value.v_gobject));
775
776 event_types_tree = lttv_attribute_find_subdir(submode_tree,
777 LTTV_STATS_EVENT_TYPES);
778 nb_event_type = lttv_attribute_get_number(event_types_tree);
779
780 sum = 0;
781 for(m = 0 ; m < nb_event_type ; m++) {
782 type = lttv_attribute_get(event_types_tree, m, &name, &value);
783 sum += *(value.v_uint);
784 }
785 lttv_attribute_find(submode_tree, LTTV_STATS_EVENTS_COUNT,
786 LTTV_UINT, &value);
787 *(value.v_uint) = sum;
788
789 type = lttv_attribute_get(submodes_tree, l, &name, &value);
790 submode_tree = LTTV_ATTRIBUTE(*(value.v_gobject));
791 lttv_attribute_recursive_add(mode_events_tree, event_types_tree);
792 lttv_attribute_recursive_add(mode_types_tree, submode_tree);
793 }
794 }
795 lttv_attribute_recursive_add(main_tree, mode_types_tree);
796 lttv_attribute_recursive_add(trace_cpu_tree, mode_types_tree);
797 lttv_attribute_recursive_add(process_tree, mode_types_tree);
798 lttv_attribute_recursive_add(function_tree, mode_types_tree);
799 }
800 lttv_attribute_recursive_add(process_tree, cpu_tree);
b445142a 801 }
f95bc830 802 }
803}
804
805
d3e01c7a 806gboolean lttv_stats_sum_traceset_hook(void *hook_data, void *call_data)
807{
808 lttv_stats_sum_traceset((LttvTracesetStats *)call_data);
809 return 0;
810}
811
f95bc830 812void
813lttv_stats_sum_traceset(LttvTracesetStats *self)
814{
815 LttvTraceset *traceset = self->parent.parent.ts;
d3e01c7a 816 LttvAttribute *sum_container = self->stats;
f95bc830 817
818 LttvTraceStats *tcs;
819
820 int i, nb_trace;
821
3813c77b 822 LttvAttribute *main_tree;
f95bc830 823
824 LttvAttributeValue value;
825
d3e01c7a 826 lttv_attribute_find(sum_container, LTTV_STATS_SUMMED,
f95bc830 827 LTTV_UINT, &value);
828 if(*(value.v_uint) != 0) return;
829 *(value.v_uint) = 1;
830
f95bc830 831 nb_trace = lttv_traceset_number(traceset);
832
833 for(i = 0 ; i < nb_trace ; i++) {
834 tcs = (LttvTraceStats *)(self->parent.parent.traces[i]);
835 lttv_stats_sum_trace(tcs);
836 main_tree = tcs->stats;
3813c77b 837 lttv_attribute_recursive_add(sum_container, main_tree);
b445142a 838 }
b445142a 839}
840
841
d3e01c7a 842// Hook wrapper. call_data is a traceset context.
00e74b69 843gboolean lttv_stats_hook_add_event_hooks(void *hook_data, void *call_data)
d3e01c7a 844{
845 LttvTracesetStats *tss = (LttvTracesetStats*)call_data;
846
847 lttv_stats_add_event_hooks(tss);
848
849 return 0;
850}
851
00e74b69 852void lttv_stats_add_event_hooks(LttvTracesetStats *self)
b445142a 853{
854 LttvTraceset *traceset = self->parent.parent.ts;
855
eed2ef37 856 guint i, j, k, l, nb_trace, nb_tracefile;
b445142a 857
b445142a 858 LttvTraceStats *ts;
859
860 LttvTracefileStats *tfs;
861
b445142a 862 GArray *hooks, *before_hooks, *after_hooks;
863
eed2ef37 864 LttvTraceHook *hook;
865
866 LttvTraceHookByFacility *thf;
b445142a 867
868 LttvAttributeValue val;
869
9d239bd9 870 gint ret;
2501204d 871 gint hn;
9d239bd9 872
b445142a 873 nb_trace = lttv_traceset_number(traceset);
874 for(i = 0 ; i < nb_trace ; i++) {
875 ts = (LttvTraceStats *)self->parent.parent.traces[i];
876
877 /* Find the eventtype id for the following events and register the
878 associated by id hooks. */
879
14236daa 880 hooks = g_array_sized_new(FALSE, FALSE, sizeof(LttvTraceHook), 11);
881 g_array_set_size(hooks, 11);
2501204d 882 hn=0;
b445142a 883
9d239bd9 884 ret = lttv_trace_find_hook(ts->parent.parent.t,
f5d7967f 885 LTT_FACILITY_KERNEL_ARCH, LTT_EVENT_SYSCALL_ENTRY,
eed2ef37 886 LTT_FIELD_SYSCALL_ID, 0, 0,
2c82c4dc 887 before_syscall_entry, NULL,
2501204d 888 &g_array_index(hooks, LttvTraceHook, hn++));
889 if(ret) hn--;
b445142a 890
9d239bd9 891 ret = lttv_trace_find_hook(ts->parent.parent.t,
f5d7967f 892 LTT_FACILITY_KERNEL_ARCH, LTT_EVENT_SYSCALL_EXIT,
eed2ef37 893 0, 0, 0,
2c82c4dc 894 before_syscall_exit, NULL,
2501204d 895 &g_array_index(hooks, LttvTraceHook, hn++));
896 if(ret) hn--;
b445142a 897
9d239bd9 898 ret = lttv_trace_find_hook(ts->parent.parent.t,
eed2ef37 899 LTT_FACILITY_KERNEL, LTT_EVENT_TRAP_ENTRY,
900 LTT_FIELD_TRAP_ID, 0, 0,
2c82c4dc 901 before_trap_entry, NULL,
2501204d 902 &g_array_index(hooks, LttvTraceHook, hn++));
903 if(ret) hn--;
b445142a 904
9d239bd9 905 ret = lttv_trace_find_hook(ts->parent.parent.t,
eed2ef37 906 LTT_FACILITY_KERNEL, LTT_EVENT_TRAP_EXIT,
907 0, 0, 0,
2c82c4dc 908 before_trap_exit, NULL,
2501204d 909 &g_array_index(hooks, LttvTraceHook, hn++));
910 if(ret) hn--;
eed2ef37 911
9d239bd9 912 ret = lttv_trace_find_hook(ts->parent.parent.t,
eed2ef37 913 LTT_FACILITY_KERNEL, LTT_EVENT_IRQ_ENTRY,
914 LTT_FIELD_IRQ_ID, 0, 0,
2c82c4dc 915 before_irq_entry, NULL,
2501204d 916 &g_array_index(hooks, LttvTraceHook, hn++));
917 if(ret) hn--;
eed2ef37 918
9d239bd9 919 ret = lttv_trace_find_hook(ts->parent.parent.t,
eed2ef37 920 LTT_FACILITY_KERNEL, LTT_EVENT_IRQ_EXIT,
921 0, 0, 0,
2c82c4dc 922 before_irq_exit, NULL,
2501204d 923 &g_array_index(hooks, LttvTraceHook, hn++));
924 if(ret) hn--;
eed2ef37 925
faf074a3 926 ret = lttv_trace_find_hook(ts->parent.parent.t,
927 LTT_FACILITY_KERNEL, LTT_EVENT_SOFT_IRQ_ENTRY,
928 LTT_FIELD_SOFT_IRQ_ID, 0, 0,
929 before_soft_irq_entry, NULL,
2501204d 930 &g_array_index(hooks, LttvTraceHook, hn++));
931 if(ret) hn--;
faf074a3 932
933 ret = lttv_trace_find_hook(ts->parent.parent.t,
934 LTT_FACILITY_KERNEL, LTT_EVENT_SOFT_IRQ_EXIT,
935 0, 0, 0,
936 before_soft_irq_exit, NULL,
2501204d 937 &g_array_index(hooks, LttvTraceHook, hn++));
938 if(ret) hn--;
faf074a3 939
9d239bd9 940 ret = lttv_trace_find_hook(ts->parent.parent.t,
eed2ef37 941 LTT_FACILITY_PROCESS, LTT_EVENT_SCHEDCHANGE,
942 LTT_FIELD_OUT, LTT_FIELD_IN, LTT_FIELD_OUT_STATE,
2c82c4dc 943 before_schedchange, NULL,
2501204d 944 &g_array_index(hooks, LttvTraceHook, hn++));
945 if(ret) hn--;
14236daa 946
947 ret = lttv_trace_find_hook(ts->parent.parent.t,
948 LTT_FACILITY_USER_GENERIC, LTT_EVENT_FUNCTION_ENTRY,
949 LTT_FIELD_THIS_FN, LTT_FIELD_CALL_SITE, 0,
950 before_function_entry, NULL,
951 &g_array_index(hooks, LttvTraceHook, hn++));
952 if(ret) hn--;
953
954 ret = lttv_trace_find_hook(ts->parent.parent.t,
955 LTT_FACILITY_USER_GENERIC, LTT_EVENT_FUNCTION_EXIT,
956 LTT_FIELD_THIS_FN, LTT_FIELD_CALL_SITE, 0,
957 before_function_exit, NULL,
958 &g_array_index(hooks, LttvTraceHook, hn++));
959 if(ret) hn--;
960
2501204d 961 g_array_set_size(hooks, hn);
b445142a 962
963 before_hooks = hooks;
964
14236daa 965 hooks = g_array_sized_new(FALSE, FALSE, sizeof(LttvTraceHook), 13);
966 g_array_set_size(hooks, 13);
2501204d 967 hn=0;
b445142a 968
9d239bd9 969 ret = lttv_trace_find_hook(ts->parent.parent.t,
f5d7967f 970 LTT_FACILITY_KERNEL_ARCH, LTT_EVENT_SYSCALL_ENTRY,
eed2ef37 971 LTT_FIELD_SYSCALL_ID, 0, 0,
2c82c4dc 972 after_syscall_entry, NULL,
2501204d 973 &g_array_index(hooks, LttvTraceHook, hn++));
974 if(ret) hn--;
b445142a 975
9d239bd9 976 ret = lttv_trace_find_hook(ts->parent.parent.t,
f5d7967f 977 LTT_FACILITY_KERNEL_ARCH, LTT_EVENT_SYSCALL_EXIT,
eed2ef37 978 0, 0, 0,
2c82c4dc 979 after_syscall_exit, NULL,
2501204d 980 &g_array_index(hooks, LttvTraceHook, hn++));
981 if(ret) hn--;
b445142a 982
9d239bd9 983 ret = lttv_trace_find_hook(ts->parent.parent.t,
eed2ef37 984 LTT_FACILITY_KERNEL, LTT_EVENT_TRAP_ENTRY,
985 LTT_FIELD_TRAP_ID, 0, 0,
2c82c4dc 986 after_trap_entry, NULL,
2501204d 987 &g_array_index(hooks, LttvTraceHook, hn++));
988 if(ret) hn--;
eed2ef37 989
9d239bd9 990 ret = lttv_trace_find_hook(ts->parent.parent.t,
eed2ef37 991 LTT_FACILITY_KERNEL, LTT_EVENT_TRAP_EXIT,
992 0, 0, 0,
2c82c4dc 993 after_trap_exit, NULL,
2501204d 994 &g_array_index(hooks, LttvTraceHook, hn++));
995 if(ret) hn--;
b445142a 996
9d239bd9 997 ret = lttv_trace_find_hook(ts->parent.parent.t,
eed2ef37 998 LTT_FACILITY_KERNEL, LTT_EVENT_IRQ_ENTRY,
999 LTT_FIELD_IRQ_ID, 0, 0,
2c82c4dc 1000 after_irq_entry, NULL,
2501204d 1001 &g_array_index(hooks, LttvTraceHook, hn++));
1002 if(ret) hn--;
b445142a 1003
9d239bd9 1004 ret = lttv_trace_find_hook(ts->parent.parent.t,
eed2ef37 1005 LTT_FACILITY_KERNEL, LTT_EVENT_IRQ_EXIT,
1006 0, 0, 0,
2c82c4dc 1007 after_irq_exit, NULL,
2501204d 1008 &g_array_index(hooks, LttvTraceHook, hn++));
1009 if(ret) hn--;
b445142a 1010
faf074a3 1011 ret = lttv_trace_find_hook(ts->parent.parent.t,
1012 LTT_FACILITY_KERNEL, LTT_EVENT_SOFT_IRQ_ENTRY,
1013 LTT_FIELD_SOFT_IRQ_ID, 0, 0,
1014 after_irq_entry, NULL,
2501204d 1015 &g_array_index(hooks, LttvTraceHook, hn++));
1016 if(ret) hn--;
faf074a3 1017
1018 ret = lttv_trace_find_hook(ts->parent.parent.t,
1019 LTT_FACILITY_KERNEL, LTT_EVENT_SOFT_IRQ_EXIT,
1020 0, 0, 0,
1021 after_soft_irq_exit, NULL,
2501204d 1022 &g_array_index(hooks, LttvTraceHook, hn++));
1023 if(ret) hn--;
b445142a 1024
9d239bd9 1025 ret = lttv_trace_find_hook(ts->parent.parent.t,
eed2ef37 1026 LTT_FACILITY_PROCESS, LTT_EVENT_FORK,
1027 LTT_FIELD_PARENT_PID, LTT_FIELD_CHILD_PID, 0,
2c82c4dc 1028 process_fork, NULL,
2501204d 1029 &g_array_index(hooks, LttvTraceHook, hn++));
1030 if(ret) hn--;
b445142a 1031
9d239bd9 1032 ret = lttv_trace_find_hook(ts->parent.parent.t,
eed2ef37 1033 LTT_FACILITY_PROCESS, LTT_EVENT_EXIT,
1034 LTT_FIELD_PID, 0, 0,
2c82c4dc 1035 process_exit, NULL,
2501204d 1036 &g_array_index(hooks, LttvTraceHook, hn++));
1037 if(ret) hn--;
eed2ef37 1038
9d239bd9 1039 ret = lttv_trace_find_hook(ts->parent.parent.t,
eed2ef37 1040 LTT_FACILITY_PROCESS, LTT_EVENT_FREE,
1041 LTT_FIELD_PID, 0, 0,
2c82c4dc 1042 process_free, NULL,
2501204d 1043 &g_array_index(hooks, LttvTraceHook, hn++));
1044 if(ret) hn--;
eed2ef37 1045
14236daa 1046 ret = lttv_trace_find_hook(ts->parent.parent.t,
1047 LTT_FACILITY_USER_GENERIC, LTT_EVENT_FUNCTION_ENTRY,
1048 LTT_FIELD_THIS_FN, LTT_FIELD_CALL_SITE, 0,
1049 after_function_entry, NULL,
1050 &g_array_index(hooks, LttvTraceHook, hn++));
1051 if(ret) hn--;
1052
1053 ret = lttv_trace_find_hook(ts->parent.parent.t,
1054 LTT_FACILITY_USER_GENERIC, LTT_EVENT_FUNCTION_EXIT,
1055 LTT_FIELD_THIS_FN, LTT_FIELD_CALL_SITE, 0,
1056 after_function_exit, NULL,
1057 &g_array_index(hooks, LttvTraceHook, hn++));
1058 if(ret) hn--;
1059
2501204d 1060 g_array_set_size(hooks, hn);
b445142a 1061
1062 after_hooks = hooks;
1063
359b2948 1064 /* Add these hooks to each event_by_id hooks list */
b445142a 1065
eed2ef37 1066 nb_tracefile = ts->parent.parent.tracefiles->len;
b445142a 1067
dbb7bb09 1068 for(j = 0 ; j < nb_tracefile ; j++) {
d7cf605c 1069 tfs = LTTV_TRACEFILE_STATS(g_array_index(ts->parent.parent.tracefiles,
1070 LttvTracefileContext*, j));
359b2948 1071 lttv_hooks_add(tfs->parent.parent.event, every_event, NULL,
1072 LTTV_PRIO_DEFAULT);
b445142a 1073
1074 for(k = 0 ; k < before_hooks->len ; k++) {
eed2ef37 1075 hook = &g_array_index(before_hooks, LttvTraceHook, k);
1076 for(l = 0; l<hook->fac_list->len;l++) {
1077 thf = g_array_index(hook->fac_list, LttvTraceHookByFacility*, l);
1078 lttv_hooks_add(
1079 lttv_hooks_by_id_find(tfs->parent.parent.event_by_id, thf->id),
1080 thf->h,
d052ffc3 1081 thf,
eed2ef37 1082 LTTV_PRIO_STATS_BEFORE_STATE);
1083 }
b445142a 1084 }
1085 for(k = 0 ; k < after_hooks->len ; k++) {
eed2ef37 1086 hook = &g_array_index(after_hooks, LttvTraceHook, k);
1087 for(l = 0; l<hook->fac_list->len;l++) {
1088 thf = g_array_index(hook->fac_list, LttvTraceHookByFacility*, l);
1089 lttv_hooks_add(
1090 lttv_hooks_by_id_find(tfs->parent.parent.event_by_id, thf->id),
1091 thf->h,
d052ffc3 1092 thf,
eed2ef37 1093 LTTV_PRIO_STATS_AFTER_STATE);
1094 }
b445142a 1095 }
1096 }
1097 lttv_attribute_find(self->parent.parent.a, LTTV_STATS_BEFORE_HOOKS,
1098 LTTV_POINTER, &val);
1099 *(val.v_pointer) = before_hooks;
1100 lttv_attribute_find(self->parent.parent.a, LTTV_STATS_AFTER_HOOKS,
1101 LTTV_POINTER, &val);
1102 *(val.v_pointer) = after_hooks;
1103 }
b445142a 1104}
1105
d3e01c7a 1106// Hook wrapper. call_data is a traceset context.
00e74b69 1107gboolean lttv_stats_hook_remove_event_hooks(void *hook_data, void *call_data)
d3e01c7a 1108{
1109 LttvTracesetStats *tss = (LttvTracesetStats*)call_data;
1110
1111 lttv_stats_remove_event_hooks(tss);
1112
1113 return 0;
1114}
b445142a 1115
00e74b69 1116void lttv_stats_remove_event_hooks(LttvTracesetStats *self)
b445142a 1117{
1118 LttvTraceset *traceset = self->parent.parent.ts;
1119
eed2ef37 1120 guint i, j, k, l, nb_trace, nb_tracefile;
b445142a 1121
1122 LttvTraceStats *ts;
1123
1124 LttvTracefileStats *tfs;
1125
1126 void *hook_data;
1127
1128 GArray *before_hooks, *after_hooks;
1129
eed2ef37 1130 LttvTraceHook *hook;
1131
1132 LttvTraceHookByFacility *thf;
b445142a 1133
1134 LttvAttributeValue val;
1135
1136 nb_trace = lttv_traceset_number(traceset);
1137 for(i = 0 ; i < nb_trace ; i++) {
ae80b609 1138 ts = (LttvTraceStats*)self->parent.parent.traces[i];
b445142a 1139 lttv_attribute_find(self->parent.parent.a, LTTV_STATS_BEFORE_HOOKS,
1140 LTTV_POINTER, &val);
1141 before_hooks = *(val.v_pointer);
1142 lttv_attribute_find(self->parent.parent.a, LTTV_STATS_AFTER_HOOKS,
1143 LTTV_POINTER, &val);
1144 after_hooks = *(val.v_pointer);
1145
359b2948 1146 /* Remove these hooks from each event_by_id hooks list */
b445142a 1147
eed2ef37 1148 nb_tracefile = ts->parent.parent.tracefiles->len;
b445142a 1149
dbb7bb09 1150 for(j = 0 ; j < nb_tracefile ; j++) {
cb03932a 1151 tfs = LTTV_TRACEFILE_STATS(g_array_index(ts->parent.parent.tracefiles,
1152 LttvTracefileContext*, j));
359b2948 1153 lttv_hooks_remove_data(tfs->parent.parent.event, every_event,
b445142a 1154 NULL);
1155
1156 for(k = 0 ; k < before_hooks->len ; k++) {
eed2ef37 1157 hook = &g_array_index(before_hooks, LttvTraceHook, k);
1158 for(l = 0 ; l < hook->fac_list->len ; l++) {
1159 thf = g_array_index(hook->fac_list, LttvTraceHookByFacility*, l);
1160 lttv_hooks_remove_data(
1161 lttv_hooks_by_id_find(tfs->parent.parent.event_by_id, thf->id),
1162 thf->h,
d052ffc3 1163 thf);
eed2ef37 1164 }
b445142a 1165 }
1166 for(k = 0 ; k < after_hooks->len ; k++) {
eed2ef37 1167 hook = &g_array_index(after_hooks, LttvTraceHook, k);
1168 for(l = 0 ; l < hook->fac_list->len ; l++) {
1169 thf = g_array_index(hook->fac_list, LttvTraceHookByFacility*, l);
1170 lttv_hooks_remove_data(
1171 lttv_hooks_by_id_find(tfs->parent.parent.event_by_id, thf->id),
1172 thf->h,
d052ffc3 1173 thf);
eed2ef37 1174 }
b445142a 1175 }
1176 }
2a2fa4f0 1177 g_debug("lttv_stats_remove_event_hooks()");
b445142a 1178 g_array_free(before_hooks, TRUE);
1179 g_array_free(after_hooks, TRUE);
1180 }
9f797243 1181}
08b1c66e 1182
1183
1184static void module_init()
1185{
1186 LTTV_STATS_PROCESS_UNKNOWN = g_quark_from_string("unknown process");
1187 LTTV_STATS_PROCESSES = g_quark_from_string("processes");
1188 LTTV_STATS_CPU = g_quark_from_string("cpu");
1189 LTTV_STATS_MODE_TYPES = g_quark_from_string("mode_types");
1190 LTTV_STATS_MODES = g_quark_from_string("modes");
1191 LTTV_STATS_SUBMODES = g_quark_from_string("submodes");
14236daa 1192 LTTV_STATS_FUNCTIONS = g_quark_from_string("functions");
08b1c66e 1193 LTTV_STATS_EVENT_TYPES = g_quark_from_string("event_types");
1194 LTTV_STATS_CPU_TIME = g_quark_from_string("cpu time");
1195 LTTV_STATS_ELAPSED_TIME = g_quark_from_string("elapsed time");
1196 LTTV_STATS_EVENTS = g_quark_from_string("events");
1197 LTTV_STATS_EVENTS_COUNT = g_quark_from_string("events count");
1198 LTTV_STATS_BEFORE_HOOKS = g_quark_from_string("saved stats before hooks");
1199 LTTV_STATS_AFTER_HOOKS = g_quark_from_string("saved stats after hooks");
f95bc830 1200 LTTV_STATS_USE_COUNT = g_quark_from_string("stats_use_count");
1201 LTTV_STATS = g_quark_from_string("statistics");
1202 LTTV_STATS_TRACEFILES = g_quark_from_string("tracefiles statistics");
1203 LTTV_STATS_SUMMED = g_quark_from_string("statistics summed");
08b1c66e 1204}
1205
1206static void module_destroy()
1207{
1208}
1209
1210
1211LTTV_MODULE("stats", "Compute processes statistics", \
1212 "Accumulate statistics for event types, processes and CPUs", \
1213 module_init, module_destroy, "state");
f95bc830 1214
1215/* Change the places where stats are called (create/read/write stats)
1216
1217 Check for options in batchtest.c to reduce writing and see what tests are
1218 best candidates for performance analysis. Once OK, commit, move to main
1219 and run tests. Update the gui for statistics. */
This page took 0.094456 seconds and 4 git commands to generate.