Process state in gui
[lttv.git] / lttv / modules / gui / lttvwindow / lttvwindow / callbacks.c
CommitLineData
e076699e 1/* This file is part of the Linux Trace Toolkit viewer
b052368a 2 * Copyright (C) 2003-2004 XangXiu Yang, Mathieu Desnoyers
e076699e 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
561eba2a 19#ifdef HAVE_CONFIG_H
20# include <config.h>
21#endif
22
a1a2b649 23#include <limits.h> // for PATH_MAX
24#include <stdlib.h>
f02b5e22 25#include <ctype.h>
26#include <string.h>
27#include <stdlib.h>
a1a2b649 28
561eba2a 29#include <gtk/gtk.h>
561eba2a 30
31#include "callbacks.h"
32#include "interface.h"
33#include "support.h"
a43d67ba 34#include <ltt/trace.h>
a43d67ba 35#include <ltt/time.h>
36#include <ltt/event.h>
2a2fa4f0 37#include <lttv/lttv.h>
a43d67ba 38#include <lttv/module.h>
39#include <lttv/iattribute.h>
451aaf27
FD
40#include <lttv/traceset.h>
41#ifdef BABEL_CLEANUP
a43d67ba 42#include <lttv/stats.h>
2f076594 43#include <lttv/sync/sync_chain_lttv.h>
451aaf27
FD
44#endif /* BABEL_CLEANUP */
45#include <lttv/filter.h>
13f86ce2 46#include <lttvwindow/mainwindow.h>
2d262115 47#include <lttvwindow/mainwindow-private.h>
13f86ce2 48#include <lttvwindow/menu.h>
4172f013 49#include <lttvwindow/timebar.h>
13f86ce2 50#include <lttvwindow/toolbar.h>
501e4e70 51#include <lttvwindow/lttvwindow.h>
a1a2b649 52#include <lttvwindow/lttvwindowtraces.h>
e433e6d6 53#include <lttvwindow/lttv_plugin_tab.h>
a1a2b649 54
451aaf27
FD
55#include <babeltrace/babeltrace.h>
56#include <babeltrace/ctf/events.h>
57#include <babeltrace/ctf/iterator.h>
58
6c35c853 59static LttTime lttvwindow_default_time_width = { 1, 0 };
f02b5e22 60#define CLIP_BUF 256 // size of clipboard buffer
f7afe191 61
49bf71b5 62extern LttvTrace *g_init_trace ;
561eba2a 63
ec25ff5e 64
65/** Array containing instanced objects. */
68b48a45 66extern GSList * g_main_window_list;
561eba2a 67
a43d67ba 68/** MD : keep old directory. */
a1a2b649 69static char remember_plugins_dir[PATH_MAX] = "";
70static char remember_trace_dir[PATH_MAX] = "";
6fbb1ddf 71
e433e6d6 72void tab_destructor(LttvPluginTab * ptab);
6fbb1ddf 73
bca3b81f 74MainWindow * get_window_data_struct(GtkWidget * widget);
93ac601b 75char * get_load_module(MainWindow *mw,
76 char ** load_module_name, int nb_module);
77char * get_unload_module(MainWindow *mw,
78 char ** loaded_module_name, int nb_module);
79char * get_remove_trace(MainWindow *mw, char ** all_trace_name, int nb_trace);
80char * get_selection(MainWindow *mw,
81 char ** all_name, int nb, char *title, char * column_title);
e433e6d6 82void init_tab(Tab *tab, MainWindow * mw, Tab *copy_tab,
716e4367 83 GtkNotebook * notebook, char * label);
561eba2a 84
68764dff
AM
85int update_traceset(Tab *tab, LttvTraceset *traceset);
86
2d262115 87static void insert_viewer(GtkWidget* widget, lttvwindow_viewer_constructor constructor);
49bf71b5 88
e433e6d6 89LttvPluginTab *create_new_tab(GtkWidget* widget, gpointer user_data);
49bf71b5 90
501e4e70 91static gboolean lttvwindow_process_pending_requests(Tab *tab);
202f6c8f 92
4172f013
YB
93static void on_timebar_starttime_changed(Timebar *timebar,
94 gpointer user_data);
95static void on_timebar_endtime_changed(Timebar *timebar,
96 gpointer user_data);
97static void on_timebar_currenttime_changed(Timebar *timebar,
98 gpointer user_data);
99
49bf71b5 100enum {
101 CHECKBOX_COLUMN,
102 NAME_COLUMN,
103 TOTAL_COLUMNS
104};
561eba2a 105
36b3c068 106enum
107{
108 MODULE_COLUMN,
109 N_COLUMNS
110};
111
f02b5e22 112
e433e6d6 113#if 0
114static void on_top_notify(GObject *gobject,
115 GParamSpec *arg1,
116 gpointer user_data)
117{
118 Tab *tab = (Tab*)user_data;
119 g_message("in on_top_notify.\n");
f02b5e22 120
e433e6d6 121}
122#endif //0
b052368a 123static gboolean viewer_grab_focus(GtkWidget *widget, GdkEventButton *event,
124 gpointer data)
125{
f37a2002 126 GtkWidget *viewer = GTK_WIDGET(data);
127 GtkWidget *viewer_container = gtk_widget_get_parent(viewer);
b052368a 128
129 g_debug("FOCUS GRABBED");
f37a2002 130 g_object_set_data(G_OBJECT(viewer_container), "focused_viewer", viewer);
131 return 0;
b052368a 132}
133
f02b5e22 134
f37a2002 135static void connect_focus_recursive(GtkWidget *widget,
136 GtkWidget *viewer)
137{
138 if(GTK_IS_CONTAINER(widget)) {
139 gtk_container_forall(GTK_CONTAINER(widget),
140 (GtkCallback)connect_focus_recursive,
141 viewer);
1818a315 142
143 }
144 if(GTK_IS_TREE_VIEW(widget)) {
2eef04b5 145 gtk_tree_view_set_headers_clickable(GTK_TREE_VIEW(widget), TRUE);
f37a2002 146 }
147 gtk_widget_add_events(widget, GDK_BUTTON_PRESS_MASK);
148 g_signal_connect (G_OBJECT(widget),
149 "button-press-event",
150 G_CALLBACK (viewer_grab_focus),
151 (gpointer)viewer);
152}
b052368a 153
d27948a3 154/* Stop all the processings and call gtk_main_quit() */
155static void mainwindow_quit()
156{
157 lttvwindowtraces_unregister_requests(g_quark_from_string("stats"));
158 lttvwindowtraces_unregister_requests(g_quark_from_string("state"));
159 lttvwindowtraces_unregister_computation_hooks(g_quark_from_string("stats"));
160 lttvwindowtraces_unregister_computation_hooks(g_quark_from_string("state"));
161
162 gtk_main_quit();
163}
164
165
abe346a3 166/* insert_viewer function constructs an instance of a viewer first,
167 * then inserts the widget of the instance into the container of the
168 * main window
169 */
170
561eba2a 171void
606309a4 172insert_viewer_wrap(GtkWidget *menuitem, gpointer user_data)
561eba2a 173{
42fcbb71 174 insert_viewer((GtkWidget*)menuitem, (lttvwindow_viewer_constructor)user_data);
561eba2a 175}
176
561eba2a 177
178/* internal functions */
2d262115 179void insert_viewer(GtkWidget* widget, lttvwindow_viewer_constructor constructor)
561eba2a 180{
b052368a 181 GtkWidget * viewer_container;
6ced96ef 182 GtkWidget * notebook = lookup_widget(widget, "MNotebook");
f9334f6f 183 GtkWidget * viewer;
6ced96ef 184 GtkWidget *page = gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook),
185 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook)));
e433e6d6 186 LttvPluginTab *ptab;
6ced96ef 187 Tab *tab;
188
189 if(!page) {
e433e6d6 190 ptab = create_new_tab(widget, NULL);
6ced96ef 191 } else {
e433e6d6 192 ptab = (LttvPluginTab *)g_object_get_data(G_OBJECT(page), "Tab_Plugin");
47cd8a09 193 }
e433e6d6 194 tab = ptab->tab;
47cd8a09 195
b052368a 196 viewer_container = tab->viewer_container;
561eba2a 197
7d0aa40c 198 viewer = (GtkWidget*)constructor(&ptab->parent);
f9334f6f 199 if(viewer)
f0d936c0 200 {
b052368a 201 //gtk_multivpaned_widget_add(GTK_MULTIVPANED(multivpaned), viewer);
202
203 gtk_box_pack_end(GTK_BOX(viewer_container),
204 viewer,
205 TRUE,
206 TRUE,
207 0);
208
f37a2002 209 /* We want to connect the viewer_grab_focus to EVERY
210 * child of this widget. The little trick is to get each child
211 * of each GTK_CONTAINER, even subchildren.
212 */
0f9d55ef 213 connect_focus_recursive(viewer, viewer);
f0d936c0 214 }
561eba2a 215}
216
313bd6fc 217/**
218 * Function to set/update traceset for the viewers
219 * @param tab viewer's tab
220 * @param traceset traceset of the main window.
221 * return value :
222 * 0 : traceset updated
223 * 1 : no traceset hooks to update; not an error.
224 */
225
226int SetTraceset(Tab * tab, LttvTraceset *traceset)
227{
451aaf27 228
482fe481
BP
229 TimeInterval time_span;
230 TimeWindow new_time_window;
231 LttTime new_current_time;
d26f0474 232
451aaf27 233#ifdef BABEL_CLEANUP
482fe481 234 // Perform time synchronization on the traces
665fdbb7 235 if (syncTraceset(tsc))
482fe481
BP
236 {
237 /* There is some time-dependant information that was calculated during
238 * context initialization. Destroy the old contexts and initialize new
239 * ones.
240 * Modified from lttvwindow_add_trace()
241 */
242 // Keep a reference to the traces so they are not freed
243 for(i = 0; i < lttv_traceset_number(traceset); i++)
244 {
245 LttvTrace *trace = lttv_traceset_get(traceset, i);
246 lttv_trace_ref(trace);
247 }
248
249 // Remove state update hooks
250 lttv_state_remove_event_hooks(
251 (LttvTracesetState*)tab->traceset_info->traceset_context);
252
253 lttv_context_fini(LTTV_TRACESET_CONTEXT(
254 tab->traceset_info->traceset_context));
255 g_object_unref(tab->traceset_info->traceset_context);
256
257 for(i = 0; i < lttv_traceset_number(traceset); i++)
258 {
259 LttvTrace *trace = lttv_traceset_get(traceset, i);
260 lttvwindowtraces_remove_trace(trace);
261 lttvwindowtraces_add_trace(trace);
262 }
263
264 // Create new context
265 tab->traceset_info->traceset_context =
266 g_object_new(LTTV_TRACESET_STATS_TYPE, NULL);
267 lttv_context_init(LTTV_TRACESET_CONTEXT(tab->traceset_info->
268 traceset_context), traceset);
269
270 // Add state update hooks
271 lttv_state_add_event_hooks(
272 (LttvTracesetState*)tab->traceset_info->traceset_context);
273
274 // Remove local reference to the traces
275 for(i=0; i<lttv_traceset_number(traceset); i++)
276 {
277 LttvTrace *trace = lttv_traceset_get(traceset, i);
278 lttv_trace_unref(trace);
279 }
280
281 tsc = LTTV_TRACESET_CONTEXT(tab->traceset_info->traceset_context);
282 }
451aaf27 283#endif /*BABEL_CLEANUP*/
482fe481 284
9aaa78dc 285 time_span = lttv_traceset_get_time_span(traceset);
451aaf27
FD
286
287 tab->traceset_info->traceset = traceset;
288
289 new_time_window = tab->time_window;
290 new_current_time = tab->current_time;
291
1ba187d3 292 /* Set the tab's time window and current time if
293 * out of bounds */
294 if(ltt_time_compare(tab->time_window.start_time, time_span.start_time) < 0
6f26fc38 295 || ltt_time_compare(tab->time_window.end_time,
1ba187d3 296 time_span.end_time) > 0) {
e800cf84 297 new_time_window.start_time = time_span.start_time;
298
299 new_current_time = time_span.start_time;
1ba187d3 300
301 LttTime tmp_time;
6c35c853 302
303 if(ltt_time_compare(lttvwindow_default_time_width,
4249a3e8 304 ltt_time_sub(time_span.end_time, time_span.start_time)) < 0
305 ||
306 ltt_time_compare(time_span.end_time, time_span.start_time) == 0)
6c35c853 307 tmp_time = lttvwindow_default_time_width;
1ba187d3 308 else
6c35c853 309 tmp_time = time_span.end_time;
310
e800cf84 311 new_time_window.time_width = tmp_time ;
a18124ff 312 new_time_window.time_width_double = ltt_time_to_double(tmp_time);
6f26fc38 313 new_time_window.end_time = ltt_time_add(new_time_window.start_time,
314 new_time_window.time_width) ;
1ba187d3 315 }
a7598d50 316 lttv_state_add_event_hooks(traceset);
e800cf84 317
1ba187d3 318 /* Finally, call the update hooks of the viewers */
68764dff 319 gint retval = update_traceset(tab, traceset);
1ba187d3 320
4249a3e8 321 time_change_manager(tab, new_time_window);
322 current_time_change_manager(tab, new_current_time);
323
b052368a 324 return retval;
451aaf27 325
313bd6fc 326}
327
328/**
329 * Function to set/update filter for the viewers
330 * @param tab viewer's tab
331 * @param filter filter of the main window.
332 * return value :
333 * -1 : error
334 * 0 : filters updated
335 * 1 : no filter hooks to update; not an error.
336 */
a998b781 337#if 0
313bd6fc 338int SetFilter(Tab * tab, gpointer filter)
339{
340 LttvHooks * tmp;
341 LttvAttributeValue value;
342
343 g_assert(lttv_iattribute_find_by_path(tab->attributes,
344 "hooks/updatefilter", LTTV_POINTER, &value));
345
346 tmp = (LttvHooks*)*(value.v_pointer);
347
348 if(tmp == NULL) return 1;
349 lttv_hooks_call(tmp,filter);
350
351 return 0;
352}
a998b781 353#endif //0
313bd6fc 354
355
356/**
357 * Function to redraw each viewer belonging to the current tab
358 * @param tab viewer's tab
359 */
360
1e3594a3 361int update_traceset(Tab *tab, LttvTraceset *traceset)
313bd6fc 362{
363 LttvAttributeValue value;
364 LttvHooks * tmp;
8f318283
BP
365 gboolean retval;
366
367 retval= lttv_iattribute_find_by_path(tab->attributes,
1e3594a3
YB
368 "hooks/updatetraceset",
369 LTTV_POINTER,
370 &value);
8f318283 371 g_assert(retval);
313bd6fc 372 tmp = (LttvHooks*)*(value.v_pointer);
1e3594a3
YB
373 if(tmp == NULL) {
374 retval = 1;
375 } else {
376 lttv_hooks_call(tmp, traceset);
377 }
378 return retval;
313bd6fc 379}
380
1e3594a3
YB
381/**
382 Call hooks register to get update on traceset time span changes
383*/
384int notify_time_span_changed(Tab *tab)
385{
386 LttvAttributeValue value;
387 LttvHooks * tmp;
388 gboolean retval;
389
390 retval= lttv_iattribute_find_by_path(tab->attributes,
391 "hooks/updatetimespan",
392 LTTV_POINTER,
393 &value);
394 g_assert(retval);
395 tmp = (LttvHooks*)*(value.v_pointer);
396 if(tmp == NULL) {
397 retval = 1;
398 } else {
399 lttv_hooks_call(tmp, NULL);
400 }
401 return retval;
402}
abe346a3 403
404/* get_label function is used to get user input, it displays an input
405 * box, which allows user to input a string
406 */
407
561eba2a 408void get_label_string (GtkWidget * text, gchar * label)
409{
410 GtkEntry * entry = (GtkEntry*)text;
411 if(strlen(gtk_entry_get_text(entry))!=0)
412 strcpy(label,gtk_entry_get_text(entry));
413}
414
eb38aea5 415gboolean get_label(MainWindow * mw, gchar * str, gchar* dialogue_title, gchar * label_str)
561eba2a 416{
417 GtkWidget * dialogue;
418 GtkWidget * text;
419 GtkWidget * label;
420 gint id;
421
5723fa24 422 dialogue = gtk_dialog_new_with_buttons(dialogue_title,NULL,
561eba2a 423 GTK_DIALOG_MODAL,
424 GTK_STOCK_OK,GTK_RESPONSE_ACCEPT,
425 GTK_STOCK_CANCEL,GTK_RESPONSE_REJECT,
426 NULL);
427
6b1d3120 428 label = gtk_label_new(label_str);
561eba2a 429 gtk_widget_show(label);
430
431 text = gtk_entry_new();
432 gtk_widget_show(text);
433
434 gtk_box_pack_start(GTK_BOX(GTK_DIALOG(dialogue)->vbox), label,TRUE, TRUE,0);
435 gtk_box_pack_start(GTK_BOX(GTK_DIALOG(dialogue)->vbox), text,FALSE, FALSE,0);
436
437 id = gtk_dialog_run(GTK_DIALOG(dialogue));
438 switch(id){
439 case GTK_RESPONSE_ACCEPT:
440 get_label_string(text,str);
441 gtk_widget_destroy(dialogue);
442 break;
443 case GTK_RESPONSE_REJECT:
444 default:
445 gtk_widget_destroy(dialogue);
eb38aea5 446 return FALSE;
561eba2a 447 }
eb38aea5 448 return TRUE;
561eba2a 449}
450
abe346a3 451
452/* get_window_data_struct function is actually a lookup function,
453 * given a widget which is in the tree of the main window, it will
454 * return the MainWindow data structure associated with main window
455 */
456
bca3b81f 457MainWindow * get_window_data_struct(GtkWidget * widget)
561eba2a 458{
459 GtkWidget * mw;
bca3b81f 460 MainWindow * mw_data;
561eba2a 461
462 mw = lookup_widget(widget, "MWindow");
463 if(mw == NULL){
56e5a0f7 464 g_info("Main window does not exist\n");
2d262115 465 return NULL;
561eba2a 466 }
467
2d262115 468 mw_data = (MainWindow *) g_object_get_data(G_OBJECT(mw),"main_window_data");
68b48a45 469 if(mw_data == NULL){
2eef04b5 470 g_warning("Main window data does not exist\n");
2d262115 471 return NULL;
561eba2a 472 }
68b48a45 473 return mw_data;
561eba2a 474}
475
abe346a3 476
477/* create_new_window function, just constructs a new main window
478 */
479
68b48a45 480void create_new_window(GtkWidget* widget, gpointer user_data, gboolean clone)
561eba2a 481{
bca3b81f 482 MainWindow * parent = get_window_data_struct(widget);
561eba2a 483
561eba2a 484 if(clone){
56e5a0f7 485 g_info("Clone : use the same traceset\n");
08b1c66e 486 construct_main_window(parent);
561eba2a 487 }else{
56e5a0f7 488 g_info("Empty : traceset is set to NULL\n");
08b1c66e 489 construct_main_window(NULL);
561eba2a 490 }
491}
492
0f9d55ef 493/* Get the currently focused viewer.
494 * If no viewer is focused, use the first one.
495 *
496 * If no viewer available, return NULL.
497 */
b052368a 498GtkWidget *viewer_container_focus(GtkWidget *container)
499{
500 GtkWidget *widget;
501
502 widget = (GtkWidget*)g_object_get_data(G_OBJECT(container),
bb574a9c 503 "focused_viewer");
b052368a 504
0f9d55ef 505 if(widget == NULL) {
506 g_debug("no widget focused");
507 GList *children = gtk_container_get_children(GTK_CONTAINER(container));
508
509 if(children != NULL)
510 widget = GTK_WIDGET(children->data);
bb574a9c 511 g_object_set_data(G_OBJECT(container),
512 "focused_viewer",
513 widget);
0f9d55ef 514 }
515
b052368a 516 return widget;
517
518
519}
520
521gint viewer_container_position(GtkWidget *container, GtkWidget *child)
522{
523
524 if(child == NULL) return -1;
525
526 gint pos;
2eef04b5 527 GValue value;
528 memset(&value, 0, sizeof(GValue));
b052368a 529 g_value_init(&value, G_TYPE_INT);
530 gtk_container_child_get_property(GTK_CONTAINER(container),
531 child,
532 "position",
533 &value);
534 pos = g_value_get_int(&value);
535
536 return pos;
537}
538
abe346a3 539
540/* move_*_viewer functions move the selected view up/down in
541 * the current tab
542 */
543
b052368a 544void move_down_viewer(GtkWidget * widget, gpointer user_data)
561eba2a 545{
6ced96ef 546 GtkWidget * notebook = lookup_widget(widget, "MNotebook");
547
548 GtkWidget *page = gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook),
549 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook)));
550
551 Tab *tab;
6ced96ef 552 if(!page) {
553 return;
554 } else {
e433e6d6 555 LttvPluginTab *ptab;
43ed82b5 556 ptab = g_object_get_data(G_OBJECT(page), "Tab_Plugin");
e433e6d6 557 tab = ptab->tab;
6ced96ef 558 }
559
b052368a 560 //gtk_multivpaned_widget_move_up(GTK_MULTIVPANED(tab->multivpaned));
561
562 /* change the position in the vbox */
563 GtkWidget *focus_widget;
564 gint position;
565 focus_widget = viewer_container_focus(tab->viewer_container);
566 position = viewer_container_position(tab->viewer_container, focus_widget);
567
568 if(position > 0) {
569 /* can move up one position */
570 gtk_box_reorder_child(GTK_BOX(tab->viewer_container),
571 focus_widget,
572 position-1);
573 }
574
561eba2a 575}
576
b052368a 577void move_up_viewer(GtkWidget * widget, gpointer user_data)
561eba2a 578{
6ced96ef 579 GtkWidget * notebook = lookup_widget(widget, "MNotebook");
580
581 GtkWidget *page = gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook),
582 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook)));
583 Tab *tab;
584
585 if(!page) {
586 return;
587 } else {
e433e6d6 588 LttvPluginTab *ptab;
589 ptab = (LttvPluginTab *)g_object_get_data(G_OBJECT(page), "Tab_Plugin");
590 tab = ptab->tab;
6ced96ef 591 }
592
b052368a 593 //gtk_multivpaned_widget_move_down(GTK_MULTIVPANED(tab->multivpaned));
594 /* change the position in the vbox */
595 GtkWidget *focus_widget;
596 gint position;
597 focus_widget = viewer_container_focus(tab->viewer_container);
598 position = viewer_container_position(tab->viewer_container, focus_widget);
599
600 if(position != -1 &&
601 position <
602 g_list_length(gtk_container_get_children(
603 GTK_CONTAINER(tab->viewer_container)))-1
604 ) {
605 /* can move down one position */
606 gtk_box_reorder_child(GTK_BOX(tab->viewer_container),
607 focus_widget,
608 position+1);
609 }
610
561eba2a 611}
612
abe346a3 613
614/* delete_viewer deletes the selected viewer in the current tab
615 */
616
561eba2a 617void delete_viewer(GtkWidget * widget, gpointer user_data)
618{
6ced96ef 619 GtkWidget * notebook = lookup_widget(widget, "MNotebook");
620
621 GtkWidget *page = gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook),
622 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook)));
623 Tab *tab;
624
625 if(!page) {
626 return;
627 } else {
e433e6d6 628 LttvPluginTab *ptab;
43ed82b5 629 ptab = g_object_get_data(G_OBJECT(page), "Tab_Plugin");
e433e6d6 630 tab = ptab->tab;
6ced96ef 631 }
632
b052368a 633 //gtk_multivpaned_widget_delete(GTK_MULTIVPANED(tab->multivpaned));
634
635 GtkWidget *focus_widget = viewer_container_focus(tab->viewer_container);
636
637 if(focus_widget != NULL)
638 gtk_widget_destroy(focus_widget);
639
640 g_object_set_data(G_OBJECT(tab->viewer_container), "focused_viewer", NULL);
561eba2a 641}
642
e865422c
YB
643#if UNFINISHED_FEATURE
644/* TODO ybrosseau 2012-03-15: Function is half implemented. Should be removed */
abe346a3 645/* open_traceset will open a traceset saved in a file
646 * Right now, it is not finished yet, (not working)
a43d67ba 647 * FIXME
abe346a3 648 */
649
561eba2a 650void open_traceset(GtkWidget * widget, gpointer user_data)
651{
2176f952 652 char ** dir;
653 gint id;
654 LttvTraceset * traceset;
bca3b81f 655 MainWindow * mw_data = get_window_data_struct(widget);
68b48a45 656 GtkFileSelection * file_selector =
2176f952 657 (GtkFileSelection *)gtk_file_selection_new("Select a traceset");
658
68b48a45 659 gtk_file_selection_hide_fileop_buttons(file_selector);
c64c7ea1 660
93ac601b 661 gtk_window_set_transient_for(GTK_WINDOW(file_selector),
662 GTK_WINDOW(mw_data->mwindow));
663
68b48a45 664 id = gtk_dialog_run(GTK_DIALOG(file_selector));
2176f952 665 switch(id){
666 case GTK_RESPONSE_ACCEPT:
667 case GTK_RESPONSE_OK:
68b48a45 668 dir = gtk_file_selection_get_selections (file_selector);
2176f952 669 traceset = lttv_traceset_load(dir[0]);
56e5a0f7 670 g_info("Open a trace set %s\n", dir[0]);
2176f952 671 //Not finished yet
672 g_strfreev(dir);
673 case GTK_RESPONSE_REJECT:
674 case GTK_RESPONSE_CANCEL:
675 default:
68b48a45 676 gtk_widget_destroy((GtkWidget*)file_selector);
2176f952 677 break;
678 }
c64c7ea1 679
561eba2a 680}
e865422c 681#endif
501e4e70 682/* lttvwindow_process_pending_requests
d389bc8d 683 *
684 * Process requests for parts of the trace from viewers.
685 *
686 * These requests are made by lttvwindow_events_request().
501e4e70 687 *
688 * This internal function gets called by g_idle, taking care of the pending
689 * requests. It is responsible for concatenation of time intervals and position
690 * requests. It does it with the following algorithm organizing process traceset
691 * calls. Here is the detailed description of the way it works :
692 *
693 * - Events Requests Servicing Algorithm
694 *
695 * Data structures necessary :
696 *
697 * List of requests added to context : list_in
698 * List of requests not added to context : list_out
699 *
700 * Initial state :
701 *
702 * list_in : empty
703 * list_out : many events requests
704 *
705 * FIXME : insert rest of algorithm here
706 *
abe346a3 707 */
708
6ea08962 709#define list_out tab->events_requests
a43d67ba 710
501e4e70 711gboolean lttvwindow_process_pending_requests(Tab *tab)
a8c0f09d 712{
ff5c41f1
YB
713
714 LttvTraceset *ts;
715
501e4e70 716 GSList *list_in = NULL;
717 LttTime end_time;
718 guint end_nb_events;
2d262115 719 guint count;
ff5c41f1 720 LttvTracesetPosition *end_position;
a43d67ba 721
3c456a8a 722 if(lttvwindow_preempt_count > 0) return TRUE;
723
b052368a 724 if(tab == NULL) {
725 g_critical("Foreground processing : tab does not exist. Processing removed.");
501e4e70 726 return FALSE;
b052368a 727 }
a43d67ba 728
501e4e70 729 /* There is no events requests pending : we should never have been called! */
6ea08962 730 g_assert(g_slist_length(list_out) != 0);
a43d67ba 731
ff5c41f1 732 ts = tab->traceset_info->traceset;
a8c0f09d 733
abe346a3 734 //set the cursor to be X shape, indicating that the computer is busy in doing its job
a0577796 735#if 0
a8c0f09d 736 new = gdk_cursor_new(GDK_X_CURSOR);
2d262115 737 widget = lookup_widget(tab->mw->mwindow, "MToolbar1");
a8c0f09d 738 win = gtk_widget_get_parent_window(widget);
739 gdk_window_set_cursor(win, new);
740 gdk_cursor_unref(new);
741 gdk_window_stick(win);
742 gdk_window_unstick(win);
a0577796 743#endif //0
a43d67ba 744
6ea08962 745 g_debug("SIZE events req len : %d", g_slist_length(list_out));
746
747 /* Preliminary check for no trace in traceset */
748 /* Unregister the routine if empty, empty list_out too */
ff5c41f1 749 if(lttv_traceset_number(ts) == 0) {
6ea08962 750
751 /* - For each req in list_out */
752 GSList *iter = list_out;
753
754 while(iter != NULL) {
755
756 gboolean remove = FALSE;
757 gboolean free_data = FALSE;
758 EventsRequest *events_request = (EventsRequest *)iter->data;
759
760 /* - Call end request for req */
761 if(events_request->servicing == TRUE)
ff5c41f1 762 lttv_hooks_call(events_request->after_request, (gpointer)ts);
6ea08962 763
764 /* - remove req from list_out */
765 /* Destroy the request */
766 remove = TRUE;
767 free_data = TRUE;
ff5c41f1 768 //TODO ybrosseau: This if is always true
6ea08962 769 /* Go to next */
770 if(remove)
771 {
772 GSList *remove_iter = iter;
773
774 iter = g_slist_next(iter);
b052368a 775 if(free_data) events_request_free((EventsRequest*)remove_iter->data);
6ea08962 776 list_out = g_slist_remove_link(list_out, remove_iter);
777 } else { // not remove
778 iter = g_slist_next(iter);
779 }
780 }
781 }
088f6772 782
b052368a 783 /* 0.1 Lock Traces */
784 {
785 guint iter_trace=0;
786
787 for(iter_trace=0;
ff5c41f1 788 iter_trace<lttv_traceset_number(ts);
b052368a 789 iter_trace++) {
ff5c41f1 790 LttvTrace *trace_v = lttv_traceset_get(ts, iter_trace);
b052368a 791
792 if(lttvwindowtraces_lock(trace_v) != 0) {
793 g_critical("Foreground processing : Unable to get trace lock");
794 return TRUE; /* Cannot get lock, try later */
795 }
796 }
797 }
798
799 /* 0.2 Seek tracefiles positions to context position */
ff5c41f1 800#ifdef BABEL_CLEANUP
088f6772 801 //g_assert(lttv_process_traceset_seek_position(tsc, sync_position) == 0);
b052368a 802 lttv_process_traceset_synchronize_tracefiles(tsc);
ff5c41f1 803#endif
b052368a 804
501e4e70 805 /* Events processing algorithm implementation */
dd316a11 806 /* Warning : the gtk_events_pending takes a LOT of cpu time. So what we do
807 * instead is to leave the control to GTK and take it back.
808 */
501e4e70 809 /* A. Servicing loop */
dd316a11 810 //while( (g_slist_length(list_in) != 0 || g_slist_length(list_out) != 0)) {
3bafb436 811 if((g_slist_length(list_in) != 0 || g_slist_length(list_out) != 0)) {
812 /* Servicing */
813 /* 1. If list_in is empty (need a seek) */
814 if( g_slist_length(list_in) == 0 ) {
501e4e70 815
3bafb436 816 /* list in is empty, need a seek */
dd316a11 817 {
3bafb436 818 /* 1.1 Add requests to list_in */
819 GSList *ltime = NULL;
820 GSList *lpos = NULL;
821 GSList *iter = NULL;
501e4e70 822
3bafb436 823 /* 1.1.1 Find all time requests with the lowest start time in list_out
824 * (ltime)
825 */
826 if(g_slist_length(list_out) > 0)
827 ltime = g_slist_append(ltime, g_slist_nth_data(list_out, 0));
828 for(iter=g_slist_nth(list_out,1);iter!=NULL;iter=g_slist_next(iter)) {
829 /* Find all time requests with the lowest start time in list_out */
3bafb436 830 EventsRequest *event_request_ltime = (EventsRequest*)g_slist_nth_data(ltime, 0);
831 EventsRequest *event_request_list_out = (EventsRequest*)iter->data;
832
833 int comp;
834 comp = ltt_time_compare(event_request_ltime->start_time,
835 event_request_list_out->start_time);
836 if(comp == 0)
837 ltime = g_slist_append(ltime, event_request_list_out);
838 else if(comp > 0) {
839 /* Remove all elements from ltime, and add current */
840 while(ltime != NULL)
841 ltime = g_slist_delete_link(ltime, g_slist_nth(ltime, 0));
842 ltime = g_slist_append(ltime, event_request_list_out);
843 }
501e4e70 844 }
845
3bafb436 846 /* 1.1.2 Find all position requests with the lowest position in list_out
847 * (lpos)
848 */
849 if(g_slist_length(list_out) > 0)
850 lpos = g_slist_append(lpos, g_slist_nth_data(list_out, 0));
851 for(iter=g_slist_nth(list_out,1);iter!=NULL;iter=g_slist_next(iter)) {
852 /* Find all position requests with the lowest position in list_out */
853 EventsRequest *event_request_lpos = (EventsRequest*)g_slist_nth_data(lpos, 0);
854 EventsRequest *event_request_list_out = (EventsRequest*)iter->data;
855
856 int comp;
857 if(event_request_lpos->start_position != NULL
858 && event_request_list_out->start_position != NULL)
859 {
ff5c41f1
YB
860 //TODO ybrosseau: this compare is in fact an equal, so the behavior might not be right.
861 comp = lttv_traceset_position_time_compare
3bafb436 862 (event_request_lpos->start_position,
863 event_request_list_out->start_position);
864 } else {
865 comp = -1;
553d1e7b 866 }
3bafb436 867 if(comp == 0)
868 lpos = g_slist_append(lpos, event_request_list_out);
869 else if(comp > 0) {
870 /* Remove all elements from lpos, and add current */
871 while(lpos != NULL)
872 lpos = g_slist_delete_link(lpos, g_slist_nth(lpos, 0));
873 lpos = g_slist_append(lpos, event_request_list_out);
501e4e70 874 }
875 }
3bafb436 876
877 {
878 EventsRequest *event_request_lpos = (EventsRequest*)g_slist_nth_data(lpos, 0);
879 EventsRequest *event_request_ltime = (EventsRequest*)g_slist_nth_data(ltime, 0);
880 LttTime lpos_start_time;
dd316a11 881
3bafb436 882 if(event_request_lpos != NULL
883 && event_request_lpos->start_position != NULL) {
ff5c41f1 884 lpos_start_time = lttv_traceset_position_get_time(
3bafb436 885 event_request_lpos->start_position);
886 }
887
888 /* 1.1.3 If lpos.start time < ltime */
889 if(event_request_lpos != NULL
890 && event_request_lpos->start_position != NULL
891 && ltt_time_compare(lpos_start_time,
892 event_request_ltime->start_time)<0) {
893 /* Add lpos to list_in, remove them from list_out */
894 for(iter=lpos;iter!=NULL;iter=g_slist_next(iter)) {
895 /* Add to list_in */
896 EventsRequest *event_request_lpos =
897 (EventsRequest*)iter->data;
898
899 list_in = g_slist_append(list_in, event_request_lpos);
900 /* Remove from list_out */
901 list_out = g_slist_remove(list_out, event_request_lpos);
902 }
903 } else {
904 /* 1.1.4 (lpos.start time >= ltime) */
905 /* Add ltime to list_in, remove them from list_out */
906
907 for(iter=ltime;iter!=NULL;iter=g_slist_next(iter)) {
908 /* Add to list_in */
909 EventsRequest *event_request_ltime =
910 (EventsRequest*)iter->data;
911
912 list_in = g_slist_append(list_in, event_request_ltime);
913 /* Remove from list_out */
914 list_out = g_slist_remove(list_out, event_request_ltime);
915 }
916 }
dd316a11 917 }
3bafb436 918 g_slist_free(lpos);
919 g_slist_free(ltime);
dd316a11 920 }
dd316a11 921
3bafb436 922 /* 1.2 Seek */
923 {
ff5c41f1 924
3bafb436 925 g_assert(g_slist_length(list_in)>0);
926 EventsRequest *events_request = g_slist_nth_data(list_in, 0);
e865422c 927#ifdef DEBUG
3bafb436 928 guint seek_count;
e865422c 929#endif
3bafb436 930
931 /* 1.2.1 If first request in list_in is a time request */
932 if(events_request->start_position == NULL) {
933 /* - If first req in list_in start time != current time */
ff5c41f1
YB
934 //TODO ybrosseau: if commented out, since it was only affecting the g_debug
935 //if(tfc == NULL || ltt_time_compare(events_request->start_time,
936 // tfc->timestamp) != 0)
3bafb436 937 /* - Seek to that time */
938 g_debug("SEEK TIME : %lu, %lu", events_request->start_time.tv_sec,
939 events_request->start_time.tv_nsec);
940 //lttv_process_traceset_seek_time(tsc, events_request->start_time);
ff5c41f1 941 lttv_process_traceset_seek_time(ts,
3bafb436 942 events_request->start_time);
943
944 /* Process the traceset with only state hooks */
e865422c 945#ifdef DEBUG
3bafb436 946 seek_count =
e865422c 947#endif //DEBUG
ff5c41f1 948 lttv_process_traceset_middle(ts,
3bafb436 949 events_request->start_time,
950 G_MAXUINT, NULL);
f4b88a7d 951#ifdef DEBUG
952 g_assert(seek_count < LTTV_STATE_SAVE_INTERVAL);
953#endif //DEBUG
6ea08962 954
a43d67ba 955
3bafb436 956 } else {
ff5c41f1
YB
957 //LttTime pos_time;
958 //LttvTracefileContext *tfc =
959 // lttv_traceset_context_get_current_tfc(tsc);
3bafb436 960 /* Else, the first request in list_in is a position request */
961 /* If first req in list_in pos != current pos */
962 g_assert(events_request->start_position != NULL);
963 g_debug("SEEK POS time : %lu, %lu",
ff5c41f1 964 lttv_traceset_position_get_time(
3bafb436 965 events_request->start_position).tv_sec,
ff5c41f1 966 lttv_traceset_position_get_time(
3bafb436 967 events_request->start_position).tv_nsec);
2a7a425c 968
ff5c41f1
YB
969 /*if(tfc) {*/ if(0) {
970 /* g_debug("SEEK POS context time : %lu, %lu",
971 tfc->timestamp.tv_sec,
972 tfc->timestamp.tv_nsec); */
2a7a425c 973 } else {
974 g_debug("SEEK POS context time : %lu, %lu",
975 ltt_time_infinite.tv_sec,
976 ltt_time_infinite.tv_nsec);
977 }
3bafb436 978 g_assert(events_request->start_position != NULL);
ff5c41f1
YB
979 //TODO ybrosseau: for now, always seek
980 if(/*lttv_traceset_context_ctx_pos_compare(tsc,
981 events_request->start_position) != 0*/1) {
3bafb436 982 /* 1.2.2.1 Seek to that position */
983 g_debug("SEEK POSITION");
984 //lttv_process_traceset_seek_position(tsc, events_request->start_position);
ff5c41f1
YB
985 //pos_time = lttv_traceset_position_get_time(
986 // events_request->start_position);
987 //
988 //lttv_state_traceset_seek_time(ts,
989 // pos_time);
990 lttv_traceset_seek_to_position( events_request->start_position);
3bafb436 991
992 /* Process the traceset with only state hooks */
e865422c 993#ifdef DEBUG
3bafb436 994 seek_count =
9a366873 995
ff5c41f1 996 lttv_process_traceset_middle(ts,
3bafb436 997 ltt_time_infinite,
998 G_MAXUINT,
999 events_request->start_position);
9a366873 1000#endif
ff5c41f1
YB
1001 //g_assert(lttv_traceset_context_ctx_pos_compare(tsc,
1002 // events_request->start_position) == 0);
dd316a11 1003
dd316a11 1004
3bafb436 1005 }
1006 }
1007 }
2d262115 1008
3bafb436 1009 /* 1.3 Add hooks and call before request for all list_in members */
1010 {
1011 GSList *iter = NULL;
dd316a11 1012
3bafb436 1013 for(iter=list_in;iter!=NULL;iter=g_slist_next(iter)) {
1014 EventsRequest *events_request = (EventsRequest*)iter->data;
1015 /* 1.3.1 If !servicing */
2d262115 1016 if(events_request->servicing == FALSE) {
1017 /* - begin request hooks called
1018 * - servicing = TRUE
1019 */
ff5c41f1 1020 lttv_hooks_call(events_request->before_request, (gpointer)ts);
2d262115 1021 events_request->servicing = TRUE;
1022 }
3bafb436 1023 /* 1.3.2 call before chunk
1024 * 1.3.3 events hooks added
2d262115 1025 */
ff5c41f1
YB
1026 //TODO ybrosseau 2012-07-10: || TRUE added since we only support
1027 // traceset wide requests
1028 if(events_request->trace == -1 || TRUE)
1029 lttv_process_traceset_begin(ts,
54d8f654 1030 events_request->before_chunk_traceset,
1031 events_request->before_chunk_trace,
ff5c41f1
YB
1032 events_request->event
1033 );
54d8f654 1034 else {
ff5c41f1 1035 guint nb_trace = lttv_traceset_number(ts);
2eef04b5 1036 g_assert((guint)events_request->trace < nb_trace &&
54d8f654 1037 events_request->trace > -1);
ff5c41f1 1038 LttvTrace *trace = lttv_traceset_get(ts, events_request->trace);
54d8f654 1039
ff5c41f1 1040 lttv_hooks_call(events_request->before_chunk_traceset, ts);
54d8f654 1041
ff5c41f1 1042 lttv_trace_add_hooks(trace,
54d8f654 1043 events_request->before_chunk_trace,
ff5c41f1
YB
1044
1045 events_request->event
1046 );
54d8f654 1047 }
501e4e70 1048 }
3bafb436 1049 }
1050 } else {
1051 /* 2. Else, list_in is not empty, we continue a read */
1052
1053 {
1054 /* 2.0 For each req of list_in */
1055 GSList *iter = list_in;
1056
1057 while(iter != NULL) {
2d262115 1058
3bafb436 1059 EventsRequest *events_request = (EventsRequest *)iter->data;
1060
1061 /* - Call before chunk
1062 * - events hooks added
1063 */
ff5c41f1
YB
1064 //TODO ybrosseau 2012-07-10: || TRUE added since we only support
1065 // traceset wide requests
1066 if(events_request->trace == -1 || TRUE)
1067 lttv_process_traceset_begin(ts,
54d8f654 1068 events_request->before_chunk_traceset,
1069 events_request->before_chunk_trace,
ff5c41f1
YB
1070 events_request->event
1071 );
54d8f654 1072 else {
ff5c41f1 1073 guint nb_trace = lttv_traceset_number(ts);
2eef04b5 1074 g_assert((guint)events_request->trace < nb_trace &&
54d8f654 1075 events_request->trace > -1);
ff5c41f1 1076 LttvTrace *trace = lttv_traceset_get(ts, events_request->trace);
54d8f654 1077
ff5c41f1 1078 lttv_hooks_call(events_request->before_chunk_traceset, ts);
54d8f654 1079
ff5c41f1 1080 lttv_trace_add_hooks(trace,
3bafb436 1081 events_request->before_chunk_trace,
ff5c41f1
YB
1082
1083 events_request->event
1084 );
54d8f654 1085 }
6ea08962 1086
1087 iter = g_slist_next(iter);
1088 }
1089 }
1090
3bafb436 1091 {
ff5c41f1 1092
3bafb436 1093
1094 /* 2.1 For each req of list_out */
1095 GSList *iter = list_out;
553d1e7b 1096
3bafb436 1097 while(iter != NULL) {
6ea08962 1098
3bafb436 1099 gboolean remove = FALSE;
1100 gboolean free_data = FALSE;
1101 EventsRequest *events_request = (EventsRequest *)iter->data;
1102
1103 /* if req.start time == current context time
1104 * or req.start position == current position*/
ff5c41f1 1105 /* if( ltt_time_compare(events_request->start_time,
3bafb436 1106 tfc->timestamp) == 0
1107 ||
1108 (events_request->start_position != NULL
1109 &&
1110 lttv_traceset_context_ctx_pos_compare(tsc,
1111 events_request->start_position) == 0)
1112 ) {
ff5c41f1
YB
1113 */
1114 if(lttv_traceset_position_compare_current(ts, events_request->start_position) == 0) {
1115
3bafb436 1116 /* - Add to list_in, remove from list_out */
1117 list_in = g_slist_append(list_in, events_request);
1118 remove = TRUE;
1119 free_data = FALSE;
1120
1121 /* - If !servicing */
1122 if(events_request->servicing == FALSE) {
1123 /* - begin request hooks called
1124 * - servicing = TRUE
1125 */
ff5c41f1 1126 lttv_hooks_call(events_request->before_request, (gpointer)ts);
3bafb436 1127 events_request->servicing = TRUE;
1128 }
1129 /* call before chunk
1130 * events hooks added
1131 */
ff5c41f1
YB
1132 //TODO ybrosseau 2012-07-10: || TRUE added since we only support
1133 // traceset wide requests
1134 if(events_request->trace == -1 || TRUE)
1135 lttv_process_traceset_begin(ts,
54d8f654 1136 events_request->before_chunk_traceset,
1137 events_request->before_chunk_trace,
ff5c41f1
YB
1138 events_request->event
1139 );
54d8f654 1140 else {
ff5c41f1 1141 guint nb_trace = lttv_traceset_number(ts);
2eef04b5 1142 g_assert((guint)events_request->trace < nb_trace &&
54d8f654 1143 events_request->trace > -1);
ff5c41f1 1144 LttvTrace* trace = lttv_traceset_get(ts,events_request->trace);
54d8f654 1145
ff5c41f1 1146 lttv_hooks_call(events_request->before_chunk_traceset, ts);
54d8f654 1147
ff5c41f1
YB
1148 lttv_trace_add_hooks(trace,
1149 events_request->before_chunk_trace,
1150
1151 events_request->event);
1152
54d8f654 1153 }
1154
1155
3bafb436 1156 }
501e4e70 1157
3bafb436 1158 /* Go to next */
1159 if(remove)
1160 {
1161 GSList *remove_iter = iter;
2d262115 1162
3bafb436 1163 iter = g_slist_next(iter);
1164 if(free_data) events_request_free((EventsRequest*)remove_iter->data);
1165 list_out = g_slist_remove_link(list_out, remove_iter);
1166 } else { // not remove
1167 iter = g_slist_next(iter);
1168 }
1169 }
1170 }
1171 }
8f2872f4 1172
3bafb436 1173 /* 3. Find end criterions */
1174 {
1175 /* 3.1 End time */
1176 GSList *iter;
1177
1178 /* 3.1.1 Find lowest end time in list_in */
1179 g_assert(g_slist_length(list_in)>0);
1180 end_time = ((EventsRequest*)g_slist_nth_data(list_in,0))->end_time;
1181
1182 for(iter=g_slist_nth(list_in,1);iter!=NULL;iter=g_slist_next(iter)) {
1183 EventsRequest *events_request = (EventsRequest*)iter->data;
501e4e70 1184
3bafb436 1185 if(ltt_time_compare(events_request->end_time,
1186 end_time) < 0)
1187 end_time = events_request->end_time;
1188 }
1189
1190 /* 3.1.2 Find lowest start time in list_out */
1191 for(iter=list_out;iter!=NULL;iter=g_slist_next(iter)) {
1192 EventsRequest *events_request = (EventsRequest*)iter->data;
2d262115 1193
3bafb436 1194 if(ltt_time_compare(events_request->start_time,
1195 end_time) < 0)
1196 end_time = events_request->start_time;
1197 }
501e4e70 1198 }
1199
3bafb436 1200 {
1201 /* 3.2 Number of events */
dd316a11 1202
3bafb436 1203 /* 3.2.1 Find lowest number of events in list_in */
1204 GSList *iter;
501e4e70 1205
3bafb436 1206 end_nb_events = ((EventsRequest*)g_slist_nth_data(list_in,0))->num_events;
501e4e70 1207
3bafb436 1208 for(iter=g_slist_nth(list_in,1);iter!=NULL;iter=g_slist_next(iter)) {
1209 EventsRequest *events_request = (EventsRequest*)iter->data;
501e4e70 1210
3bafb436 1211 if(events_request->num_events < end_nb_events)
1212 end_nb_events = events_request->num_events;
1213 }
501e4e70 1214
3bafb436 1215 /* 3.2.2 Use min(CHUNK_NUM_EVENTS, min num events in list_in) as
1216 * num_events */
1217
1218 end_nb_events = MIN(CHUNK_NUM_EVENTS, end_nb_events);
501e4e70 1219 }
501e4e70 1220
3bafb436 1221 {
1222 /* 3.3 End position */
501e4e70 1223
3bafb436 1224 /* 3.3.1 Find lowest end position in list_in */
1225 GSList *iter;
6ea08962 1226
3bafb436 1227 end_position =((EventsRequest*)g_slist_nth_data(list_in,0))->end_position;
6ea08962 1228
3bafb436 1229 for(iter=g_slist_nth(list_in,1);iter!=NULL;iter=g_slist_next(iter)) {
1230 EventsRequest *events_request = (EventsRequest*)iter->data;
dd316a11 1231
3bafb436 1232 if(events_request->end_position != NULL && end_position != NULL &&
ff5c41f1 1233 lttv_traceset_position_time_compare(events_request->end_position,
3bafb436 1234 end_position) <0)
1235 end_position = events_request->end_position;
1236 }
1237 }
1238
1239 {
1240 /* 3.3.2 Find lowest start position in list_out */
1241 GSList *iter;
dd316a11 1242
3bafb436 1243 for(iter=list_out;iter!=NULL;iter=g_slist_next(iter)) {
1244 EventsRequest *events_request = (EventsRequest*)iter->data;
dd316a11 1245
3bafb436 1246 if(events_request->end_position != NULL && end_position != NULL &&
ff5c41f1 1247 lttv_traceset_position_time_compare(events_request->end_position,
3bafb436 1248 end_position) <0)
1249 end_position = events_request->end_position;
dd316a11 1250 }
2d262115 1251 }
3bafb436 1252
2d262115 1253 {
3bafb436 1254 /* 4. Call process traceset middle */
ff5c41f1
YB
1255 g_debug("Calling process traceset middle with %p, %lu sec %lu nsec, %u nb ev, %p end pos", ts, end_time.tv_sec, end_time.tv_nsec, end_nb_events, end_position);
1256 count = lttv_process_traceset_middle(ts, end_time, end_nb_events, end_position);
2d262115 1257
ff5c41f1 1258#ifdef BABEL_CLEANUP
3bafb436 1259 tfc = lttv_traceset_context_get_current_tfc(tsc);
1260 if(tfc != NULL)
1261 g_debug("Context time after middle : %lu, %lu", tfc->timestamp.tv_sec,
1262 tfc->timestamp.tv_nsec);
1263 else
1264 g_debug("End of trace reached after middle.");
ff5c41f1 1265#endif
3bafb436 1266 }
ff5c41f1 1267
3bafb436 1268 {
1269 /* 5. After process traceset middle */
3bafb436 1270
ff5c41f1 1271 LttTime curTime = lttv_traceset_get_current_time(ts);
3bafb436 1272 /* - if current context time > traceset.end time */
ff5c41f1
YB
1273 if(ltt_time_compare(curTime,
1274 lttv_traceset_get_time_span_real(ts).end_time) > 0) {
3bafb436 1275 /* - For each req in list_in */
1276 GSList *iter = list_in;
1277
1278 while(iter != NULL) {
1279
1280 gboolean remove = FALSE;
1281 gboolean free_data = FALSE;
1282 EventsRequest *events_request = (EventsRequest *)iter->data;
1283
1284 /* - Remove events hooks for req
1285 * - Call end chunk for req
1286 */
ff5c41f1
YB
1287 //TODO ybrosseau 2012-07-10: || TRUE added since we only support
1288 // traceset wide requests
1289 if(events_request->trace == -1 || TRUE)
1290 lttv_process_traceset_end(ts,
54d8f654 1291 events_request->after_chunk_traceset,
3bafb436 1292 events_request->after_chunk_trace,
ff5c41f1
YB
1293
1294 events_request->event);
54d8f654 1295
1296 else {
ff5c41f1 1297 guint nb_trace = lttv_traceset_number(ts);
54d8f654 1298 g_assert(events_request->trace < nb_trace &&
1299 events_request->trace > -1);
ff5c41f1 1300 LttvTrace *trace = lttv_traceset_get(ts,events_request->trace);
54d8f654 1301
ff5c41f1 1302 lttv_trace_remove_hooks(trace,
54d8f654 1303 events_request->after_chunk_trace,
ff5c41f1
YB
1304
1305 events_request->event);
1306
1307 lttv_hooks_call(events_request->after_chunk_traceset, ts);
54d8f654 1308
1309
1310 }
1311
3bafb436 1312 /* - Call end request for req */
ff5c41f1 1313 lttv_hooks_call(events_request->after_request, (gpointer)ts);
3bafb436 1314
2d262115 1315 /* - remove req from list_in */
1316 /* Destroy the request */
1317 remove = TRUE;
1318 free_data = TRUE;
3bafb436 1319
1320 /* Go to next */
1321 if(remove)
1322 {
1323 GSList *remove_iter = iter;
1324
1325 iter = g_slist_next(iter);
1326 if(free_data) events_request_free((EventsRequest*)remove_iter->data);
1327 list_in = g_slist_remove_link(list_in, remove_iter);
1328 } else { // not remove
1329 iter = g_slist_next(iter);
1330 }
2d262115 1331 }
3bafb436 1332 }
1333 {
1334 /* 5.1 For each req in list_in */
1335 GSList *iter = list_in;
1336
1337 while(iter != NULL) {
501e4e70 1338
3bafb436 1339 gboolean remove = FALSE;
1340 gboolean free_data = FALSE;
1341 EventsRequest *events_request = (EventsRequest *)iter->data;
1342
1343 /* - Remove events hooks for req
1344 * - Call end chunk for req
1345 */
ff5c41f1
YB
1346 //TODO ybrosseau 2012-07-10: || TRUE added since we only support
1347 // traceset wide requests
1348 if(events_request->trace == -1 || TRUE)
1349 lttv_process_traceset_end(ts,
54d8f654 1350 events_request->after_chunk_traceset,
3bafb436 1351 events_request->after_chunk_trace,
ff5c41f1
YB
1352
1353 events_request->event);
1354
3bafb436 1355
54d8f654 1356 else {
ff5c41f1 1357 guint nb_trace = lttv_traceset_number(ts);
54d8f654 1358 g_assert(events_request->trace < nb_trace &&
1359 events_request->trace > -1);
ff5c41f1 1360 LttvTrace *trace = lttv_traceset_get(ts, events_request->trace);
54d8f654 1361
ff5c41f1 1362 lttv_trace_remove_hooks(trace,
54d8f654 1363 events_request->after_chunk_trace,
54d8f654 1364
ff5c41f1
YB
1365 events_request->event);
1366
1367
1368 lttv_hooks_call(events_request->after_chunk_traceset, ts);
54d8f654 1369 }
1370
3bafb436 1371 /* - req.num -= count */
1372 g_assert(events_request->num_events >= count);
1373 events_request->num_events -= count;
1374
ff5c41f1 1375 //g_assert(tfc != NULL);
3bafb436 1376 /* - if req.num == 0
1377 * or
1378 * current context time >= req.end time
1379 * or
1380 * req.end pos == current pos
1381 * or
1382 * req.stop_flag == TRUE
1383 */
1384 if( events_request->num_events == 0
1385 ||
1386 events_request->stop_flag == TRUE
1387 ||
ff5c41f1 1388 ltt_time_compare(lttv_traceset_get_current_time(ts),
3bafb436 1389 events_request->end_time) >= 0
1390 ||
1391 (events_request->end_position != NULL
1392 &&
ff5c41f1 1393 lttv_traceset_position_compare_current(ts,
3bafb436 1394 events_request->end_position) == 0)
1395
1396 ) {
1397 g_assert(events_request->servicing == TRUE);
1398 /* - Call end request for req
1399 * - remove req from list_in */
ff5c41f1 1400 lttv_hooks_call(events_request->after_request, (gpointer)ts);
3bafb436 1401 /* - remove req from list_in */
1402 /* Destroy the request */
1403 remove = TRUE;
1404 free_data = TRUE;
1405 }
1406
1407 /* Go to next */
1408 if(remove)
1409 {
1410 GSList *remove_iter = iter;
1411
1412 iter = g_slist_next(iter);
1413 if(free_data) events_request_free((EventsRequest*)remove_iter->data);
1414 list_in = g_slist_remove_link(list_in, remove_iter);
1415 } else { // not remove
1416 iter = g_slist_next(iter);
1417 }
2d262115 1418 }
1419 }
1420 }
501e4e70 1421 }
dd316a11 1422 /* End of removed servicing loop : leave control to GTK instead. */
1423 // if(gtk_events_pending()) break;
1424 //}
1425
2d262115 1426 /* B. When interrupted between chunks */
501e4e70 1427
501e4e70 1428 {
1429 GSList *iter = list_in;
1430
2d262115 1431 /* 1. for each request in list_in */
501e4e70 1432 while(iter != NULL) {
1433
1434 gboolean remove = FALSE;
1435 gboolean free_data = FALSE;
2d262115 1436 EventsRequest *events_request = (EventsRequest *)iter->data;
501e4e70 1437
1438 /* 1.1. Use current postition as start position */
a1a2b649 1439 if(events_request->start_position != NULL)
ff5c41f1
YB
1440 lttv_traceset_destroy_position(events_request->start_position);
1441 events_request->start_position = lttv_traceset_create_current_position(ts);
1442
501e4e70 1443
1444 /* 1.2. Remove start time */
0aa6c3a1 1445 events_request->start_time = ltt_time_infinite;
501e4e70 1446
2d262115 1447 /* 1.3. Move from list_in to list_out */
501e4e70 1448 remove = TRUE;
1449 free_data = FALSE;
1450 list_out = g_slist_append(list_out, events_request);
1451
501e4e70 1452 /* Go to next */
1453 if(remove)
8f2872f4 1454 {
501e4e70 1455 GSList *remove_iter = iter;
1456
1457 iter = g_slist_next(iter);
b052368a 1458 if(free_data) events_request_free((EventsRequest*)remove_iter->data);
501e4e70 1459 list_in = g_slist_remove_link(list_in, remove_iter);
1460 } else { // not remove
1461 iter = g_slist_next(iter);
8f2872f4 1462 }
1463 }
a43d67ba 1464
501e4e70 1465
1466 }
b052368a 1467 /* C Unlock Traces */
1468 {
ff5c41f1 1469#ifdef BABEL_CLEANUP
088f6772 1470 lttv_process_traceset_get_sync_data(tsc);
ff5c41f1 1471#endif
088f6772 1472 //lttv_traceset_context_position_save(tsc, sync_position);
b052368a 1473
1474 guint iter_trace;
1475
1476 for(iter_trace=0;
ff5c41f1 1477 iter_trace<lttv_traceset_number(ts);
b052368a 1478 iter_trace++) {
ff5c41f1 1479 LttvTrace *trace_v = lttv_traceset_get(ts, iter_trace);
b052368a 1480
1481 lttvwindowtraces_unlock(trace_v);
1482 }
1483 }
a0577796 1484#if 0
abe346a3 1485 //set the cursor back to normal
a8c0f09d 1486 gdk_window_set_cursor(win, NULL);
a0577796 1487#endif //0
501e4e70 1488
2d262115 1489 g_assert(g_slist_length(list_in) == 0);
6ea08962 1490
2d262115 1491 if( g_slist_length(list_out) == 0 ) {
501e4e70 1492 /* Put tab's request pending flag back to normal */
2d262115 1493 tab->events_request_pending = FALSE;
b052368a 1494 g_debug("remove the idle fct");
501e4e70 1495 return FALSE; /* Remove the idle function */
1496 }
b052368a 1497 g_debug("leave the idle fct");
501e4e70 1498 return TRUE; /* Leave the idle function */
b052368a 1499
1500 /* We do not use simili-round-robin, it may require to read 1 meg buffers
1501 * again and again if many tracesets use the same tracefiles. */
1502 /* Hack for round-robin idle functions */
1503 /* It will put the idle function at the end of the pool */
1504 /*g_idle_add_full((G_PRIORITY_HIGH_IDLE + 21),
1505 (GSourceFunc)execute_events_requests,
1506 tab,
1507 NULL);
1508 return FALSE;
1509 */
451aaf27 1510
ff5c41f1 1511
202f6c8f 1512}
1513
6ea08962 1514#undef list_out
1e3594a3
YB
1515/**
1516 Manage the periodic update of a live trace
1517*/
1518static gboolean
1519live_trace_update_handler(Tab *tab)
1520{
451aaf27 1521#ifdef BABEL_CLEANUP
9a366873 1522 unsigned int updated_count;
1e3594a3
YB
1523 LttvTracesetContext *tsc = LTTV_TRACESET_CONTEXT(tab->traceset_info->traceset_context);
1524 TimeInterval initial_time_span = tsc->time_span;
1525 TimeInterval updated_time_span;
1526
1527 updated_count = lttv_process_traceset_update(tsc);
1528
1529 /* TODO ybrosseau 2011-01-12: Add trace resynchronization */
501e4e70 1530
1e3594a3
YB
1531 /* Get the changed period bounds */
1532 updated_time_span = tsc->time_span;
1533
1534 if(ltt_time_compare(updated_time_span.start_time,
1535 initial_time_span.start_time) != 0) {
1536 /* The initial time should not change on a live update */
1537 g_assert(FALSE);
1538 }
1539
1540 /* Notify viewers (only on updates) */
1541 if(ltt_time_compare(updated_time_span.end_time,
1542 initial_time_span.end_time) != 0) {
1543
1544 notify_time_span_changed(tab);
1545 /* TODO ybrosseau 2011-01-12: Change the timebar to register
1546 to the time_span hook */
1547 timebar_set_minmax_time(TIMEBAR(tab->MTimebar),
1548 &updated_time_span.start_time,
1549 &updated_time_span.end_time );
1550
1551 /* To update the min max */
1552 time_change_manager(tab, tab->time_window);
1553 }
1554
1555 /* Timer will be recalled as long as there is files to update */
1556 return (updated_count > 0);
451aaf27 1557#endif /* BABEL_CLEANUP */
1e3594a3 1558}
abe346a3 1559
4266dc7f 1560static void lttvwindow_add_trace(Tab *tab, LttvTrace *trace_v)
1561{
9a366873 1562#ifdef BABEL_CLEANUP
4266dc7f 1563 LttvTraceset *traceset = tab->traceset_info->traceset;
1564 guint i;
91fd6881 1565 guint num_traces = lttv_traceset_number(traceset);
4266dc7f 1566
a1a2b649 1567 //Verify if trace is already present.
91fd6881 1568 for(i=0; i<num_traces; i++)
a1a2b649 1569 {
1570 LttvTrace * trace = lttv_traceset_get(traceset, i);
1571 if(trace == trace_v)
1572 return;
1573 }
1574
4266dc7f 1575 //Keep a reference to the traces so they are not freed.
1576 for(i=0; i<lttv_traceset_number(traceset); i++)
1577 {
1578 LttvTrace * trace = lttv_traceset_get(traceset, i);
1579 lttv_trace_ref(trace);
1580 }
1581
1582 //remove state update hooks
1583 lttv_state_remove_event_hooks(
1584 (LttvTracesetState*)tab->traceset_info->traceset_context);
1585
1586 lttv_context_fini(LTTV_TRACESET_CONTEXT(
1587 tab->traceset_info->traceset_context));
1588 g_object_unref(tab->traceset_info->traceset_context);
1589
1590 lttv_traceset_add(traceset, trace_v);
a1a2b649 1591 lttv_trace_ref(trace_v); /* local ref */
4266dc7f 1592
1593 /* Create new context */
1594 tab->traceset_info->traceset_context =
1595 g_object_new(LTTV_TRACESET_STATS_TYPE, NULL);
1596 lttv_context_init(
1597 LTTV_TRACESET_CONTEXT(tab->traceset_info->
1598 traceset_context),
1599 traceset);
6ea08962 1600
6ea08962 1601
4266dc7f 1602 //add state update hooks
1603 lttv_state_add_event_hooks(
1604 (LttvTracesetState*)tab->traceset_info->traceset_context);
1605 //Remove local reference to the traces.
1606 for(i=0; i<lttv_traceset_number(traceset); i++)
1607 {
1608 LttvTrace * trace = lttv_traceset_get(traceset, i);
1609 lttv_trace_unref(trace);
1610 }
1611
b052368a 1612 //FIXME
1613 //add_trace_into_traceset_selector(GTK_MULTIVPANED(tab->multivpaned), lttv_trace(trace_v));
1e3594a3
YB
1614
1615
1616 if (lttv_trace(trace_v)->is_live) {
1617 /* Add timer for live update */
1618 /* TODO ybrosseau 2011-01-12: Parametrize the hardcoded 1 seconds */
1619 g_timeout_add_seconds (1,
1620 (GSourceFunc) live_trace_update_handler,
1621 tab);
1622 }
451aaf27 1623#endif /* BABEL_CLEANUP */
4266dc7f 1624}
1625
abe346a3 1626/* add_trace adds a trace into the current traceset. It first displays a
1627 * directory selection dialogue to let user choose a trace, then recreates
1628 * tracset_context, and redraws all the viewer of the current tab
1629 */
1630
561eba2a 1631void add_trace(GtkWidget * widget, gpointer user_data)
1632{
861fbe5f 1633
deb3d2f8 1634 LttvTraceset * traceset = NULL;
861fbe5f 1635 const char * path;
a1a2b649 1636 char abs_path[PATH_MAX];
2176f952 1637 gint id;
bca3b81f 1638 MainWindow * mw_data = get_window_data_struct(widget);
6ced96ef 1639 GtkWidget * notebook = lookup_widget(widget, "MNotebook");
1640
1641 GtkWidget *page = gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook),
1642 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook)));
e433e6d6 1643 LttvPluginTab *ptab;
6ced96ef 1644 Tab *tab;
1645
1646 if(!page) {
e433e6d6 1647 ptab = create_new_tab(widget, NULL);
1648 tab = ptab->tab;
6ced96ef 1649 } else {
e433e6d6 1650 ptab = (LttvPluginTab *)g_object_get_data(G_OBJECT(page), "Tab_Plugin");
1651 tab = ptab->tab;
6ced96ef 1652 }
1167062f 1653//TODO fdeslauriers 2012-07-06: Remove this popup when we support multiple traces
deb3d2f8 1654 traceset = lttvwindow_get_traceset(tab);
95544594 1655 if(traceset != NULL && lttv_traceset_number(traceset) > 0){
deb3d2f8
FD
1656 GtkWidget *dialogue =
1657 gtk_message_dialog_new(
1658 GTK_WINDOW(gtk_widget_get_toplevel(widget)),
1659 GTK_DIALOG_MODAL|GTK_DIALOG_DESTROY_WITH_PARENT,
1660 GTK_MESSAGE_ERROR,
1661 GTK_BUTTONS_OK,
1662 "Loading multiple traces is not supported at the moment.");
1663 gtk_dialog_run(GTK_DIALOG(dialogue));
1664 gtk_widget_destroy(dialogue);
1665 return;
1666 }
1667
861fbe5f
FD
1668 /* Create a new traceset*/
1669 traceset = lttv_traceset_new();
ba013432 1670 /* File open dialog management */
95544594
FD
1671#ifdef BABEL_CLEANUP
1672 GtkWidget *extra_live_button;
1673#endif //babel_cleanup
ba013432
MD
1674 GtkFileChooser * file_chooser =
1675 GTK_FILE_CHOOSER(
1676 gtk_file_chooser_dialog_new ("Select a trace",
1677 GTK_WINDOW(mw_data->mwindow),
1678 GTK_FILE_CHOOSER_ACTION_SELECT_FOLDER,
1679 GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL,
1680 GTK_STOCK_OPEN, GTK_RESPONSE_ACCEPT,
861fbe5f 1681 NULL));
95544594 1682#ifdef BABEL_CLEANUP
1e3594a3
YB
1683 /* Button to indicate the opening of a live trace */
1684 extra_live_button = gtk_check_button_new_with_mnemonic ("Trace is live (currently being writen)");
1685 gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (extra_live_button), FALSE);
1686 gtk_file_chooser_set_extra_widget (GTK_FILE_CHOOSER (file_chooser), extra_live_button);
95544594 1687#endif //babel_cleanup
ba013432 1688 gtk_file_chooser_set_show_hidden (file_chooser, TRUE);
3658a338 1689 if(remember_trace_dir[0] != '\0')
ba013432
MD
1690 gtk_file_chooser_set_filename(file_chooser, remember_trace_dir);
1691
861fbe5f 1692 gboolean closeFileChooserDialog = TRUE;
1e3594a3 1693
861fbe5f
FD
1694 do
1695 {
1696 id = gtk_dialog_run(GTK_DIALOG(file_chooser));
1697 switch(id){
1698 case GTK_RESPONSE_ACCEPT:
1699 case GTK_RESPONSE_OK:
1700 path = gtk_file_chooser_get_filename (file_chooser);
1701
1702 strncpy(remember_trace_dir, path, PATH_MAX);
1703 strncat(remember_trace_dir, "/", PATH_MAX);
1704 if(!path || strlen(path) == 0){
1705 break;
1e3594a3 1706 }
861fbe5f
FD
1707 get_absolute_pathname(path, abs_path);
1708
1709 if(lttv_traceset_add_path(traceset,abs_path) != 0 ){ /*failure*/
49bf71b5 1710
861fbe5f
FD
1711 g_warning("cannot open trace %s", abs_path);
1712 strncpy(remember_trace_dir, "\0", PATH_MAX);
1713 GtkWidget *dialogue =
1714 gtk_message_dialog_new(
1715 GTK_WINDOW(gtk_widget_get_toplevel(widget)),
1716 GTK_DIALOG_MODAL|GTK_DIALOG_DESTROY_WITH_PARENT,
1717 GTK_MESSAGE_ERROR,
1718 GTK_BUTTONS_OK,
1719 "Cannot open trace : maybe you should enter in the directory "
1720 "to select it ?");
1721 gtk_dialog_run(GTK_DIALOG(dialogue));
1722 gtk_widget_destroy(dialogue);
1723 closeFileChooserDialog = FALSE;
1724 }
1725 else{
1726 closeFileChooserDialog = TRUE;
1727 SetTraceset(tab, traceset);
1728 }
1729 break;
1730 //update current tab
1731 //update_traceset(mw_data);
21e8c385 1732
861fbe5f
FD
1733 // in expose now call_pending_read_hooks(mw_data);
1734
1735 //lttvwindow_report_current_time(mw_data,&(tab->current_time));
a43d67ba 1736
861fbe5f
FD
1737 case GTK_RESPONSE_REJECT:
1738 case GTK_RESPONSE_CANCEL:
1739 default:
1740 closeFileChooserDialog = TRUE;
1741 break;
1742 }
1743 }while(!closeFileChooserDialog);
451aaf27 1744
861fbe5f 1745 gtk_widget_destroy((GtkWidget*)file_chooser);
ba013432 1746
49bf71b5 1747}
1748
abe346a3 1749/* remove_trace removes a trace from the current traceset if all viewers in
1750 * the current tab are not interested in the trace. It first displays a
1751 * dialogue, which shows all traces in the current traceset, to let user choose
1752 * a trace, then it checks if all viewers unselect the trace, if it is true,
1753 * it will remove the trace, recreate the traceset_contex,
1754 * and redraws all the viewer of the current tab. If there is on trace in the
1755 * current traceset, it will delete all viewers of the current tab
3a5f75c1 1756 *
1757 * It destroys the filter tree. FIXME... we should request for an update
1758 * instead.
abe346a3 1759 */
1760
b052368a 1761void remove_trace(GtkWidget *widget, gpointer user_data)
1762{
9a366873 1763#ifdef BABEL_CLEANUP
b052368a 1764 LttTrace *trace;
1765 LttvTrace * trace_v;
1766 LttvTraceset * traceset;
1767 gint i, j, nb_trace, index=-1;
1768 char ** name, *remove_trace_name;
1769 MainWindow * mw_data = get_window_data_struct(widget);
1770 GtkWidget * notebook = lookup_widget(widget, "MNotebook");
1771
1772 GtkWidget *page = gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook),
1773 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook)));
1774 Tab *tab;
1775
1776 if(!page) {
1777 return;
1778 } else {
e433e6d6 1779 LttvPluginTab *ptab;
1780 ptab = (LttvPluginTab *)g_object_get_data(G_OBJECT(page), "Tab_Plugin");
1781 tab = ptab->tab;
b052368a 1782 }
1783
1784 nb_trace =lttv_traceset_number(tab->traceset_info->traceset);
1785 name = g_new(char*,nb_trace);
1786 for(i = 0; i < nb_trace; i++){
1787 trace_v = lttv_traceset_get(tab->traceset_info->traceset, i);
1788 trace = lttv_trace(trace_v);
8d8c5ea7 1789 name[i] = (char *) g_quark_to_string(ltt_trace_name(trace));
b052368a 1790 }
1791
93ac601b 1792 remove_trace_name = get_remove_trace(mw_data, name, nb_trace);
b052368a 1793
1794
1795 if(remove_trace_name){
1796
1797 /* yuk, cut n paste from old code.. should be better (MD)*/
1798 for(i = 0; i<nb_trace; i++) {
1799 if(strcmp(remove_trace_name,name[i]) == 0){
1800 index = i;
1801 }
1802 }
1803
1804 traceset = tab->traceset_info->traceset;
1805 //Keep a reference to the traces so they are not freed.
1806 for(j=0; j<lttv_traceset_number(traceset); j++)
1807 {
1808 LttvTrace * trace = lttv_traceset_get(traceset, j);
1809 lttv_trace_ref(trace);
1810 }
1811
1812 //remove state update hooks
1813 lttv_state_remove_event_hooks(
1814 (LttvTracesetState*)tab->traceset_info->traceset_context);
1815 lttv_context_fini(LTTV_TRACESET_CONTEXT(tab->traceset_info->traceset_context));
1816 g_object_unref(tab->traceset_info->traceset_context);
1817
1818 trace_v = lttv_traceset_get(traceset, index);
1819
b052368a 1820 lttv_traceset_remove(traceset, index);
1821 lttv_trace_unref(trace_v); // Remove local reference
1822
d27948a3 1823 if(lttv_trace_get_ref_number(trace_v) <= 1) {
1ba187d3 1824 /* ref 1 : lttvwindowtraces only*/
1825 ltt_trace_close(lttv_trace(trace_v));
1826 /* lttvwindowtraces_remove_trace takes care of destroying
1827 * the traceset linked with the trace_v and also of destroying
1828 * the trace_v at the same time.
1829 */
d27948a3 1830 lttvwindowtraces_remove_trace(trace_v);
1831 }
b052368a 1832
1833 tab->traceset_info->traceset_context =
1834 g_object_new(LTTV_TRACESET_STATS_TYPE, NULL);
1835 lttv_context_init(
1836 LTTV_TRACESET_CONTEXT(tab->
1837 traceset_info->traceset_context),traceset);
1838 //add state update hooks
1839 lttv_state_add_event_hooks(
1840 (LttvTracesetState*)tab->traceset_info->traceset_context);
1841
1842 //Remove local reference to the traces.
1843 for(j=0; j<lttv_traceset_number(traceset); j++)
1844 {
1845 LttvTrace * trace = lttv_traceset_get(traceset, j);
1846 lttv_trace_unref(trace);
1847 }
1848
1849 SetTraceset(tab, (gpointer)traceset);
1850 }
1851 g_free(name);
451aaf27 1852#endif /* BABEL_CLEANUP */
b052368a 1853}
1854
1855#if 0
561eba2a 1856void remove_trace(GtkWidget * widget, gpointer user_data)
1857{
2176f952 1858 LttTrace *trace;
1859 LttvTrace * trace_v;
1860 LttvTraceset * traceset;
a43d67ba 1861 gint i, j, nb_trace;
2176f952 1862 char ** name, *remove_trace_name;
bca3b81f 1863 MainWindow * mw_data = get_window_data_struct(widget);
49bf71b5 1864 LttvTracesetSelector * s;
1865 LttvTraceSelector * t;
1866 GtkWidget * w;
1867 gboolean selected;
6ced96ef 1868 GtkWidget * notebook = lookup_widget(widget, "MNotebook");
1869
1870 GtkWidget *page = gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook),
1871 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook)));
1872 Tab *tab;
1873
1874 if(!page) {
1875 return;
1876 } else {
1877 tab = (Tab *)g_object_get_data(G_OBJECT(page), "Tab_Info");
1878 }
1879
4266dc7f 1880 nb_trace =lttv_traceset_number(tab->traceset_info->traceset);
2176f952 1881 name = g_new(char*,nb_trace);
1882 for(i = 0; i < nb_trace; i++){
4266dc7f 1883 trace_v = lttv_traceset_get(tab->traceset_info->traceset, i);
2176f952 1884 trace = lttv_trace(trace_v);
a5dcde2f 1885 name[i] = ltt_trace_name(trace);
2176f952 1886 }
1887
1888 remove_trace_name = get_remove_trace(name, nb_trace);
1889
1890 if(remove_trace_name){
1891 for(i=0; i<nb_trace; i++){
1892 if(strcmp(remove_trace_name,name[i]) == 0){
6ced96ef 1893 //unselect the trace from the current viewer
b052368a 1894 //FIXME
1895 w = gtk_multivpaned_get_widget(GTK_MULTIVPANED(tab->multivpaned));
6ced96ef 1896 if(w){
1897 s = g_object_get_data(G_OBJECT(w), "Traceset_Selector");
1898 if(s){
1899 t = lttv_traceset_selector_trace_get(s,i);
1900 lttv_trace_selector_set_selected(t, FALSE);
1901 }
1902
1903 //check if other viewers select the trace
b052368a 1904 w = gtk_multivpaned_get_first_widget(GTK_MULTIVPANED(tab->multivpaned));
6ced96ef 1905 while(w){
1906 s = g_object_get_data(G_OBJECT(w), "Traceset_Selector");
1907 if(s){
1908 t = lttv_traceset_selector_trace_get(s,i);
1909 selected = lttv_trace_selector_get_selected(t);
1910 if(selected)break;
1911 }
b052368a 1912 w = gtk_multivpaned_get_next_widget(GTK_MULTIVPANED(tab->multivpaned));
6ced96ef 1913 }
1914 }else selected = FALSE;
49bf71b5 1915
6ced96ef 1916 //if no viewer selects the trace, remove it
1917 if(!selected){
b052368a 1918 remove_trace_from_traceset_selector(GTK_MULTIVPANED(tab->multivpaned), i);
49bf71b5 1919
6ced96ef 1920 traceset = tab->traceset_info->traceset;
1921 //Keep a reference to the traces so they are not freed.
1922 for(j=0; j<lttv_traceset_number(traceset); j++)
1923 {
1924 LttvTrace * trace = lttv_traceset_get(traceset, j);
1925 lttv_trace_ref(trace);
1926 }
a43d67ba 1927
6ced96ef 1928 //remove state update hooks
1929 lttv_state_remove_event_hooks(
1930 (LttvTracesetState*)tab->traceset_info->traceset_context);
1931 lttv_context_fini(LTTV_TRACESET_CONTEXT(tab->traceset_info->traceset_context));
1932 g_object_unref(tab->traceset_info->traceset_context);
a43d67ba 1933
a43d67ba 1934
6ced96ef 1935 trace_v = lttv_traceset_get(traceset, i);
a43d67ba 1936
a1a2b649 1937 if(lttv_trace_get_ref_number(trace_v) <= 2) {
1938 /* ref 2 : traceset, local */
1939 lttvwindowtraces_remove_trace(trace_v);
6ced96ef 1940 ltt_trace_close(lttv_trace(trace_v));
a1a2b649 1941 }
6ced96ef 1942
1943 lttv_traceset_remove(traceset, i);
1944 lttv_trace_unref(trace_v); // Remove local reference
c2619a30 1945
6ced96ef 1946 if(!lttv_trace_get_ref_number(trace_v))
1947 lttv_trace_destroy(trace_v);
1948
1949 tab->traceset_info->traceset_context =
1950 g_object_new(LTTV_TRACESET_STATS_TYPE, NULL);
1951 lttv_context_init(
1952 LTTV_TRACESET_CONTEXT(tab->
1953 traceset_info->traceset_context),traceset);
1954 //add state update hooks
1955 lttv_state_add_event_hooks(
1956 (LttvTracesetState*)tab->traceset_info->traceset_context);
1957
1958 //Remove local reference to the traces.
1959 for(j=0; j<lttv_traceset_number(traceset); j++)
1960 {
1961 LttvTrace * trace = lttv_traceset_get(traceset, j);
1962 lttv_trace_unref(trace);
1963 }
a43d67ba 1964
a43d67ba 1965
6ced96ef 1966 //update current tab
1967 //update_traceset(mw_data);
313bd6fc 1968 //if(nb_trace > 1){
6ced96ef 1969
313bd6fc 1970 SetTraceset(tab, (gpointer)traceset);
6ced96ef 1971 // in expose now call_pending_read_hooks(mw_data);
1972
1973 //lttvwindow_report_current_time(mw_data,&(tab->current_time));
313bd6fc 1974 //}else{
1975 // if(tab){
1976 // while(tab->multi_vpaned->num_children){
1977 // gtk_multi_vpaned_widget_delete(tab->multi_vpaned);
1978 // }
1979 // }
1980 //}
6ced96ef 1981 }
1982 break;
2176f952 1983 }
1984 }
1985 }
1986
1987 g_free(name);
561eba2a 1988}
b052368a 1989#endif //0
abe346a3 1990
9878c8a4 1991/* Redraw all the viewers in the current tab */
1992void redraw(GtkWidget *widget, gpointer user_data)
1993{
1994 GtkWidget * notebook = lookup_widget(widget, "MNotebook");
1995 GtkWidget *page = gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook),
1996 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook)));
1997 Tab *tab;
8f318283
BP
1998 gboolean retval;
1999
9878c8a4 2000 if(!page) {
2001 return;
2002 } else {
e433e6d6 2003 LttvPluginTab *ptab;
2004 ptab = (LttvPluginTab *)g_object_get_data(G_OBJECT(page), "Tab_Plugin");
2005 tab = ptab->tab;
9878c8a4 2006 }
2007
2008 LttvHooks * tmp;
2009 LttvAttributeValue value;
2010
8f318283
BP
2011 retval= lttv_iattribute_find_by_path(tab->attributes, "hooks/redraw", LTTV_POINTER, &value);
2012 g_assert(retval);
9878c8a4 2013
2014 tmp = (LttvHooks*)*(value.v_pointer);
c07e9b26 2015 if(tmp != NULL)
2016 lttv_hooks_call(tmp,NULL);
9878c8a4 2017}
2018
2019
2020void continue_processing(GtkWidget *widget, gpointer user_data)
2021{
2022 GtkWidget * notebook = lookup_widget(widget, "MNotebook");
2023 GtkWidget *page = gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook),
2024 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook)));
2025 Tab *tab;
8f318283
BP
2026 gboolean retval;
2027
9878c8a4 2028 if(!page) {
2029 return;
2030 } else {
e433e6d6 2031 LttvPluginTab *ptab;
2032 ptab = (LttvPluginTab *)g_object_get_data(G_OBJECT(page), "Tab_Plugin");
2033 tab = ptab->tab;
9878c8a4 2034 }
2035
2036 LttvHooks * tmp;
2037 LttvAttributeValue value;
2038
8f318283
BP
2039 retval= lttv_iattribute_find_by_path(tab->attributes, "hooks/continue",
2040 LTTV_POINTER, &value);
2041 g_assert(retval);
9878c8a4 2042
2043 tmp = (LttvHooks*)*(value.v_pointer);
c07e9b26 2044 if(tmp != NULL)
2045 lttv_hooks_call(tmp,NULL);
9878c8a4 2046}
2047
2048/* Stop the processing for the calling main window's current tab.
2049 * It removes every processing requests that are in its list. It does not call
2050 * the end request hooks, because the request is not finished.
2051 */
2052
2053void stop_processing(GtkWidget *widget, gpointer user_data)
2054{
2055 GtkWidget * notebook = lookup_widget(widget, "MNotebook");
2056 GtkWidget *page = gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook),
2057 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook)));
2058 Tab *tab;
2059 if(!page) {
2060 return;
2061 } else {
e433e6d6 2062 LttvPluginTab *ptab;
2063 ptab = (LttvPluginTab *)g_object_get_data(G_OBJECT(page), "Tab_Plugin");
2064 tab = ptab->tab;
9878c8a4 2065 }
a0577796 2066 GSList *iter = tab->events_requests;
9878c8a4 2067
2068 while(iter != NULL) {
2069 GSList *remove_iter = iter;
2070 iter = g_slist_next(iter);
2071
2072 g_free(remove_iter->data);
a0577796 2073 tab->events_requests =
2074 g_slist_remove_link(tab->events_requests, remove_iter);
9878c8a4 2075 }
a0577796 2076 tab->events_request_pending = FALSE;
5698740e 2077 tab->stop_foreground = TRUE;
a0577796 2078 g_idle_remove_by_data(tab);
2079 g_assert(g_slist_length(tab->events_requests) == 0);
9878c8a4 2080}
2081
2082
abe346a3 2083/* save will save the traceset to a file
a43d67ba 2084 * Not implemented yet FIXME
abe346a3 2085 */
2086
561eba2a 2087void save(GtkWidget * widget, gpointer user_data)
2088{
56e5a0f7 2089 g_info("Save\n");
561eba2a 2090}
2091
2092void save_as(GtkWidget * widget, gpointer user_data)
2093{
56e5a0f7 2094 g_info("Save as\n");
561eba2a 2095}
2096
abe346a3 2097
2098/* zoom will change the time_window of all the viewers of the
2099 * current tab, and redisplay them. The main functionality is to
2100 * determine the new time_window of the current tab
2101 */
2102
1f1ae829 2103void zoom(GtkWidget * widget, double size)
2104{
9a366873 2105#ifdef BABEL_CLEANUP
b052368a 2106 TimeInterval time_span;
a43d67ba 2107 TimeWindow new_time_window;
2eef04b5 2108 LttTime current_time, time_delta;
4266dc7f 2109 LttvTracesetContext *tsc;
6ced96ef 2110 GtkWidget * notebook = lookup_widget(widget, "MNotebook");
2111
2112 GtkWidget *page = gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook),
2113 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook)));
2114 Tab *tab;
2115
2116 if(!page) {
2117 return;
2118 } else {
e433e6d6 2119 LttvPluginTab *ptab;
2120 ptab = (LttvPluginTab *)g_object_get_data(G_OBJECT(page), "Tab_Plugin");
2121 tab = ptab->tab;
6ced96ef 2122 }
1f1ae829 2123
fda16332 2124 if(size == 1) return;
2125
4266dc7f 2126 tsc = LTTV_TRACESET_CONTEXT(tab->traceset_info->traceset_context);
b052368a 2127 time_span = tsc->time_span;
501e4e70 2128 new_time_window = tab->time_window;
2129 current_time = tab->current_time;
1f1ae829 2130
b052368a 2131 time_delta = ltt_time_sub(time_span.end_time,time_span.start_time);
1f1ae829 2132 if(size == 0){
b052368a 2133 new_time_window.start_time = time_span.start_time;
a43d67ba 2134 new_time_window.time_width = time_delta;
a18124ff 2135 new_time_window.time_width_double = ltt_time_to_double(time_delta);
6f26fc38 2136 new_time_window.end_time = ltt_time_add(new_time_window.start_time,
2137 new_time_window.time_width) ;
1f1ae829 2138 }else{
a43d67ba 2139 new_time_window.time_width = ltt_time_div(new_time_window.time_width, size);
a18124ff 2140 new_time_window.time_width_double =
2141 ltt_time_to_double(new_time_window.time_width);
a43d67ba 2142 if(ltt_time_compare(new_time_window.time_width,time_delta) > 0)
2143 { /* Case where zoom out is bigger than trace length */
b052368a 2144 new_time_window.start_time = time_span.start_time;
a43d67ba 2145 new_time_window.time_width = time_delta;
a18124ff 2146 new_time_window.time_width_double = ltt_time_to_double(time_delta);
6f26fc38 2147 new_time_window.end_time = ltt_time_add(new_time_window.start_time,
2148 new_time_window.time_width) ;
a8c0f09d 2149 }
a43d67ba 2150 else
2151 {
2152 /* Center the image on the current time */
a43d67ba 2153 new_time_window.start_time =
a18124ff 2154 ltt_time_sub(current_time,
2155 ltt_time_from_double(new_time_window.time_width_double/2.0));
6f26fc38 2156 new_time_window.end_time = ltt_time_add(new_time_window.start_time,
2157 new_time_window.time_width) ;
a43d67ba 2158 /* If on borders, don't fall off */
9e494e53 2159 if(ltt_time_compare(new_time_window.start_time, time_span.start_time) <0
2160 || ltt_time_compare(new_time_window.start_time, time_span.end_time) >0)
a43d67ba 2161 {
b052368a 2162 new_time_window.start_time = time_span.start_time;
6f26fc38 2163 new_time_window.end_time = ltt_time_add(new_time_window.start_time,
2164 new_time_window.time_width) ;
a43d67ba 2165 }
2166 else
2167 {
6f26fc38 2168 if(ltt_time_compare(new_time_window.end_time,
9e494e53 2169 time_span.end_time) > 0
2170 || ltt_time_compare(new_time_window.end_time,
2171 time_span.start_time) < 0)
a43d67ba 2172 {
2173 new_time_window.start_time =
b052368a 2174 ltt_time_sub(time_span.end_time, new_time_window.time_width);
6f26fc38 2175
2176 new_time_window.end_time = ltt_time_add(new_time_window.start_time,
2177 new_time_window.time_width) ;
a43d67ba 2178 }
2179 }
2180
1f1ae829 2181 }
1f1ae829 2182 }
a43d67ba 2183
f02b5e22 2184 if(ltt_time_compare(new_time_window.time_width, ltt_time_zero) == 0) {
2185 g_warning("Zoom more than 1 ns impossible");
b052368a 2186 } else {
e800cf84 2187 time_change_manager(tab, new_time_window);
b052368a 2188 }
451aaf27
FD
2189
2190#endif /* BABEL_CLEANUP */
1f1ae829 2191}
2192
561eba2a 2193void zoom_in(GtkWidget * widget, gpointer user_data)
2194{
1f1ae829 2195 zoom(widget, 2);
561eba2a 2196}
2197
2198void zoom_out(GtkWidget * widget, gpointer user_data)
2199{
1f1ae829 2200 zoom(widget, 0.5);
561eba2a 2201}
2202
2203void zoom_extended(GtkWidget * widget, gpointer user_data)
2204{
1f1ae829 2205 zoom(widget, 0);
561eba2a 2206}
2207
2208void go_to_time(GtkWidget * widget, gpointer user_data)
2209{
56e5a0f7 2210 g_info("Go to time\n");
561eba2a 2211}
2212
2213void show_time_frame(GtkWidget * widget, gpointer user_data)
2214{
56e5a0f7 2215 g_info("Show time frame\n");
561eba2a 2216}
2217
2218
2219/* callback function */
2220
2221void
2222on_empty_traceset_activate (GtkMenuItem *menuitem,
2223 gpointer user_data)
2224{
68b48a45 2225 create_new_window((GtkWidget*)menuitem, user_data, FALSE);
561eba2a 2226}
2227
2228
2229void
2230on_clone_traceset_activate (GtkMenuItem *menuitem,
2231 gpointer user_data)
2232{
68b48a45 2233 create_new_window((GtkWidget*)menuitem, user_data, TRUE);
561eba2a 2234}
2235
abe346a3 2236
2237/* create_new_tab calls create_tab to construct a new tab in the main window
2238 */
2239
e433e6d6 2240LttvPluginTab *create_new_tab(GtkWidget* widget, gpointer user_data)
2241{
a1a2b649 2242 gchar label[PATH_MAX];
2901f314 2243 MainWindow * mw_data = get_window_data_struct(widget);
4266dc7f 2244
2901f314 2245 GtkNotebook * notebook = (GtkNotebook *)lookup_widget(widget, "MNotebook");
561eba2a 2246 if(notebook == NULL){
56e5a0f7 2247 g_info("Notebook does not exist\n");
6ced96ef 2248 return NULL;
2249 }
2250 GtkWidget *page = gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook),
2251 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook)));
2252 Tab *copy_tab;
2253
2254 if(!page) {
2255 copy_tab = NULL;
2256 } else {
e433e6d6 2257 LttvPluginTab *ptab;
2258 ptab = (LttvPluginTab *)g_object_get_data(G_OBJECT(page), "Tab_Plugin");
2259 copy_tab = ptab->tab;
561eba2a 2260 }
4266dc7f 2261
6b1d3120 2262 strcpy(label,"Page");
e433e6d6 2263 if(get_label(mw_data, label,"Get the name of the tab","Please input tab's name")) {
2264 LttvPluginTab *ptab;
2265
2266 ptab = g_object_new(LTTV_TYPE_PLUGIN_TAB, NULL);
2267 init_tab (ptab->tab, mw_data, copy_tab, notebook, label);
2268 ptab->parent.top_widget = ptab->tab->top_widget;
2269 g_object_set_data_full(
2270 G_OBJECT(ptab->tab->vbox),
2271 "Tab_Plugin",
2272 ptab,
2273 (GDestroyNotify)tab_destructor);
2274 return ptab;
2275 }
2276 else return NULL;
561eba2a 2277}
2278
2901f314 2279void
2280on_tab_activate (GtkMenuItem *menuitem,
2281 gpointer user_data)
2282{
2283 create_new_tab((GtkWidget*)menuitem, user_data);
2284}
2285
561eba2a 2286
2287void
2288on_open_activate (GtkMenuItem *menuitem,
2289 gpointer user_data)
2290{
e865422c 2291#ifdef UNFINISHED_FEATURE
561eba2a 2292 open_traceset((GtkWidget*)menuitem, user_data);
e865422c 2293#endif
561eba2a 2294}
2295
2296
2297void
2298on_close_activate (GtkMenuItem *menuitem,
2299 gpointer user_data)
2300{
bca3b81f 2301 MainWindow * mw_data = get_window_data_struct((GtkWidget*)menuitem);
68b48a45 2302 main_window_destructor(mw_data);
561eba2a 2303}
2304
2305
4266dc7f 2306/* remove the current tab from the main window
abe346a3 2307 */
2308
561eba2a 2309void
27a559b9 2310on_close_tab_activate (GtkWidget *widget,
561eba2a 2311 gpointer user_data)
2312{
4266dc7f 2313 gint page_num;
2061e03d 2314 GtkWidget * notebook;
27a559b9 2315 notebook = lookup_widget(widget, "MNotebook");
2061e03d 2316 if(notebook == NULL){
56e5a0f7 2317 g_info("Notebook does not exist\n");
2061e03d 2318 return;
2319 }
4266dc7f 2320
2321 page_num = gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook));
2061e03d 2322
4266dc7f 2323 gtk_notebook_remove_page(GTK_NOTEBOOK(notebook), page_num);
2061e03d 2324
561eba2a 2325}
2326
27a559b9 2327void
2328on_close_tab_X_clicked (GtkWidget *widget,
2329 gpointer user_data)
2330{
2331 gint page_num;
2332 GtkWidget *notebook = lookup_widget(widget, "MNotebook");
2333 if(notebook == NULL){
56e5a0f7 2334 g_info("Notebook does not exist\n");
27a559b9 2335 return;
2336 }
2337
2338 if((page_num = gtk_notebook_page_num(GTK_NOTEBOOK(notebook), widget)) != -1)
2339 gtk_notebook_remove_page(GTK_NOTEBOOK(notebook), page_num);
2340
2341}
2342
561eba2a 2343
2344void
2345on_add_trace_activate (GtkMenuItem *menuitem,
2346 gpointer user_data)
2347{
2348 add_trace((GtkWidget*)menuitem, user_data);
2349}
2350
2351
2352void
2353on_remove_trace_activate (GtkMenuItem *menuitem,
2354 gpointer user_data)
2355{
2356 remove_trace((GtkWidget*)menuitem, user_data);
2357}
2358
2359
2360void
2361on_save_activate (GtkMenuItem *menuitem,
2362 gpointer user_data)
2363{
2364 save((GtkWidget*)menuitem, user_data);
2365}
2366
2367
2368void
2369on_save_as_activate (GtkMenuItem *menuitem,
2370 gpointer user_data)
2371{
2372 save_as((GtkWidget*)menuitem, user_data);
2373}
2374
2375
2376void
2377on_quit_activate (GtkMenuItem *menuitem,
2378 gpointer user_data)
2379{
6f9c921e 2380 while (g_slist_length(g_main_window_list) != 0) {
2381 on_MWindow_destroy(((MainWindow *)g_main_window_list->data)->mwindow,
2382 user_data);
2383 }
561eba2a 2384}
2385
2386
2387void
2388on_cut_activate (GtkMenuItem *menuitem,
2389 gpointer user_data)
2390{
56e5a0f7 2391 g_info("Cut\n");
561eba2a 2392}
2393
2394
2395void
2396on_copy_activate (GtkMenuItem *menuitem,
2397 gpointer user_data)
2398{
56e5a0f7 2399 g_info("Copye\n");
561eba2a 2400}
2401
2402
2403void
2404on_paste_activate (GtkMenuItem *menuitem,
2405 gpointer user_data)
2406{
56e5a0f7 2407 g_info("Paste\n");
561eba2a 2408}
2409
2410
2411void
2412on_delete_activate (GtkMenuItem *menuitem,
2413 gpointer user_data)
2414{
56e5a0f7 2415 g_info("Delete\n");
561eba2a 2416}
2417
2418
2419void
2420on_zoom_in_activate (GtkMenuItem *menuitem,
2421 gpointer user_data)
2422{
2423 zoom_in((GtkWidget*)menuitem, user_data);
2424}
2425
2426
2427void
2428on_zoom_out_activate (GtkMenuItem *menuitem,
2429 gpointer user_data)
2430{
2431 zoom_out((GtkWidget*)menuitem, user_data);
2432}
2433
2434
2435void
2436on_zoom_extended_activate (GtkMenuItem *menuitem,
2437 gpointer user_data)
2438{
2439 zoom_extended((GtkWidget*)menuitem, user_data);
2440}
2441
2442
2443void
2444on_go_to_time_activate (GtkMenuItem *menuitem,
2445 gpointer user_data)
2446{
2447 go_to_time((GtkWidget*)menuitem, user_data);
2448}
2449
2450
2451void
2452on_show_time_frame_activate (GtkMenuItem *menuitem,
2453 gpointer user_data)
2454{
2455 show_time_frame((GtkWidget*)menuitem, user_data);
2456}
2457
2458
2459void
2460on_move_viewer_up_activate (GtkMenuItem *menuitem,
2461 gpointer user_data)
2462{
2463 move_up_viewer((GtkWidget*)menuitem, user_data);
2464}
2465
2466
2467void
2468on_move_viewer_down_activate (GtkMenuItem *menuitem,
2469 gpointer user_data)
2470{
2471 move_down_viewer((GtkWidget*)menuitem, user_data);
2472}
2473
2474
2475void
2476on_remove_viewer_activate (GtkMenuItem *menuitem,
2477 gpointer user_data)
2478{
2479 delete_viewer((GtkWidget*)menuitem, user_data);
2480}
2481
49bf71b5 2482void
2483on_trace_facility_activate (GtkMenuItem *menuitem,
2484 gpointer user_data)
2485{
43ed82b5 2486 g_info("Trace facility selector: %s\n", "");
49bf71b5 2487}
561eba2a 2488
abe346a3 2489
b052368a 2490/* Dispaly a file selection dialogue to let user select a library, then call
2491 * lttv_library_load().
2492 */
2493
2494void
2495on_load_library_activate (GtkMenuItem *menuitem,
2496 gpointer user_data)
2497{
2498 GError *error = NULL;
2499 MainWindow * mw_data = get_window_data_struct((GtkWidget*)menuitem);
2500
2501 gchar load_module_path_alter[PATH_MAX];
2502 {
2503 GPtrArray *name;
2504 guint nb,i;
2505 gchar *load_module_path;
2506 name = g_ptr_array_new();
2507 nb = lttv_library_path_number();
2508 /* ask for the library path */
2509
2510 for(i=0;i<nb;i++){
2511 gchar *path;
2512 path = lttv_library_path_get(i);
2513 g_ptr_array_add(name, path);
2514 }
2515
93ac601b 2516 load_module_path = get_selection(mw_data,
2517 (char **)(name->pdata), name->len,
b052368a 2518 "Select a library path", "Library paths");
2519 if(load_module_path != NULL)
2520 strncpy(load_module_path_alter, load_module_path, PATH_MAX-1); // -1 for /
2521
2522 g_ptr_array_free(name, TRUE);
2523
2524 if(load_module_path == NULL) return;
2525 }
2526
2527 {
2528 /* Make sure the module path ends with a / */
2529 gchar *ptr = load_module_path_alter;
2530
2531 ptr = strchr(ptr, '\0');
2532
2533 if(*(ptr-1) != '/') {
2534 *ptr = '/';
2535 *(ptr+1) = '\0';
2536 }
2537 }
2538
2539 {
2540 /* Ask for the library to load : list files in the previously selected
2541 * directory */
2542 gchar str[PATH_MAX];
2543 gchar ** dir;
2544 gint id;
2545 GtkFileSelection * file_selector =
2546 (GtkFileSelection *)gtk_file_selection_new("Select a module");
2547 gtk_file_selection_set_filename(file_selector, load_module_path_alter);
2548 gtk_file_selection_hide_fileop_buttons(file_selector);
2549
93ac601b 2550 gtk_window_set_transient_for(GTK_WINDOW(file_selector),
2551 GTK_WINDOW(mw_data->mwindow));
2552
b052368a 2553 str[0] = '\0';
2554 id = gtk_dialog_run(GTK_DIALOG(file_selector));
2555 switch(id){
2556 case GTK_RESPONSE_ACCEPT:
2557 case GTK_RESPONSE_OK:
2558 dir = gtk_file_selection_get_selections (file_selector);
2559 strncpy(str,dir[0],PATH_MAX);
2560 strncpy(remember_plugins_dir,dir[0],PATH_MAX);
2561 /* only keep file name */
2562 gchar *str1;
2563 str1 = strrchr(str,'/');
2564 if(str1)str1++;
2565 else{
2566 str1 = strrchr(str,'\\');
2567 str1++;
2568 }
2569#if 0
2570 /* remove "lib" */
2571 if(*str1 == 'l' && *(str1+1)== 'i' && *(str1+2)=='b')
2572 str1=str1+3;
2573 remove info after . */
2574 {
2575 gchar *str2 = str1;
2576
2577 str2 = strrchr(str2, '.');
2578 if(str2 != NULL) *str2 = '\0';
2579 }
2580 lttv_module_require(str1, &error);
2581#endif //0
2582 lttv_library_load(str1, &error);
2eef04b5 2583 if(error != NULL) g_warning("%s", error->message);
56e5a0f7 2584 else g_info("Load library: %s\n", str);
b052368a 2585 g_strfreev(dir);
2586 case GTK_RESPONSE_REJECT:
2587 case GTK_RESPONSE_CANCEL:
2588 default:
2589 gtk_widget_destroy((GtkWidget*)file_selector);
2590 break;
2591 }
2592
2593 }
2594
2595
2596
2597}
2598
2599
2600/* Display all loaded modules, let user to select a module to unload
2601 * by calling lttv_module_unload
2602 */
2603
2604void
2605on_unload_library_activate (GtkMenuItem *menuitem,
2606 gpointer user_data)
2607{
2608 MainWindow * mw_data = get_window_data_struct((GtkWidget*)menuitem);
2609
2eef04b5 2610 LttvLibrary *library = NULL;
b052368a 2611
2eef04b5 2612 GPtrArray *name;
2613 guint nb,i;
2614 gchar *lib_name;
2615 name = g_ptr_array_new();
2616 nb = lttv_library_number();
2617 LttvLibraryInfo *lib_info = g_new(LttvLibraryInfo,nb);
2618 /* ask for the library name */
2619
2620 for(i=0;i<nb;i++){
2621 LttvLibrary *iter_lib = lttv_library_get(i);
2622 lttv_library_info(iter_lib, &lib_info[i]);
2623
2624 gchar *path = lib_info[i].name;
2625 g_ptr_array_add(name, path);
2626 }
93ac601b 2627 lib_name = get_selection(mw_data, (char **)(name->pdata), name->len,
2eef04b5 2628 "Select a library", "Libraries");
2629 if(lib_name != NULL) {
b052368a 2630 for(i=0;i<nb;i++){
2eef04b5 2631 if(strcmp(lib_name, lib_info[i].name) == 0) {
2632 library = lttv_library_get(i);
2633 break;
b052368a 2634 }
2635 }
b052368a 2636 }
2eef04b5 2637 g_ptr_array_free(name, TRUE);
2638 g_free(lib_info);
2639
2640 if(lib_name == NULL) return;
2641
2642 if(library != NULL) lttv_library_unload(library);
b052368a 2643}
2644
2645
abe346a3 2646/* Dispaly a file selection dialogue to let user select a module, then call
b052368a 2647 * lttv_module_require().
abe346a3 2648 */
2649
561eba2a 2650void
2651on_load_module_activate (GtkMenuItem *menuitem,
2652 gpointer user_data)
2653{
b052368a 2654 GError *error = NULL;
bca3b81f 2655 MainWindow * mw_data = get_window_data_struct((GtkWidget*)menuitem);
b052368a 2656
2eef04b5 2657 LttvLibrary *library = NULL;
b052368a 2658 {
2659 GPtrArray *name;
2660 guint nb,i;
2661 gchar *lib_name;
2662 name = g_ptr_array_new();
2663 nb = lttv_library_number();
2664 LttvLibraryInfo *lib_info = g_new(LttvLibraryInfo,nb);
2665 /* ask for the library name */
2666
2667 for(i=0;i<nb;i++){
2668 LttvLibrary *iter_lib = lttv_library_get(i);
2669 lttv_library_info(iter_lib, &lib_info[i]);
2670
2671 gchar *path = lib_info[i].name;
2672 g_ptr_array_add(name, path);
2673 }
93ac601b 2674 lib_name = get_selection(mw_data,(char **)(name->pdata), name->len,
b052368a 2675 "Select a library", "Libraries");
2676 if(lib_name != NULL) {
2677 for(i=0;i<nb;i++){
2678 if(strcmp(lib_name, lib_info[i].name) == 0) {
2679 library = lttv_library_get(i);
2680 break;
2681 }
3872a20e 2682 }
b052368a 2683 }
2684 g_ptr_array_free(name, TRUE);
2685 g_free(lib_info);
2686
2687 if(lib_name == NULL) return;
36b3c068 2688 }
b052368a 2689
2690 //LttvModule *module;
2691 gchar module_name_out[PATH_MAX];
2692 {
2693 /* Ask for the module to load : list modules in the selected lib */
2694 GPtrArray *name;
2695 guint nb,i;
2696 gchar *module_name;
bbbd6c25 2697 nb = lttv_library_module_number(library);
b052368a 2698 LttvModuleInfo *module_info = g_new(LttvModuleInfo,nb);
2699 name = g_ptr_array_new();
b052368a 2700 /* ask for the module name */
2701
2702 for(i=0;i<nb;i++){
2703 LttvModule *iter_module = lttv_library_module_get(library, i);
2704 lttv_module_info(iter_module, &module_info[i]);
2705
2706 gchar *path = module_info[i].name;
2707 g_ptr_array_add(name, path);
2708 }
93ac601b 2709 module_name = get_selection(mw_data, (char **)(name->pdata), name->len,
b052368a 2710 "Select a module", "Modules");
2711 if(module_name != NULL) {
2712 for(i=0;i<nb;i++){
2713 if(strcmp(module_name, module_info[i].name) == 0) {
2714 strncpy(module_name_out, module_name, PATH_MAX);
2715 //module = lttv_library_module_get(i);
2716 break;
2717 }
2718 }
2719 }
2720
2721 g_ptr_array_free(name, TRUE);
2722 g_free(module_info);
2723
2724 if(module_name == NULL) return;
2725 }
2726
2727 lttv_module_require(module_name_out, &error);
2eef04b5 2728 if(error != NULL) g_warning("%s", error->message);
56e5a0f7 2729 else g_info("Load module: %s", module_name_out);
b052368a 2730
2731
2732#if 0
2733 {
2734
2735
2736 gchar str[PATH_MAX];
2737 gchar ** dir;
2738 gint id;
2739 GtkFileSelection * file_selector =
2740 (GtkFileSelection *)gtk_file_selection_new("Select a module");
2741 gtk_file_selection_set_filename(file_selector, load_module_path_alter);
2742 gtk_file_selection_hide_fileop_buttons(file_selector);
2743
2744 str[0] = '\0';
2745 id = gtk_dialog_run(GTK_DIALOG(file_selector));
2746 switch(id){
2747 case GTK_RESPONSE_ACCEPT:
2748 case GTK_RESPONSE_OK:
2749 dir = gtk_file_selection_get_selections (file_selector);
2750 strncpy(str,dir[0],PATH_MAX);
2751 strncpy(remember_plugins_dir,dir[0],PATH_MAX);
2752 {
2753 /* only keep file name */
2754 gchar *str1;
2755 str1 = strrchr(str,'/');
2756 if(str1)str1++;
2757 else{
2758 str1 = strrchr(str,'\\');
2759 str1++;
2760 }
2761#if 0
2762 /* remove "lib" */
2763 if(*str1 == 'l' && *(str1+1)== 'i' && *(str1+2)=='b')
2764 str1=str1+3;
2765 remove info after . */
2766 {
2767 gchar *str2 = str1;
2768
2769 str2 = strrchr(str2, '.');
2770 if(str2 != NULL) *str2 = '\0';
2771 }
2772 lttv_module_require(str1, &error);
2773#endif //0
2774 lttv_library_load(str1, &error);
2775 if(error != NULL) g_warning(error->message);
56e5a0f7 2776 else g_info("Load library: %s\n", str);
b052368a 2777 g_strfreev(dir);
2778 case GTK_RESPONSE_REJECT:
2779 case GTK_RESPONSE_CANCEL:
2780 default:
2781 gtk_widget_destroy((GtkWidget*)file_selector);
2782 break;
2783 }
2784
2785 }
2786#endif //0
2787
2788
561eba2a 2789}
2790
2791
b052368a 2792
abe346a3 2793/* Display all loaded modules, let user to select a module to unload
2794 * by calling lttv_module_unload
2795 */
2796
561eba2a 2797void
2798on_unload_module_activate (GtkMenuItem *menuitem,
2799 gpointer user_data)
2800{
bca3b81f 2801 MainWindow * mw_data = get_window_data_struct((GtkWidget*)menuitem);
08b1c66e 2802
43ed82b5 2803 LttvLibrary *library = NULL;
b052368a 2804 {
2805 GPtrArray *name;
2806 guint nb,i;
2807 gchar *lib_name;
2808 name = g_ptr_array_new();
2809 nb = lttv_library_number();
2810 LttvLibraryInfo *lib_info = g_new(LttvLibraryInfo,nb);
2811 /* ask for the library name */
36b3c068 2812
36b3c068 2813 for(i=0;i<nb;i++){
b052368a 2814 LttvLibrary *iter_lib = lttv_library_get(i);
2815 lttv_library_info(iter_lib, &lib_info[i]);
2816
2817 gchar *path = lib_info[i].name;
2818 g_ptr_array_add(name, path);
2819 }
93ac601b 2820 lib_name = get_selection(mw_data, (char **)(name->pdata), name->len,
b052368a 2821 "Select a library", "Libraries");
2822 if(lib_name != NULL) {
2823 for(i=0;i<nb;i++){
2824 if(strcmp(lib_name, lib_info[i].name) == 0) {
2825 library = lttv_library_get(i);
2826 break;
2827 }
36b3c068 2828 }
b052368a 2829 }
2830 g_ptr_array_free(name, TRUE);
2831 g_free(lib_info);
2832
2833 if(lib_name == NULL) return;
36b3c068 2834 }
2835
2eef04b5 2836 LttvModule *module = NULL;
b052368a 2837 {
2838 /* Ask for the module to load : list modules in the selected lib */
2839 GPtrArray *name;
2840 guint nb,i;
2841 gchar *module_name;
6d677a86 2842 nb = lttv_library_module_number(library);
b052368a 2843 LttvModuleInfo *module_info = g_new(LttvModuleInfo,nb);
2844 name = g_ptr_array_new();
b052368a 2845 /* ask for the module name */
2846
2847 for(i=0;i<nb;i++){
2848 LttvModule *iter_module = lttv_library_module_get(library, i);
2849 lttv_module_info(iter_module, &module_info[i]);
2850
2851 gchar *path = module_info[i].name;
2852 if(module_info[i].use_count > 0) g_ptr_array_add(name, path);
2853 }
93ac601b 2854 module_name = get_selection(mw_data, (char **)(name->pdata), name->len,
b052368a 2855 "Select a module", "Modules");
2856 if(module_name != NULL) {
2857 for(i=0;i<nb;i++){
2858 if(strcmp(module_name, module_info[i].name) == 0) {
2859 module = lttv_library_module_get(library, i);
2860 break;
2861 }
2862 }
2863 }
2864
2865 g_ptr_array_free(name, TRUE);
2866 g_free(module_info);
2867
2868 if(module_name == NULL) return;
2869 }
2870
b052368a 2871 LttvModuleInfo module_info;
2872 lttv_module_info(module, &module_info);
56e5a0f7 2873 g_info("Release module: %s\n", module_info.name);
fce9a2fc 2874
2875 lttv_module_release(module);
561eba2a 2876}
2877
2878
b052368a 2879/* Display a directory dialogue to let user select a path for library searching
abe346a3 2880 */
2881
561eba2a 2882void
b052368a 2883on_add_library_search_path_activate (GtkMenuItem *menuitem,
561eba2a 2884 gpointer user_data)
2885{
93ac601b 2886 MainWindow * mw_data = get_window_data_struct((GtkWidget*)menuitem);
0a946563 2887 //GtkDirSelection * file_selector = (GtkDirSelection *)gtk_dir_selection_new("Select library path");
2888 GtkFileSelection * file_selector = (GtkFileSelection *)gtk_file_selection_new("Select a trace");
2889 gtk_widget_hide( (file_selector)->file_list->parent) ;
93ac601b 2890
2891 gtk_window_set_transient_for(GTK_WINDOW(file_selector),
2892 GTK_WINDOW(mw_data->mwindow));
2893
67b98724 2894 const char * dir;
fc188b78 2895 gint id;
2896
3658a338 2897 if(remember_plugins_dir[0] != '\0')
0a946563 2898 gtk_file_selection_set_filename(file_selector, remember_plugins_dir);
fc188b78 2899
68b48a45 2900 id = gtk_dialog_run(GTK_DIALOG(file_selector));
fc188b78 2901 switch(id){
2902 case GTK_RESPONSE_ACCEPT:
2903 case GTK_RESPONSE_OK:
0a946563 2904 dir = gtk_file_selection_get_filename (file_selector);
a1a2b649 2905 strncpy(remember_plugins_dir,dir,PATH_MAX);
2906 strncat(remember_plugins_dir,"/",PATH_MAX);
08b1c66e 2907 lttv_library_path_add(dir);
fc188b78 2908 case GTK_RESPONSE_REJECT:
2909 case GTK_RESPONSE_CANCEL:
2910 default:
68b48a45 2911 gtk_widget_destroy((GtkWidget*)file_selector);
fc188b78 2912 break;
6b1d3120 2913 }
561eba2a 2914}
2915
2916
b052368a 2917/* Display a directory dialogue to let user select a path for library searching
2918 */
2919
2920void
2921on_remove_library_search_path_activate (GtkMenuItem *menuitem,
2922 gpointer user_data)
2923{
2924 MainWindow * mw_data = get_window_data_struct((GtkWidget*)menuitem);
2925
2926 const char *lib_path;
2927 {
2928 GPtrArray *name;
2929 guint nb,i;
b052368a 2930 name = g_ptr_array_new();
2931 nb = lttv_library_path_number();
2932 /* ask for the library name */
2933
2934 for(i=0;i<nb;i++){
2935 gchar *path = lttv_library_path_get(i);
2936 g_ptr_array_add(name, path);
2937 }
93ac601b 2938 lib_path = get_selection(mw_data, (char **)(name->pdata), name->len,
b052368a 2939 "Select a library path", "Library paths");
2940
2941 g_ptr_array_free(name, TRUE);
2942
2943 if(lib_path == NULL) return;
2944 }
2945
2946 lttv_library_path_remove(lib_path);
2947}
2948
561eba2a 2949void
2950on_color_activate (GtkMenuItem *menuitem,
2951 gpointer user_data)
2952{
56e5a0f7 2953 g_info("Color\n");
561eba2a 2954}
2955
2956
561eba2a 2957void
2958on_save_configuration_activate (GtkMenuItem *menuitem,
2959 gpointer user_data)
2960{
56e5a0f7 2961 g_info("Save configuration\n");
561eba2a 2962}
2963
2964
2965void
2966on_content_activate (GtkMenuItem *menuitem,
2967 gpointer user_data)
2968{
7e18bb76
F
2969 char* filename = NULL,
2970 *path;
2971 GdkScreen *screen;
2972 const char* relativePath = "doc/user/user_guide/html/index.html";
2973 filename = g_build_filename (g_get_current_dir(), relativePath, NULL);
2974 path = g_strdup_printf ("ghelp://%s", filename);
2975
2976 screen = gdk_screen_get_default();
2977 gtk_show_uri (screen, path, gtk_get_current_event_time(), NULL);
2978
2979 g_free(filename);
2980 g_free(path);
56e5a0f7 2981 g_info("Content\n");
561eba2a 2982}
2983
2984
51ef553b 2985static void
2986on_about_close_activate (GtkButton *button,
2987 gpointer user_data)
2988{
2989 GtkWidget *about_widget = GTK_WIDGET(user_data);
2990
2991 gtk_widget_destroy(about_widget);
2992}
2993
561eba2a 2994void
2995on_about_activate (GtkMenuItem *menuitem,
2996 gpointer user_data)
2997{
51ef553b 2998 MainWindow *main_window = get_window_data_struct(GTK_WIDGET(menuitem));
2999 GtkWidget *window_widget = main_window->mwindow;
3000 GtkWidget *about_widget = gtk_window_new(GTK_WINDOW_TOPLEVEL);
3001 GtkWindow *about_window = GTK_WINDOW(about_widget);
51ef553b 3002
3003 gtk_window_set_title(about_window, "About Linux Trace Toolkit");
3004
3005 gtk_window_set_resizable(about_window, FALSE);
f5f1a04e 3006 gtk_window_set_transient_for(about_window, GTK_WINDOW(window_widget));
51ef553b 3007 gtk_window_set_destroy_with_parent(about_window, TRUE);
3008 gtk_window_set_modal(about_window, FALSE);
3009
3010 /* Put the about window at the center of the screen */
7e18bb76
F
3011 gtk_window_set_position(about_window, GTK_WIN_POS_CENTER_ALWAYS);
3012
51ef553b 3013 GtkWidget *vbox = gtk_vbox_new(FALSE, 1);
3014
3015 gtk_container_add(GTK_CONTAINER(about_widget), vbox);
3016
51ef553b 3017 /* Text to show */
3018 GtkWidget *label1 = gtk_label_new("");
c8bba5fa 3019 gtk_misc_set_padding(GTK_MISC(label1), 10, 20);
51ef553b 3020 gtk_label_set_markup(GTK_LABEL(label1), "\
f5f1a04e 3021<big>Linux Trace Toolkit " VERSION "</big>");
51ef553b 3022 gtk_label_set_justify(GTK_LABEL(label1), GTK_JUSTIFY_CENTER);
3023
3024 GtkWidget *label2 = gtk_label_new("");
c8bba5fa 3025 gtk_misc_set_padding(GTK_MISC(label2), 10, 20);
51ef553b 3026 gtk_label_set_markup(GTK_LABEL(label2), "\
51ef553b 3027Contributors :\n\
3028\n\
3029Michel Dagenais (New trace format, lttv main)\n\
4b601423 3030Mathieu Desnoyers (Kernel Tracer, Directory structure, build with automake/conf,\n\
ef26c1ea 3031 lttv gui, control flow view, gui cooperative trace reading\n\
4b7bd7e1 3032 scheduler with interruptible foreground and background\n\
57ca4914 3033 computation, detailed event list (rewrite), trace reading\n\
3034 library (rewrite))\n\
7d2855bf 3035Benoit Des Ligneris, Eric Clement (Cluster adaptation, work in progress)\n\
51ef553b 3036Xang-Xiu Yang (new trace reading library and converter, lttv gui, \n\
3037 detailed event list and statistics view)\n\
e8ac6a5e 3038Tom Zanussi (RelayFS)\n\
3039\n\
f5f1a04e 3040Inspired from the original Linux Trace Toolkit Visualizer made by\n\
e8ac6a5e 3041Karim Yaghmour");
c8bba5fa 3042
3043 GtkWidget *label3 = gtk_label_new("");
3044 gtk_label_set_markup(GTK_LABEL(label3), "\
f5f1a04e 3045Linux Trace Toolkit Viewer, Copyright (C) 2004, 2005, 2006\n\
7d2855bf 3046 Michel Dagenais\n\
e8ac6a5e 3047 Mathieu Desnoyers\n\
3048 Xang-Xiu Yang\n\
c8bba5fa 3049Linux Trace Toolkit comes with ABSOLUTELY NO WARRANTY.\n\
3050This is free software, and you are welcome to redistribute it\n\
3051under certain conditions. See COPYING for details.");
3052 gtk_misc_set_padding(GTK_MISC(label3), 10, 20);
3053
51ef553b 3054 gtk_box_pack_start_defaults(GTK_BOX(vbox), label1);
3055 gtk_box_pack_start_defaults(GTK_BOX(vbox), label2);
c8bba5fa 3056 gtk_box_pack_start_defaults(GTK_BOX(vbox), label3);
51ef553b 3057
3058 GtkWidget *hbox = gtk_hbox_new(TRUE, 0);
3059 gtk_box_pack_end(GTK_BOX(vbox), hbox, FALSE, FALSE, 0);
3060 GtkWidget *close_button = gtk_button_new_with_mnemonic("_Close");
3061 gtk_box_pack_end(GTK_BOX(hbox), close_button, FALSE, FALSE, 0);
3062 gtk_container_set_border_width(GTK_CONTAINER(close_button), 20);
3063
3064 g_signal_connect(G_OBJECT(close_button), "clicked",
3065 G_CALLBACK(on_about_close_activate),
3066 (gpointer)about_widget);
3067
3068 gtk_widget_show_all(about_widget);
561eba2a 3069}
3070
3071
3072void
3073on_button_new_clicked (GtkButton *button,
3074 gpointer user_data)
3075{
6f7ad7ae 3076 create_new_window((GtkWidget*)button, user_data, TRUE);
561eba2a 3077}
3078
2901f314 3079void
3080on_button_new_tab_clicked (GtkButton *button,
3081 gpointer user_data)
3082{
3083 create_new_tab((GtkWidget*)button, user_data);
3084}
561eba2a 3085
3086void
3087on_button_open_clicked (GtkButton *button,
3088 gpointer user_data)
3089{
e865422c 3090#ifdef UNFINISHED_FEATURE
561eba2a 3091 open_traceset((GtkWidget*)button, user_data);
e865422c 3092#endif
561eba2a 3093}
3094
3095
3096void
3097on_button_add_trace_clicked (GtkButton *button,
3098 gpointer user_data)
3099{
3100 add_trace((GtkWidget*)button, user_data);
3101}
3102
3103
3104void
3105on_button_remove_trace_clicked (GtkButton *button,
3106 gpointer user_data)
3107{
3108 remove_trace((GtkWidget*)button, user_data);
3109}
3110
9878c8a4 3111void
3112on_button_redraw_clicked (GtkButton *button,
3113 gpointer user_data)
3114{
3115 redraw((GtkWidget*)button, user_data);
3116}
3117
3118void
3119on_button_continue_processing_clicked (GtkButton *button,
3120 gpointer user_data)
3121{
3122 continue_processing((GtkWidget*)button, user_data);
3123}
3124
3125void
3126on_button_stop_processing_clicked (GtkButton *button,
3127 gpointer user_data)
3128{
3129 stop_processing((GtkWidget*)button, user_data);
3130}
3131
3132
561eba2a 3133
3134void
3135on_button_save_clicked (GtkButton *button,
3136 gpointer user_data)
3137{
3138 save((GtkWidget*)button, user_data);
3139}
3140
3141
3142void
3143on_button_save_as_clicked (GtkButton *button,
3144 gpointer user_data)
3145{
3146 save_as((GtkWidget*)button, user_data);
3147}
3148
3149
3150void
3151on_button_zoom_in_clicked (GtkButton *button,
3152 gpointer user_data)
3153{
3154 zoom_in((GtkWidget*)button, user_data);
3155}
3156
3157
3158void
3159on_button_zoom_out_clicked (GtkButton *button,
3160 gpointer user_data)
3161{
3162 zoom_out((GtkWidget*)button, user_data);
3163}
3164
3165
3166void
3167on_button_zoom_extended_clicked (GtkButton *button,
3168 gpointer user_data)
3169{
3170 zoom_extended((GtkWidget*)button, user_data);
3171}
3172
3173
3174void
3175on_button_go_to_time_clicked (GtkButton *button,
3176 gpointer user_data)
3177{
3178 go_to_time((GtkWidget*)button, user_data);
3179}
3180
3181
3182void
3183on_button_show_time_frame_clicked (GtkButton *button,
3184 gpointer user_data)
3185{
3186 show_time_frame((GtkWidget*)button, user_data);
3187}
3188
3189
3190void
3191on_button_move_up_clicked (GtkButton *button,
3192 gpointer user_data)
3193{
3194 move_up_viewer((GtkWidget*)button, user_data);
3195}
3196
3197
3198void
3199on_button_move_down_clicked (GtkButton *button,
3200 gpointer user_data)
3201{
3202 move_down_viewer((GtkWidget*)button, user_data);
3203}
3204
3205
3206void
3207on_button_delete_viewer_clicked (GtkButton *button,
3208 gpointer user_data)
3209{
3210 delete_viewer((GtkWidget*)button, user_data);
3211}
3212
3213void
2d262115 3214on_MWindow_destroy (GtkWidget *widget,
561eba2a 3215 gpointer user_data)
3216{
2d262115 3217 MainWindow *main_window = get_window_data_struct(widget);
ef68c3ac 3218 LttvIAttribute *attributes = main_window->attributes;
3219 LttvAttributeValue value;
8f318283 3220 gboolean retval;
e4d09234 3221
ef68c3ac 3222 //This is unnecessary, since widgets will be destroyed
3223 //by the main window widget anyway.
3224 //remove_all_menu_toolbar_constructors(main_window, NULL);
3225
8f318283
BP
3226 retval= lttv_iattribute_find_by_path(attributes, "viewers/menu",
3227 LTTV_POINTER, &value);
3228 g_assert(retval);
ef68c3ac 3229 lttv_menus_destroy((LttvMenus*)*(value.v_pointer));
3230
8f318283
BP
3231 retval= lttv_iattribute_find_by_path(attributes, "viewers/toolbar",
3232 LTTV_POINTER, &value);
3233 g_assert(retval);
ef68c3ac 3234 lttv_toolbars_destroy((LttvToolbars*)*(value.v_pointer));
2d262115 3235
ef68c3ac 3236 g_object_unref(main_window->attributes);
3237 g_main_window_list = g_slist_remove(g_main_window_list, main_window);
561eba2a 3238
56e5a0f7 3239 g_info("There are now : %d windows\n",g_slist_length(g_main_window_list));
2d262115 3240 if(g_slist_length(g_main_window_list) == 0)
d27948a3 3241 mainwindow_quit();
561eba2a 3242}
3243
58eecf4a 3244gboolean
3245on_MWindow_configure (GtkWidget *widget,
3246 GdkEventConfigure *event,
3247 gpointer user_data)
3248{
bd24a9af 3249 // MD : removed time width modification upon resizing of the main window.
3250 // The viewers will redraw themselves completely, without time interval
3251 // modification.
3252/* while(tab){
58eecf4a 3253 if(mw_data->window_width){
3254 time_span = LTTV_TRACESET_CONTEXT(tab->traceset_info->traceset_context)->Time_Span ;
3255 time_win = tab->time_window;
3256 ratio = width / mw_data->window_width;
3257 tab->time_window.time_width = ltt_time_mul(time_win.time_width,ratio);
3258 time = ltt_time_sub(time_span->endTime, time_win.start_time);
3259 if(ltt_time_compare(time, tab->time_window.time_width) < 0){
3260 tab->time_window.time_width = time;
3261 }
3262 }
3263 tab = tab->next;
3264 }
3265
3266 mw_data->window_width = (int)width;
bd24a9af 3267 */
58eecf4a 3268 return FALSE;
3269}
561eba2a 3270
abe346a3 3271/* Set current tab
3272 */
3273
561eba2a 3274void
3275on_MNotebook_switch_page (GtkNotebook *notebook,
3276 GtkNotebookPage *page,
3277 guint page_num,
3278 gpointer user_data)
3279{
47cd8a09 3280
561eba2a 3281}
3282
abe346a3 3283
e800cf84 3284void time_change_manager (Tab *tab,
3285 TimeWindow new_time_window)
451aaf27
FD
3286{
3287
e800cf84 3288 /* Only one source of time change */
3289 if(tab->time_manager_lock == TRUE) return;
3290
3291 tab->time_manager_lock = TRUE;
451aaf27
FD
3292 TimeInterval time_span;
3293
3294 LttvTraceset *ts = tab->traceset_info->traceset;
3295 time_span.start_time =ltt_time_from_uint64( lttv_traceset_get_timestamp_begin(ts));
3296 time_span.end_time = ltt_time_from_uint64(lttv_traceset_get_timestamp_end(ts));
3297
e800cf84 3298
e800cf84 3299 LttTime start_time = new_time_window.start_time;
6f26fc38 3300 LttTime end_time = new_time_window.end_time;
e800cf84 3301
a998b781 3302 g_assert(ltt_time_compare(start_time, end_time) < 0);
3303
e800cf84 3304 /* Set scrollbar */
3305 GtkAdjustment *adjustment = gtk_range_get_adjustment(GTK_RANGE(tab->scrollbar));
451aaf27
FD
3306 LttTime upper = ltt_time_sub(time_span.end_time, time_span.start_time);
3307
e800cf84 3308#if 0
3309 gtk_range_set_increments(GTK_RANGE(tab->scrollbar),
3310 ltt_time_to_double(new_time_window.time_width)
3311 / SCROLL_STEP_PER_PAGE
3312 * NANOSECONDS_PER_SECOND, /* step increment */
3313 ltt_time_to_double(new_time_window.time_width)
3314 * NANOSECONDS_PER_SECOND); /* page increment */
3315 gtk_range_set_range(GTK_RANGE(tab->scrollbar),
3316 0.0, /* lower */
3317 ltt_time_to_double(upper)
3318 * NANOSECONDS_PER_SECOND); /* upper */
3319#endif //0
3320 g_object_set(G_OBJECT(adjustment),
3321 "lower",
3322 0.0, /* lower */
3323 "upper",
c74e0cf9 3324 ltt_time_to_double(upper), /* upper */
e800cf84 3325 "step_increment",
a18124ff 3326 new_time_window.time_width_double
c74e0cf9 3327 / SCROLL_STEP_PER_PAGE, /* step increment */
e800cf84 3328 "page_increment",
a18124ff 3329 new_time_window.time_width_double,
c74e0cf9 3330 /* page increment */
e800cf84 3331 "page_size",
a18124ff 3332 new_time_window.time_width_double, /* page size */
e800cf84 3333 NULL);
3334 gtk_adjustment_changed(adjustment);
3335
3336 // g_object_set(G_OBJECT(adjustment),
3337 // "value",
3338 // ltt_time_to_double(
3339 // ltt_time_sub(start_time, time_span.start_time))
c74e0cf9 3340 // , /* value */
e800cf84 3341 // NULL);
3342 //gtk_adjustment_value_changed(adjustment);
3343 gtk_range_set_value(GTK_RANGE(tab->scrollbar),
3344 ltt_time_to_double(
c74e0cf9 3345 ltt_time_sub(start_time, time_span.start_time)) /* value */);
e800cf84 3346
3347 /* set the time bar. */
e800cf84 3348
6f26fc38 3349
4172f013
YB
3350 timebar_set_minmax_time(TIMEBAR(tab->MTimebar),
3351 &time_span.start_time,
3352 &time_span.end_time );
3353 timebar_set_start_time(TIMEBAR(tab->MTimebar),&start_time);
3354 timebar_set_end_time(TIMEBAR(tab->MTimebar),&end_time);
e800cf84 3355
e800cf84 3356
58de9fc1 3357
4172f013
YB
3358 /* call viewer hooks for new time window */
3359 set_time_window(tab, &new_time_window);
58de9fc1 3360
4172f013 3361 tab->time_manager_lock = FALSE;
451aaf27
FD
3362
3363
58de9fc1 3364}
3365
58de9fc1 3366
58de9fc1 3367
3368
e800cf84 3369
3370void current_time_change_manager (Tab *tab,
3371 LttTime new_current_time)
3372{
3373 /* Only one source of time change */
3374 if(tab->current_time_manager_lock == TRUE) return;
3375
3376 tab->current_time_manager_lock = TRUE;
3377
4172f013 3378 timebar_set_current_time(TIMEBAR(tab->MTimebar), &new_current_time);
e800cf84 3379
db8bc917 3380 set_current_time(tab, &new_current_time);
e800cf84 3381
3382 tab->current_time_manager_lock = FALSE;
3383}
3384
9a366873 3385void current_position_change_manager(Tab *tab, LttvTracesetPosition *pos)
5290ec02 3386{
9a366873 3387 lttv_traceset_seek_to_position( pos);
5290ec02 3388
9a366873 3389 LttTime new_time = lttv_traceset_position_get_time(pos);
16e2bb34 3390 /* Put the context in a state coherent position */
9a366873
FD
3391#ifdef BABEL_CLEANUP
3392 lttv_state_traceset_seek_time_closest((LttvTracesetState*)tsc, ltt_time_zero);
3393#endif /* BABEL_CLEANUP */
5290ec02 3394 current_time_change_manager(tab, new_time);
3395
3396 set_current_position(tab, pos);
3397}
3398
4172f013
YB
3399static void on_timebar_starttime_changed(Timebar *timebar,
3400 gpointer user_data)
e800cf84 3401{
4172f013 3402 Tab *tab = (Tab *)user_data;
9aaa78dc
FD
3403 LttvTraceset * ts =tab->traceset_info->traceset;
3404 TimeInterval time_span = lttv_traceset_get_time_span(ts);
4172f013
YB
3405
3406 TimeWindow new_time_window = tab->time_window;
3407 new_time_window.start_time = timebar_get_start_time(timebar);
3408
3409 LttTime end_time = new_time_window.end_time;
3410
3411 /* TODO ybrosseau 2010-12-02: This if should have been checked
3412 by the timebar already */
3413 if(ltt_time_compare(new_time_window.start_time, end_time) >= 0) {
3414 /* Then, we must push back end time : keep the same time width
3415 * if possible, else end traceset time */
3416 end_time = LTT_TIME_MIN(ltt_time_add(new_time_window.start_time,
3417 new_time_window.time_width),
3418 time_span.end_time);
3419 }
3420
3421 /* Fix the time width to fit start time and end time */
3422 new_time_window.time_width = ltt_time_sub(end_time,
3423 new_time_window.start_time);
3424
3425 new_time_window.time_width_double =
3426 ltt_time_to_double(new_time_window.time_width);
3427
3428 new_time_window.end_time = end_time;
3429
3430 /* Notify the time_manager */
3431 time_change_manager(tab, new_time_window);
9aaa78dc 3432
e800cf84 3433}
3434
4172f013
YB
3435static void on_timebar_endtime_changed(Timebar *timebar,
3436 gpointer user_data)
e800cf84 3437{
4172f013 3438 Tab *tab = (Tab *)user_data;
9aaa78dc
FD
3439 LttvTraceset * ts =tab->traceset_info->traceset;
3440 TimeInterval time_span = lttv_traceset_get_time_span(ts);
e800cf84 3441
4172f013
YB
3442 TimeWindow new_time_window = tab->time_window;
3443
3444 LttTime end_time = timebar_get_end_time(timebar);
3445
3446 /* TODO ybrosseau 2010-12-02: This if should have been
3447 checked by the timebar already */
3448 if(ltt_time_compare(new_time_window.start_time, end_time) >= 0) {
3449 /* Then, we must push front start time : keep the same time
3450 width if possible, else end traceset time */
3451 new_time_window.start_time = LTT_TIME_MAX(
3452 ltt_time_sub(end_time,
3453 new_time_window.time_width),
3454 time_span.start_time);
3455 }
e800cf84 3456
4172f013
YB
3457 /* Fix the time width to fit start time and end time */
3458 new_time_window.time_width = ltt_time_sub(end_time,
3459 new_time_window.start_time);
3460
3461 new_time_window.time_width_double =
3462 ltt_time_to_double(new_time_window.time_width);
3463
3464 new_time_window.end_time = end_time;
3465
3466 /* Notify the time_manager */
9aaa78dc 3467 time_change_manager(tab, new_time_window);
4172f013
YB
3468}
3469static void on_timebar_currenttime_changed(Timebar *timebar,
3470 gpointer user_data)
3471{
3472 Tab *tab = (Tab *)user_data;
3473
3474 LttTime new_current_time = timebar_get_current_time(timebar);
3475
3476 current_time_change_manager(tab, new_current_time);
3477}
e800cf84 3478
b052368a 3479void scroll_value_changed_cb(GtkWidget *scrollbar,
3480 gpointer user_data)
3481{
3482 Tab *tab = (Tab *)user_data;
e800cf84 3483 TimeWindow new_time_window;
b052368a 3484 LttTime time;
3485 GtkAdjustment *adjust = gtk_range_get_adjustment(GTK_RANGE(scrollbar));
3486 gdouble value = gtk_adjustment_get_value(adjust);
e800cf84 3487 // gdouble upper, lower, ratio, page_size;
3488 gdouble page_size;
9aaa78dc
FD
3489
3490 LttvTraceset * ts = tab->traceset_info->traceset;
3491 TimeInterval time_span = lttv_traceset_get_time_span(ts);
b052368a 3492
c74e0cf9 3493 time = ltt_time_add(ltt_time_from_double(value),
e800cf84 3494 time_span.start_time);
3495
3496 new_time_window.start_time = time;
3497
3498 page_size = adjust->page_size;
3499
3500 new_time_window.time_width =
c74e0cf9 3501 ltt_time_from_double(page_size);
e800cf84 3502
a18124ff 3503 new_time_window.time_width_double =
3504 page_size;
3505
6f26fc38 3506 new_time_window.end_time = ltt_time_add(new_time_window.start_time,
3507 new_time_window.time_width);
3508
e800cf84 3509
3510 time_change_manager(tab, new_time_window);
9aaa78dc 3511
e800cf84 3512#if 0
b052368a 3513 //time_window = tab->time_window;
3514
b052368a 3515 lower = adjust->lower;
3516 upper = adjust->upper;
3517 ratio = (value - lower) / (upper - lower);
2b5cc5a5 3518 g_info("lower %lu, upper %lu, value %lu, ratio %lu", lower, upper, value, ratio);
b052368a 3519
3520 //time = ltt_time_sub(time_span->end_time, time_span->start_time);
3521 //time = ltt_time_mul(time, (float)ratio);
3522 //time = ltt_time_add(time_span->start_time, time);
c74e0cf9 3523 time = ltt_time_add(ltt_time_from_double(value),
b9a010a2 3524 time_span.start_time);
b052368a 3525
3526 time_window.start_time = time;
3527
3528 page_size = adjust->page_size;
3529
3530 time_window.time_width =
c74e0cf9 3531 ltt_time_from_double(page_size);
b9a010a2 3532 //time = ltt_time_sub(time_span.end_time, time);
b052368a 3533 //if(ltt_time_compare(time,time_window.time_width) < 0){
3534 // time_window.time_width = time;
3535 //}
3536
3537 /* call viewer hooks for new time window */
3538 set_time_window(tab, &time_window);
e800cf84 3539#endif //0
9aaa78dc 3540
b052368a 3541}
3542
3543
abe346a3 3544/* Display a dialogue showing all eventtypes and traces, let user to select the interested
3545 * eventtypes, tracefiles and traces (filter)
3546 */
3547
abe346a3 3548/* Select a trace which will be removed from traceset
3549 */
3550
93ac601b 3551char * get_remove_trace(MainWindow *mw_data,
3552 char ** all_trace_name, int nb_trace)
2176f952 3553{
93ac601b 3554 return get_selection(mw_data, all_trace_name, nb_trace,
2176f952 3555 "Select a trace", "Trace pathname");
3556}
abe346a3 3557
3558
b052368a 3559/* Select a module which will be loaded
3560 */
3561
93ac601b 3562char * get_load_module(MainWindow *mw_data,
3563 char ** load_module_name, int nb_module)
b052368a 3564{
93ac601b 3565 return get_selection(mw_data, load_module_name, nb_module,
b052368a 3566 "Select a module to load", "Module name");
3567}
3568
3569
3570
3571
abe346a3 3572/* Select a module which will be unloaded
3573 */
3574
93ac601b 3575char * get_unload_module(MainWindow *mw_data,
3576 char ** loaded_module_name, int nb_module)
2176f952 3577{
93ac601b 3578 return get_selection(mw_data, loaded_module_name, nb_module,
b052368a 3579 "Select a module to unload", "Module name");
2176f952 3580}
3581
abe346a3 3582
3583/* Display a dialogue which shows all selectable items, let user to
3584 * select one of them
3585 */
3586
93ac601b 3587char * get_selection(MainWindow *mw_data,
3588 char ** loaded_module_name, int nb_module,
3589 char *title, char * column_title)
36b3c068 3590{
3591 GtkWidget * dialogue;
3592 GtkWidget * scroll_win;
3593 GtkWidget * tree;
3594 GtkListStore * store;
3595 GtkTreeViewColumn * column;
3596 GtkCellRenderer * renderer;
3597 GtkTreeSelection * select;
3598 GtkTreeIter iter;
3599 gint id, i;
3600 char * unload_module_name = NULL;
3601
2176f952 3602 dialogue = gtk_dialog_new_with_buttons(title,
36b3c068 3603 NULL,
3604 GTK_DIALOG_MODAL,
3605 GTK_STOCK_OK,GTK_RESPONSE_ACCEPT,
3606 GTK_STOCK_CANCEL,GTK_RESPONSE_REJECT,
3607 NULL);
3608 gtk_window_set_default_size((GtkWindow*)dialogue, 500, 200);
93ac601b 3609 gtk_window_set_transient_for(GTK_WINDOW(dialogue),
3610 GTK_WINDOW(mw_data->mwindow));
36b3c068 3611
3612 scroll_win = gtk_scrolled_window_new (NULL, NULL);
3613 gtk_widget_show ( scroll_win);
3614 gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(scroll_win),
3615 GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC);
3616
3617 store = gtk_list_store_new (N_COLUMNS,G_TYPE_STRING);
3618 tree = gtk_tree_view_new_with_model(GTK_TREE_MODEL (store));
3619 gtk_widget_show ( tree);
3620 g_object_unref (G_OBJECT (store));
3621
3622 renderer = gtk_cell_renderer_text_new ();
2176f952 3623 column = gtk_tree_view_column_new_with_attributes (column_title,
36b3c068 3624 renderer,
3625 "text", MODULE_COLUMN,
3626 NULL);
3627 gtk_tree_view_column_set_alignment (column, 0.5);
3628 gtk_tree_view_column_set_fixed_width (column, 150);
3629 gtk_tree_view_append_column (GTK_TREE_VIEW (tree), column);
3630
3631 select = gtk_tree_view_get_selection (GTK_TREE_VIEW (tree));
3632 gtk_tree_selection_set_mode (select, GTK_SELECTION_SINGLE);
3633
3634 gtk_container_add (GTK_CONTAINER (scroll_win), tree);
3635
3636 gtk_box_pack_start(GTK_BOX(GTK_DIALOG(dialogue)->vbox), scroll_win,TRUE, TRUE,0);
3637
3638 for(i=0;i<nb_module;i++){
3639 gtk_list_store_append (store, &iter);
3640 gtk_list_store_set (store, &iter, MODULE_COLUMN,loaded_module_name[i],-1);
3641 }
3642
3643 id = gtk_dialog_run(GTK_DIALOG(dialogue));
d27948a3 3644 GtkTreeModel **store_model = (GtkTreeModel**)&store;
36b3c068 3645 switch(id){
3646 case GTK_RESPONSE_ACCEPT:
3647 case GTK_RESPONSE_OK:
2eef04b5 3648 if (gtk_tree_selection_get_selected (select, store_model, &iter)){
36b3c068 3649 gtk_tree_model_get ((GtkTreeModel*)store, &iter, MODULE_COLUMN, &unload_module_name, -1);
3650 }
3651 case GTK_RESPONSE_REJECT:
3652 case GTK_RESPONSE_CANCEL:
3653 default:
3654 gtk_widget_destroy(dialogue);
3655 break;
3656 }
3657
3658 return unload_module_name;
3659}
5723fa24 3660
abe346a3 3661
ef68c3ac 3662/* Insert all menu entry and tool buttons into this main window
001d8606 3663 * for modules.
3664 *
abe346a3 3665 */
3666
6c9d86dd 3667void add_all_menu_toolbar_constructors(MainWindow * mw, gpointer user_data)
5723fa24 3668{
2eef04b5 3669 guint i;
5723fa24 3670 GdkPixbuf *pixbuf;
42fcbb71 3671 lttvwindow_viewer_constructor constructor;
001d8606 3672 LttvMenus * global_menu, * instance_menu;
3673 LttvToolbars * global_toolbar, * instance_toolbar;
6c9d86dd 3674 LttvMenuClosure *menu_item;
3675 LttvToolbarClosure *toolbar_item;
5723fa24 3676 LttvAttributeValue value;
001d8606 3677 LttvIAttribute *global_attributes = LTTV_IATTRIBUTE(lttv_global_attributes());
501e4e70 3678 LttvIAttribute *attributes = mw->attributes;
001d8606 3679 GtkWidget * tool_menu_title_menu, *new_widget, *pixmap;
8f318283 3680 gboolean retval;
001d8606 3681
8f318283
BP
3682 retval= lttv_iattribute_find_by_path(global_attributes, "viewers/menu",
3683 LTTV_POINTER, &value);
3684 g_assert(retval);
001d8606 3685 if(*(value.v_pointer) == NULL)
501e4e70 3686 *(value.v_pointer) = lttv_menus_new();
001d8606 3687 global_menu = (LttvMenus*)*(value.v_pointer);
5723fa24 3688
8f318283
BP
3689 retval= lttv_iattribute_find_by_path(attributes, "viewers/menu",
3690 LTTV_POINTER, &value);
3691 g_assert(retval);
001d8606 3692 if(*(value.v_pointer) == NULL)
501e4e70 3693 *(value.v_pointer) = lttv_menus_new();
001d8606 3694 instance_menu = (LttvMenus*)*(value.v_pointer);
5723fa24 3695
8f318283
BP
3696 retval= lttv_iattribute_find_by_path(global_attributes, "viewers/toolbar",
3697 LTTV_POINTER, &value);
3698 g_assert(retval);
001d8606 3699 if(*(value.v_pointer) == NULL)
501e4e70 3700 *(value.v_pointer) = lttv_toolbars_new();
001d8606 3701 global_toolbar = (LttvToolbars*)*(value.v_pointer);
3702
8f318283
BP
3703 retval= lttv_iattribute_find_by_path(attributes, "viewers/toolbar",
3704 LTTV_POINTER, &value);
3705 g_assert(retval);
001d8606 3706 if(*(value.v_pointer) == NULL)
501e4e70 3707 *(value.v_pointer) = lttv_toolbars_new();
001d8606 3708 instance_toolbar = (LttvToolbars*)*(value.v_pointer);
3709
3710 /* Add missing menu entries to window instance */
3711 for(i=0;i<global_menu->len;i++) {
6c9d86dd 3712 menu_item = &g_array_index(global_menu, LttvMenuClosure, i);
3713
3714 //add menu_item to window instance;
3715 constructor = menu_item->con;
3716 tool_menu_title_menu = lookup_widget(mw->mwindow,"ToolMenuTitle_menu");
3717 new_widget =
501e4e70 3718 gtk_menu_item_new_with_mnemonic (menu_item->menu_text);
6c9d86dd 3719 gtk_container_add (GTK_CONTAINER (tool_menu_title_menu),
3720 new_widget);
3721 g_signal_connect ((gpointer) new_widget, "activate",
3722 G_CALLBACK (insert_viewer_wrap),
3723 constructor);
3724 gtk_widget_show (new_widget);
3725 lttv_menus_add(instance_menu, menu_item->con,
3726 menu_item->menu_path,
3727 menu_item->menu_text,
3728 new_widget);
001d8606 3729
001d8606 3730 }
3731
3732 /* Add missing toolbar entries to window instance */
3733 for(i=0;i<global_toolbar->len;i++) {
6c9d86dd 3734 toolbar_item = &g_array_index(global_toolbar, LttvToolbarClosure, i);
3735
3736 //add toolbar_item to window instance;
3737 constructor = toolbar_item->con;
3738 tool_menu_title_menu = lookup_widget(mw->mwindow,"MToolbar1");
3739 pixbuf = gdk_pixbuf_new_from_xpm_data((const char**)toolbar_item->pixmap);
3740 pixmap = gtk_image_new_from_pixbuf(pixbuf);
3741 new_widget =
3742 gtk_toolbar_append_element (GTK_TOOLBAR (tool_menu_title_menu),
3743 GTK_TOOLBAR_CHILD_BUTTON,
3744 NULL,
3745 "",
3746 toolbar_item->tooltip, NULL,
3747 pixmap, NULL, NULL);
3748 gtk_label_set_use_underline(
3749 GTK_LABEL (((GtkToolbarChild*) (
3750 g_list_last (GTK_TOOLBAR
3751 (tool_menu_title_menu)->children)->data))->label),
3752 TRUE);
3753 gtk_container_set_border_width (GTK_CONTAINER (new_widget), 1);
3754 g_signal_connect ((gpointer) new_widget,
3755 "clicked",
3756 G_CALLBACK (insert_viewer_wrap),
3757 constructor);
3758 gtk_widget_show (new_widget);
001d8606 3759
6c9d86dd 3760 lttv_toolbars_add(instance_toolbar, toolbar_item->con,
3761 toolbar_item->tooltip,
3762 toolbar_item->pixmap,
3763 new_widget);
001d8606 3764
5723fa24 3765 }
6c9d86dd 3766
5723fa24 3767}
3768
abe346a3 3769
3770/* Create a main window
3771 */
3772
8321ae6a 3773MainWindow *construct_main_window(MainWindow * parent)
5723fa24 3774{
8f318283
BP
3775 gboolean retval;
3776
2a2fa4f0 3777 g_debug("construct_main_window()");
68b48a45 3778 GtkWidget * new_window; /* New generated main window */
bca3b81f 3779 MainWindow * new_m_window;/* New main window structure */
5723fa24 3780 GtkNotebook * notebook;
f7afe191 3781 LttvIAttribute *attributes =
3782 LTTV_IATTRIBUTE(g_object_new(LTTV_ATTRIBUTE_TYPE, NULL));
3783 LttvAttributeValue value;
e865422c 3784
bca3b81f 3785 new_m_window = g_new(MainWindow, 1);
5723fa24 3786
3787 // Add the object's information to the module's array
68b48a45 3788 g_main_window_list = g_slist_append(g_main_window_list, new_m_window);
5723fa24 3789
68b48a45 3790 new_window = create_MWindow();
3791 gtk_widget_show (new_window);
5723fa24 3792
bca3b81f 3793 new_m_window->mwindow = new_window;
a43d67ba 3794 new_m_window->attributes = attributes;
5723fa24 3795
8f318283
BP
3796 retval= lttv_iattribute_find_by_path(attributes, "viewers/menu",
3797 LTTV_POINTER, &value);
3798 g_assert(retval);
501e4e70 3799 *(value.v_pointer) = lttv_menus_new();
001d8606 3800
8f318283
BP
3801 retval= lttv_iattribute_find_by_path(attributes, "viewers/toolbar",
3802 LTTV_POINTER, &value);
3803 g_assert(retval);
501e4e70 3804 *(value.v_pointer) = lttv_toolbars_new();
2061e03d 3805
6c9d86dd 3806 add_all_menu_toolbar_constructors(new_m_window, NULL);
5723fa24 3807
2d262115 3808 g_object_set_data_full(G_OBJECT(new_window),
3809 "main_window_data",
3810 (gpointer)new_m_window,
3811 (GDestroyNotify)g_free);
5723fa24 3812 //create a default tab
bca3b81f 3813 notebook = (GtkNotebook *)lookup_widget(new_m_window->mwindow, "MNotebook");
5723fa24 3814 if(notebook == NULL){
56e5a0f7 3815 g_info("Notebook does not exist\n");
8321ae6a 3816 /* FIXME : destroy partially created widgets */
3817 g_free(new_m_window);
3818 return NULL;
5723fa24 3819 }
e800cf84 3820 //gtk_notebook_popup_enable (GTK_NOTEBOOK(notebook));
5723fa24 3821 //for now there is no name field in LttvTraceset structure
3822 //Use "Traceset" as the label for the default tab
6ced96ef 3823 if(parent) {
3824 GtkWidget * parent_notebook = lookup_widget(parent->mwindow, "MNotebook");
3825 GtkWidget *page = gtk_notebook_get_nth_page(GTK_NOTEBOOK(parent_notebook),
3826 gtk_notebook_get_current_page(GTK_NOTEBOOK(parent_notebook)));
3827 Tab *parent_tab;
3828
3829 if(!page) {
3830 parent_tab = NULL;
3831 } else {
e433e6d6 3832 LttvPluginTab *ptab;
3833 ptab = (LttvPluginTab *)g_object_get_data(G_OBJECT(page), "Tab_Plugin");
3834 parent_tab = ptab->tab;
6ced96ef 3835 }
e433e6d6 3836 LttvPluginTab *ptab = g_object_new(LTTV_TYPE_PLUGIN_TAB, NULL);
3837 init_tab(ptab->tab,
3838 new_m_window, parent_tab, notebook, "Traceset");
3839 ptab->parent.top_widget = ptab->tab->top_widget;
3840 g_object_set_data_full(
3841 G_OBJECT(ptab->tab->vbox),
3842 "Tab_Plugin",
3843 ptab,
3844 (GDestroyNotify)tab_destructor);
6ced96ef 3845 } else {
e433e6d6 3846 LttvPluginTab *ptab = g_object_new(LTTV_TYPE_PLUGIN_TAB, NULL);
3847 init_tab(ptab->tab, new_m_window, NULL, notebook, "Traceset");
3848 ptab->parent.top_widget = ptab->tab->top_widget;
3849 g_object_set_data_full(
3850 G_OBJECT(ptab->tab->vbox),
3851 "Tab_Plugin",
3852 ptab,
3853 (GDestroyNotify)tab_destructor);
6cec4cd2 3854 }
91fd6881 3855
6cec4cd2 3856 /* Insert default viewers */
3857 {
3858 LttvAttributeType type;
3859 LttvAttributeName name;
3860 LttvAttributeValue value;
3861 LttvAttribute *attribute;
3862
3863 LttvIAttribute *attributes_global =
3864 LTTV_IATTRIBUTE(lttv_global_attributes());
3865
43ed82b5 3866 attribute = LTTV_ATTRIBUTE(lttv_iattribute_find_subdir(
3867 LTTV_IATTRIBUTE(attributes_global),
3868 LTTV_VIEWER_CONSTRUCTORS));
3869 g_assert(attribute);
6cec4cd2 3870
3871 name = g_quark_from_string("guievents");
3872 type = lttv_iattribute_get_by_name(LTTV_IATTRIBUTE(attribute),
3873 name, &value);
3874 if(type == LTTV_POINTER) {
3875 lttvwindow_viewer_constructor viewer_constructor =
3876 (lttvwindow_viewer_constructor)*value.v_pointer;
3877 insert_viewer(new_window, viewer_constructor);
4266dc7f 3878 }
e025a729 3879
6cec4cd2 3880 name = g_quark_from_string("guicontrolflow");
3881 type = lttv_iattribute_get_by_name(LTTV_IATTRIBUTE(attribute),
3882 name, &value);
3883 if(type == LTTV_POINTER) {
3884 lttvwindow_viewer_constructor viewer_constructor =
3885 (lttvwindow_viewer_constructor)*value.v_pointer;
3886 insert_viewer(new_window, viewer_constructor);
3887 }
e025a729 3888
6cec4cd2 3889 name = g_quark_from_string("guistatistics");
3890 type = lttv_iattribute_get_by_name(LTTV_IATTRIBUTE(attribute),
3891 name, &value);
3892 if(type == LTTV_POINTER) {
3893 lttvwindow_viewer_constructor viewer_constructor =
3894 (lttvwindow_viewer_constructor)*value.v_pointer;
3895 insert_viewer(new_window, viewer_constructor);
e025a729 3896 }
4266dc7f 3897 }
5723fa24 3898
56e5a0f7 3899 g_info("There are now : %d windows\n",g_slist_length(g_main_window_list));
8321ae6a 3900
3901 return new_m_window;
5723fa24 3902}
3903
abe346a3 3904
3905/* Free the memory occupied by a tab structure
3906 * destroy the tab
3907 */
3908
e433e6d6 3909void tab_destructor(LttvPluginTab * ptab)
f7afe191 3910{
451aaf27 3911#ifdef BABEL_CLEANUP
716e4367 3912 int i, nb, ref_count;
3913 LttvTrace * trace;
e433e6d6 3914 Tab *tab = ptab->tab;
716e4367 3915
3234f094 3916 if(tab->attributes)
3917 g_object_unref(tab->attributes);
501e4e70 3918
3234f094 3919 if(tab->interrupted_state)
3920 g_object_unref(tab->interrupted_state);
501e4e70 3921
2061e03d 3922
3234f094 3923 if(tab->traceset_info->traceset_context != NULL){
784705cc 3924 //remove state update hooks
3925 lttv_state_remove_event_hooks(
3234f094 3926 (LttvTracesetState*)tab->traceset_info->
784705cc 3927 traceset_context);
3234f094 3928 lttv_context_fini(LTTV_TRACESET_CONTEXT(tab->traceset_info->
716e4367 3929 traceset_context));
3234f094 3930 g_object_unref(tab->traceset_info->traceset_context);
716e4367 3931 }
3234f094 3932 if(tab->traceset_info->traceset != NULL) {
3933 nb = lttv_traceset_number(tab->traceset_info->traceset);
716e4367 3934 for(i = 0 ; i < nb ; i++) {
3234f094 3935 trace = lttv_traceset_get(tab->traceset_info->traceset, i);
716e4367 3936 ref_count = lttv_trace_get_ref_number(trace);
49bf71b5 3937 if(ref_count <= 1){
a1a2b649 3938 ltt_trace_close(lttv_trace(trace));
49bf71b5 3939 }
716e4367 3940 }
dc5e5266 3941 }
3234f094 3942 lttv_traceset_destroy(tab->traceset_info->traceset);
501e4e70 3943 /* Remove the idle events requests processing function of the tab */
3234f094 3944 g_idle_remove_by_data(tab);
501e4e70 3945
3234f094 3946 g_slist_free(tab->events_requests);
3947 g_free(tab->traceset_info);
e433e6d6 3948 //g_free(tab);
3949 g_object_unref(ptab);
451aaf27 3950#endif /* BABEL_CLEANUP */
f7afe191 3951}
3952
abe346a3 3953
3954/* Create a tab and insert it into the current main window
3955 */
3956
e433e6d6 3957void init_tab(Tab *tab, MainWindow * mw, Tab *copy_tab,
716e4367 3958 GtkNotebook * notebook, char * label)
5723fa24 3959{
451aaf27 3960
5723fa24 3961 GList * list;
e433e6d6 3962 //Tab * tab;
3963 //LttvFilter *filter = NULL;
a43d67ba 3964
abe346a3 3965 //create a new tab data structure
e433e6d6 3966 //tab = g_new(Tab,1);
716e4367 3967
abe346a3 3968 //construct and initialize the traceset_info
6ced96ef 3969 tab->traceset_info = g_new(TracesetInfo,1);
a43d67ba 3970
4266dc7f 3971 if(copy_tab) {
6ced96ef 3972 tab->traceset_info->traceset =
4266dc7f 3973 lttv_traceset_copy(copy_tab->traceset_info->traceset);
dc5e5266 3974
3975 /* Copy the previous tab's filter */
3976 /* We can clone the filter, as we copy the trace set also */
3977 /* The filter must always be in sync with the trace set */
451aaf27
FD
3978
3979#ifdef BABEL_CLEANUP
ebcead4a 3980 tab->filter = lttv_filter_clone(copy_tab->filter);
451aaf27 3981#endif /* BABEL_CLEANUP */
4266dc7f 3982 } else {
6ced96ef 3983 tab->traceset_info->traceset = lttv_traceset_new();
451aaf27 3984
dc5e5266 3985 tab->filter = NULL;
716e4367 3986 }
84ddf5c9 3987#ifdef DEBUG
20fde85f 3988 lttv_attribute_write_xml(
6ced96ef 3989 lttv_traceset_attribute(tab->traceset_info->traceset),
20fde85f 3990 stdout,
3991 0, 4);
3992 fflush(stdout);
84ddf5c9 3993#endif //DEBUG
451aaf27 3994//
e800cf84 3995 tab->time_manager_lock = FALSE;
3996 tab->current_time_manager_lock = FALSE;
451aaf27 3997#ifdef BABEL_CLEANUP
716e4367 3998 //FIXME copy not implemented in lower level
6ced96ef 3999 tab->traceset_info->traceset_context =
716e4367 4000 g_object_new(LTTV_TRACESET_STATS_TYPE, NULL);
784705cc 4001 //add state update hooks
451aaf27 4002#endif //BABEL_CLEANUP
a7598d50
YB
4003 lttv_state_add_event_hooks(
4004 tab->traceset_info->traceset);
4005
abe346a3 4006 //determine the current_time and time_window of the tab
e800cf84 4007#if 0
6ced96ef 4008 if(copy_tab != NULL){
4009 tab->time_window = copy_tab->time_window;
4010 tab->current_time = copy_tab->current_time;
5723fa24 4011 }else{
6ced96ef 4012 tab->time_window.start_time =
4013 LTTV_TRACESET_CONTEXT(tab->traceset_info->traceset_context)->
4014 time_span.start_time;
f7afe191 4015 if(DEFAULT_TIME_WIDTH_S <
6ced96ef 4016 LTTV_TRACESET_CONTEXT(tab->traceset_info->traceset_context)->
4017 time_span.end_time.tv_sec)
68b48a45 4018 tmp_time.tv_sec = DEFAULT_TIME_WIDTH_S;
f7afe191 4019 else
68b48a45 4020 tmp_time.tv_sec =
6ced96ef 4021 LTTV_TRACESET_CONTEXT(tab->traceset_info->traceset_context)->
4022 time_span.end_time.tv_sec;
68b48a45 4023 tmp_time.tv_nsec = 0;
6ced96ef 4024 tab->time_window.time_width = tmp_time ;
4025 tab->current_time.tv_sec =
4026 LTTV_TRACESET_CONTEXT(tab->traceset_info->traceset_context)->
4027 time_span.start_time.tv_sec;
4028 tab->current_time.tv_nsec =
4029 LTTV_TRACESET_CONTEXT(tab->traceset_info->traceset_context)->
4030 time_span.start_time.tv_nsec;
5723fa24 4031 }
e800cf84 4032#endif //0
6ced96ef 4033 tab->attributes = LTTV_IATTRIBUTE(g_object_new(LTTV_ATTRIBUTE_TYPE, NULL));
4034 tab->interrupted_state = g_object_new(LTTV_ATTRIBUTE_TYPE, NULL);
b052368a 4035
58f6c2a4 4036 tab->vbox = gtk_vbox_new(FALSE, 2);
e433e6d6 4037 tab->top_widget = tab->vbox;
4038 //g_object_set_data_full(G_OBJECT(tab->top_widget), "filter",
4039// filter, (GDestroyNotify)lttv_filter_destroy);
4040
4041// g_signal_connect (G_OBJECT(tab->top_widget),
4042// "notify",
4043// G_CALLBACK (on_top_notify),
4044// (gpointer)tab);
4045
58f6c2a4 4046 tab->viewer_container = gtk_vbox_new(TRUE, 2);
b052368a 4047 tab->scrollbar = gtk_hscrollbar_new(NULL);
4048 //tab->multivpaned = gtk_multi_vpaned_new();
6c35c853 4049
b052368a 4050 gtk_box_pack_start(GTK_BOX(tab->vbox),
4051 tab->viewer_container,
4052 TRUE, /* expand */
4053 TRUE, /* Give the extra space to the child */
4054 0); /* No padding */
4249a3e8 4055
4056// if(copy_tab) {
4057// tab->time_window = copy_tab->time_window;
4058// tab->current_time = copy_tab->current_time;
4059// }
e800cf84 4060
4061 /* Create the timebar */
4172f013
YB
4062
4063 tab->MTimebar = timebar_new();
e800cf84 4064
b052368a 4065 gtk_box_pack_end(GTK_BOX(tab->vbox),
4066 tab->scrollbar,
4067 FALSE, /* Do not expand */
4068 FALSE, /* Fill has no effect here (expand false) */
4069 0); /* No padding */
e800cf84 4070
4071 gtk_box_pack_end(GTK_BOX(tab->vbox),
4072 tab->MTimebar,
4073 FALSE, /* Do not expand */
4074 FALSE, /* Fill has no effect here (expand false) */
4075 0); /* No padding */
4076
b052368a 4077 g_object_set_data(G_OBJECT(tab->viewer_container), "focused_viewer", NULL);
4078
4079
6ced96ef 4080 tab->mw = mw;
27a559b9 4081
3c031040 4082 /*{
4083 // Display a label with a X
27a559b9 4084 GtkWidget *w_hbox = gtk_hbox_new(FALSE, 4);
4085 GtkWidget *w_label = gtk_label_new (label);
4086 GtkWidget *pixmap = create_pixmap(GTK_WIDGET(notebook), "close.png");
4087 GtkWidget *w_button = gtk_button_new ();
4088 gtk_container_add(GTK_CONTAINER(w_button), pixmap);
4089 //GtkWidget *w_button = gtk_button_new_with_label("x");
4090
4091 gtk_button_set_relief(GTK_BUTTON(w_button), GTK_RELIEF_NONE);
4092
4093 gtk_box_pack_start(GTK_BOX(w_hbox), w_label, TRUE, TRUE, 0);
4094 gtk_box_pack_end(GTK_BOX(w_hbox), w_button, FALSE,
4095 FALSE, 0);
a43d67ba 4096
27a559b9 4097 g_signal_connect_swapped (w_button, "clicked",
4098 G_CALLBACK (on_close_tab_X_clicked),
4099 tab->multi_vpaned);
5723fa24 4100
3c031040 4101 gtk_widget_set_state(w_button, GTK_STATE_ACTIVE);
4102
27a559b9 4103 gtk_widget_show (w_label);
4104 gtk_widget_show (pixmap);
4105 gtk_widget_show (w_button);
4106 gtk_widget_show (w_hbox);
4107
4108 tab->label = w_hbox;
3c031040 4109 }*/
4110
4111
4112 tab->label = gtk_label_new (label);
b052368a 4113
4114 gtk_widget_show(tab->label);
4115 gtk_widget_show(tab->scrollbar);
4172f013 4116 gtk_widget_show(tab->MTimebar);
b052368a 4117 gtk_widget_show(tab->viewer_container);
4118 gtk_widget_show(tab->vbox);
4172f013 4119
b052368a 4120 //gtk_widget_show(tab->multivpaned);
3c031040 4121
4122
501e4e70 4123 /* Start with empty events requests list */
6ced96ef 4124 tab->events_requests = NULL;
4125 tab->events_request_pending = FALSE;
5698740e 4126 tab->stop_foreground = FALSE;
4127
a43d67ba 4128
540edb40 4129
b052368a 4130 g_signal_connect(G_OBJECT(tab->scrollbar), "value-changed",
4131 G_CALLBACK(scroll_value_changed_cb), tab);
e800cf84 4132
4172f013
YB
4133
4134 /* Timebar signal handler */
4135 g_signal_connect(G_OBJECT(tab->MTimebar), "start-time-changed",
4136 G_CALLBACK(on_timebar_starttime_changed), tab);
4137 g_signal_connect(G_OBJECT(tab->MTimebar), "end-time-changed",
4138 G_CALLBACK(on_timebar_endtime_changed), tab);
4139 g_signal_connect(G_OBJECT(tab->MTimebar), "current-time-changed",
4140 G_CALLBACK(on_timebar_currenttime_changed), tab);
e800cf84 4141
b052368a 4142 //g_signal_connect(G_OBJECT(tab->scrollbar), "changed",
4143 // G_CALLBACK(scroll_value_changed_cb), tab);
4144
4145
784705cc 4146 //insert tab into notebook
6ced96ef 4147 gtk_notebook_append_page(notebook,
b052368a 4148 tab->vbox,
4149 tab->label);
5723fa24 4150 list = gtk_container_get_children(GTK_CONTAINER(notebook));
4151 gtk_notebook_set_current_page(notebook,g_list_length(list)-1);
a43d67ba 4152 // always show : not if(g_list_length(list)>1)
4153 gtk_notebook_set_show_tabs(notebook, TRUE);
4154
4249a3e8 4155 if(copy_tab) {
4156 lttvwindow_report_time_window(tab, copy_tab->time_window);
4157 lttvwindow_report_current_time(tab, copy_tab->current_time);
4158 } else {
4159 TimeWindow time_window;
4160
4161 time_window.start_time = ltt_time_zero;
4162 time_window.end_time = ltt_time_add(time_window.start_time,
4163 lttvwindow_default_time_width);
4164 time_window.time_width = lttvwindow_default_time_width;
4165 time_window.time_width_double = ltt_time_to_double(time_window.time_width);
4166
4167 lttvwindow_report_time_window(tab, time_window);
4168 lttvwindow_report_current_time(tab, ltt_time_zero);
4169 }
451aaf27 4170
4249a3e8 4171 LttvTraceset *traceset = tab->traceset_info->traceset;
4172 SetTraceset(tab, traceset);
a43d67ba 4173}
4174
501e4e70 4175/*
4176 * execute_events_requests
4177 *
4178 * Idle function that executes the pending requests for a tab.
4179 *
4180 * @return return value : TRUE : keep the idle function, FALSE : remove it.
4181 */
4182gboolean execute_events_requests(Tab *tab)
a43d67ba 4183{
501e4e70 4184 return ( lttvwindow_process_pending_requests(tab) );
a43d67ba 4185}
4186
8321ae6a 4187
451aaf27 4188__EXPORT void create_main_window_with_trace_list(GSList *traces)
8321ae6a 4189{
451aaf27 4190
8e3a7c75 4191 GSList *iter = NULL;
8321ae6a 4192
4193 /* Create window */
4194 MainWindow *mw = construct_main_window(NULL);
4195 GtkWidget *widget = mw->mwindow;
4196
4197 GtkWidget * notebook = lookup_widget(widget, "MNotebook");
4198 GtkWidget *page = gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook),
4199 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook)));
e433e6d6 4200 LttvPluginTab *ptab;
8321ae6a 4201 Tab *tab;
4202
4203 if(!page) {
e433e6d6 4204 ptab = create_new_tab(widget, NULL);
4205 tab = ptab->tab;
8321ae6a 4206 } else {
e433e6d6 4207 ptab = (LttvPluginTab *)g_object_get_data(G_OBJECT(page), "Tab_Plugin");
4208 tab = ptab->tab;
8321ae6a 4209 }
451aaf27
FD
4210
4211 LttvTraceset * traceset = lttv_traceset_new();
8e3a7c75 4212 for(iter=traces; iter!=NULL; iter=g_slist_next(iter)) {
4213 gchar *path = (gchar*)iter->data;
4214 /* Add trace */
4215 gchar abs_path[PATH_MAX];
8e3a7c75 4216
451aaf27 4217
8e3a7c75 4218 get_absolute_pathname(path, abs_path);
451aaf27
FD
4219
4220 if(lttv_traceset_add_path(traceset,abs_path) != 0 ){ /*failure*/
4221
4222 g_warning("cannot open trace %s", abs_path);
8e3a7c75 4223
4224 GtkWidget *dialogue =
4225 gtk_message_dialog_new(
4226 GTK_WINDOW(gtk_widget_get_toplevel(widget)),
4227 GTK_DIALOG_MODAL|GTK_DIALOG_DESTROY_WITH_PARENT,
4228 GTK_MESSAGE_ERROR,
4229 GTK_BUTTONS_OK,
0246f776 4230 "Cannot open trace : maybe you should enter in the directory "
8e3a7c75 4231 "to select it ?");
4232 gtk_dialog_run(GTK_DIALOG(dialogue));
4233 gtk_widget_destroy(dialogue);
8321ae6a 4234 }
451aaf27
FD
4235 else{
4236 SetTraceset(tab, traceset);
4237 }
4238 }
8321ae6a 4239}
4240
This page took 0.329643 seconds and 4 git commands to generate.