1 /* This file is part of the Linux Trace Toolkit viewer
2 * Copyright (C) 2003-2004 XangXiu Yang, Mathieu Desnoyers
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;
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.
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,
23 #include <limits.h> // for PATH_MAX
31 #include "callbacks.h"
32 #include "interface.h"
34 #include <ltt/trace.h>
35 #include <ltt/facility.h>
37 #include <ltt/event.h>
38 #include <lttv/lttv.h>
39 #include <lttv/module.h>
40 #include <lttv/iattribute.h>
41 #include <lttv/stats.h>
42 #include <lttv/filter.h>
43 #include <lttvwindow/mainwindow.h>
44 #include <lttvwindow/mainwindow-private.h>
45 #include <lttvwindow/menu.h>
46 #include <lttvwindow/toolbar.h>
47 #include <lttvwindow/lttvwindow.h>
48 #include <lttvwindow/lttvwindowtraces.h>
51 static LttTime lttvwindow_default_time_width
= { 1, 0 };
52 #define CLIP_BUF 256 // size of clipboard buffer
54 extern LttvTrace
*g_init_trace
;
57 /** Array containing instanced objects. */
58 extern GSList
* g_main_window_list
;
60 /** MD : keep old directory. */
61 static char remember_plugins_dir
[PATH_MAX
] = "";
62 static char remember_trace_dir
[PATH_MAX
] = "";
65 MainWindow
* get_window_data_struct(GtkWidget
* widget
);
66 char * get_load_module(MainWindow
*mw
,
67 char ** load_module_name
, int nb_module
);
68 char * get_unload_module(MainWindow
*mw
,
69 char ** loaded_module_name
, int nb_module
);
70 char * get_remove_trace(MainWindow
*mw
, char ** all_trace_name
, int nb_trace
);
71 char * get_selection(MainWindow
*mw
,
72 char ** all_name
, int nb
, char *title
, char * column_title
);
73 Tab
* create_tab(MainWindow
* mw
, Tab
*copy_tab
,
74 GtkNotebook
* notebook
, char * label
);
76 static void insert_viewer(GtkWidget
* widget
, lttvwindow_viewer_constructor constructor
);
78 Tab
*create_new_tab(GtkWidget
* widget
, gpointer user_data
);
80 static gboolean
lttvwindow_process_pending_requests(Tab
*tab
);
94 /* Pasting routines */
96 static void MEventBox1a_receive(GtkClipboard
*clipboard
,
100 if(text
== NULL
) return;
101 Tab
*tab
= (Tab
*)data
;
102 gchar buffer
[CLIP_BUF
];
103 gchar
*ptr
= buffer
, *ptr_ssec
, *ptr_snsec
, *ptr_esec
, *ptr_ensec
;
105 strncpy(buffer
, text
, CLIP_BUF
);
108 while(!isdigit(*ptr
) && ptr
< buffer
+CLIP_BUF
-1) ptr
++;
109 /* remove leading junk */
111 while(isdigit(*ptr
) && ptr
< buffer
+CLIP_BUF
-1) ptr
++;
112 /* read all the first number */
116 while(!isdigit(*ptr
) && ptr
< buffer
+CLIP_BUF
-1) ptr
++;
117 /* remove leading junk */
119 while(isdigit(*ptr
) && ptr
< buffer
+CLIP_BUF
-1) ptr
++;
120 /* read all the first number */
124 while(!isdigit(*ptr
) && ptr
< buffer
+CLIP_BUF
-1) ptr
++;
125 /* remove leading junk */
127 while(isdigit(*ptr
) && ptr
< buffer
+CLIP_BUF
-1) ptr
++;
128 /* read all the first number */
132 while(!isdigit(*ptr
) && ptr
< buffer
+CLIP_BUF
-1) ptr
++;
133 /* remove leading junk */
135 while(isdigit(*ptr
) && ptr
< buffer
+CLIP_BUF
-1) ptr
++;
136 /* read all the first number */
139 gtk_spin_button_set_value(GTK_SPIN_BUTTON(tab
->MEntry1
),
140 (double)strtoul(ptr_ssec
, NULL
, 10));
141 gtk_spin_button_set_value(GTK_SPIN_BUTTON(tab
->MEntry2
),
142 (double)strtoul(ptr_snsec
, NULL
, 10));
143 gtk_spin_button_set_value(GTK_SPIN_BUTTON(tab
->MEntry3
),
144 (double)strtoul(ptr_esec
, NULL
, 10));
145 gtk_spin_button_set_value(GTK_SPIN_BUTTON(tab
->MEntry4
),
146 (double)strtoul(ptr_ensec
, NULL
, 10));
149 static gboolean
on_MEventBox1a_paste(GtkWidget
*widget
, GdkEventButton
*event
,
152 Tab
*tab
= (Tab
*)data
;
154 GtkClipboard
*clip
= gtk_clipboard_get_for_display(gdk_display_get_default(),
155 GDK_SELECTION_PRIMARY
);
156 gtk_clipboard_request_text(clip
,
157 (GtkClipboardTextReceivedFunc
)MEventBox1a_receive
,
164 static void MEventBox1b_receive(GtkClipboard
*clipboard
,
168 if(text
== NULL
) return;
169 Tab
*tab
= (Tab
*)data
;
170 gchar buffer
[CLIP_BUF
];
171 gchar
*ptr
= buffer
, *ptr_sec
, *ptr_nsec
;
173 strncpy(buffer
, text
, CLIP_BUF
);
175 while(!isdigit(*ptr
) && ptr
< buffer
+CLIP_BUF
-1) ptr
++;
176 /* remove leading junk */
178 while(isdigit(*ptr
) && ptr
< buffer
+CLIP_BUF
-1) ptr
++;
179 /* read all the first number */
183 while(!isdigit(*ptr
) && ptr
< buffer
+CLIP_BUF
-1) ptr
++;
184 /* remove leading junk */
186 while(isdigit(*ptr
) && ptr
< buffer
+CLIP_BUF
-1) ptr
++;
187 /* read all the first number */
190 gtk_spin_button_set_value(GTK_SPIN_BUTTON(tab
->MEntry1
),
191 (double)strtoul(ptr_sec
, NULL
, 10));
192 gtk_spin_button_set_value(GTK_SPIN_BUTTON(tab
->MEntry2
),
193 (double)strtoul(ptr_nsec
, NULL
, 10));
197 static gboolean
on_MEventBox1b_paste(GtkWidget
*widget
, GdkEventButton
*event
,
200 Tab
*tab
= (Tab
*)data
;
202 GtkClipboard
*clip
= gtk_clipboard_get_for_display(gdk_display_get_default(),
203 GDK_SELECTION_PRIMARY
);
204 gtk_clipboard_request_text(clip
,
205 (GtkClipboardTextReceivedFunc
)MEventBox1b_receive
,
211 static void MEventBox3b_receive(GtkClipboard
*clipboard
,
215 if(text
== NULL
) return;
216 Tab
*tab
= (Tab
*)data
;
217 gchar buffer
[CLIP_BUF
];
218 gchar
*ptr
= buffer
, *ptr_sec
, *ptr_nsec
;
220 strncpy(buffer
, text
, CLIP_BUF
);
222 while(!isdigit(*ptr
) && ptr
< buffer
+CLIP_BUF
-1) ptr
++;
223 /* remove leading junk */
225 while(isdigit(*ptr
) && ptr
< buffer
+CLIP_BUF
-1) ptr
++;
226 /* read all the first number */
230 while(!isdigit(*ptr
) && ptr
< buffer
+CLIP_BUF
-1) ptr
++;
231 /* remove leading junk */
233 while(isdigit(*ptr
) && ptr
< buffer
+CLIP_BUF
-1) ptr
++;
234 /* read all the first number */
237 gtk_spin_button_set_value(GTK_SPIN_BUTTON(tab
->MEntry3
),
238 (double)strtoul(ptr_sec
, NULL
, 10));
239 gtk_spin_button_set_value(GTK_SPIN_BUTTON(tab
->MEntry4
),
240 (double)strtoul(ptr_nsec
, NULL
, 10));
244 static gboolean
on_MEventBox3b_paste(GtkWidget
*widget
, GdkEventButton
*event
,
247 Tab
*tab
= (Tab
*)data
;
249 GtkClipboard
*clip
= gtk_clipboard_get_for_display(gdk_display_get_default(),
250 GDK_SELECTION_PRIMARY
);
251 gtk_clipboard_request_text(clip
,
252 (GtkClipboardTextReceivedFunc
)MEventBox3b_receive
,
258 static void MEventBox5b_receive(GtkClipboard
*clipboard
,
262 if(text
== NULL
) return;
263 Tab
*tab
= (Tab
*)data
;
264 gchar buffer
[CLIP_BUF
];
265 gchar
*ptr
= buffer
, *ptr_sec
, *ptr_nsec
;
267 strncpy(buffer
, text
, CLIP_BUF
);
269 while(!isdigit(*ptr
) && ptr
< buffer
+CLIP_BUF
-1) ptr
++;
270 /* remove leading junk */
272 while(isdigit(*ptr
) && ptr
< buffer
+CLIP_BUF
-1) ptr
++;
273 /* read all the first number */
277 while(!isdigit(*ptr
) && ptr
< buffer
+CLIP_BUF
-1) ptr
++;
278 /* remove leading junk */
280 while(isdigit(*ptr
) && ptr
< buffer
+CLIP_BUF
-1) ptr
++;
281 /* read all the first number */
284 gtk_spin_button_set_value(GTK_SPIN_BUTTON(tab
->MEntry5
),
285 (double)strtoul(ptr_sec
, NULL
, 10));
286 gtk_spin_button_set_value(GTK_SPIN_BUTTON(tab
->MEntry6
),
287 (double)strtoul(ptr_nsec
, NULL
, 10));
291 static gboolean
on_MEventBox5b_paste(GtkWidget
*widget
, GdkEventButton
*event
,
294 Tab
*tab
= (Tab
*)data
;
296 GtkClipboard
*clip
= gtk_clipboard_get_for_display(gdk_display_get_default(),
297 GDK_SELECTION_PRIMARY
);
298 gtk_clipboard_request_text(clip
,
299 (GtkClipboardTextReceivedFunc
)MEventBox5b_receive
,
305 static gboolean
viewer_grab_focus(GtkWidget
*widget
, GdkEventButton
*event
,
308 GtkWidget
*viewer
= GTK_WIDGET(data
);
309 GtkWidget
*viewer_container
= gtk_widget_get_parent(viewer
);
311 g_debug("FOCUS GRABBED");
312 g_object_set_data(G_OBJECT(viewer_container
), "focused_viewer", viewer
);
317 static void connect_focus_recursive(GtkWidget
*widget
,
320 if(GTK_IS_CONTAINER(widget
)) {
321 gtk_container_forall(GTK_CONTAINER(widget
),
322 (GtkCallback
)connect_focus_recursive
,
326 if(GTK_IS_TREE_VIEW(widget
)) {
327 gtk_tree_view_set_headers_clickable(GTK_TREE_VIEW(widget
), TRUE
);
329 gtk_widget_add_events(widget
, GDK_BUTTON_PRESS_MASK
);
330 g_signal_connect (G_OBJECT(widget
),
331 "button-press-event",
332 G_CALLBACK (viewer_grab_focus
),
336 /* Stop all the processings and call gtk_main_quit() */
337 static void mainwindow_quit()
339 lttvwindowtraces_unregister_requests(g_quark_from_string("stats"));
340 lttvwindowtraces_unregister_requests(g_quark_from_string("state"));
341 lttvwindowtraces_unregister_computation_hooks(g_quark_from_string("stats"));
342 lttvwindowtraces_unregister_computation_hooks(g_quark_from_string("state"));
348 /* insert_viewer function constructs an instance of a viewer first,
349 * then inserts the widget of the instance into the container of the
354 insert_viewer_wrap(GtkWidget
*menuitem
, gpointer user_data
)
356 insert_viewer((GtkWidget
*)menuitem
, (lttvwindow_viewer_constructor
)user_data
);
360 /* internal functions */
361 void insert_viewer(GtkWidget
* widget
, lttvwindow_viewer_constructor constructor
)
363 GtkWidget
* viewer_container
;
364 MainWindow
* mw_data
= get_window_data_struct(widget
);
365 GtkWidget
* notebook
= lookup_widget(widget
, "MNotebook");
367 TimeInterval
* time_interval
;
368 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook
),
369 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
)));
373 tab
= create_new_tab(widget
, NULL
);
375 tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
378 viewer_container
= tab
->viewer_container
;
380 viewer
= (GtkWidget
*)constructor(tab
);
383 //gtk_multivpaned_widget_add(GTK_MULTIVPANED(multivpaned), viewer);
385 gtk_box_pack_end(GTK_BOX(viewer_container
),
391 /* We want to connect the viewer_grab_focus to EVERY
392 * child of this widget. The little trick is to get each child
393 * of each GTK_CONTAINER, even subchildren.
395 connect_focus_recursive(viewer
, viewer
);
400 * Function to set/update traceset for the viewers
401 * @param tab viewer's tab
402 * @param traceset traceset of the main window.
404 * 0 : traceset updated
405 * 1 : no traceset hooks to update; not an error.
408 int SetTraceset(Tab
* tab
, LttvTraceset
*traceset
)
410 LttvTracesetContext
*tsc
=
411 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
);
412 TimeInterval time_span
= tsc
->time_span
;
413 TimeWindow new_time_window
= tab
->time_window
;
414 LttTime new_current_time
= tab
->current_time
;
416 /* Set the tab's time window and current time if
418 if(ltt_time_compare(tab
->time_window
.start_time
, time_span
.start_time
) < 0
419 || ltt_time_compare(tab
->time_window
.end_time
,
420 time_span
.end_time
) > 0) {
421 new_time_window
.start_time
= time_span
.start_time
;
423 new_current_time
= time_span
.start_time
;
427 if(ltt_time_compare(lttvwindow_default_time_width
,
428 ltt_time_sub(time_span
.end_time
, time_span
.start_time
)) < 0
430 ltt_time_compare(time_span
.end_time
, time_span
.start_time
) == 0)
431 tmp_time
= lttvwindow_default_time_width
;
433 tmp_time
= time_span
.end_time
;
435 new_time_window
.time_width
= tmp_time
;
436 new_time_window
.time_width_double
= ltt_time_to_double(tmp_time
);
437 new_time_window
.end_time
= ltt_time_add(new_time_window
.start_time
,
438 new_time_window
.time_width
) ;
445 GtkAdjustment
*adjustment
= gtk_range_get_adjustment(GTK_RANGE(tab
->scrollbar
));
446 LttTime upper
= ltt_time_sub(time_span
.end_time
, time_span
.start_time
);
448 g_object_set(G_OBJECT(adjustment
),
452 ltt_time_to_double(upper
)
453 * NANOSECONDS_PER_SECOND
, /* upper */
455 ltt_time_to_double(tab
->time_window
.time_width
)
456 / SCROLL_STEP_PER_PAGE
457 * NANOSECONDS_PER_SECOND
, /* step increment */
459 ltt_time_to_double(tab
->time_window
.time_width
)
460 * NANOSECONDS_PER_SECOND
, /* page increment */
462 ltt_time_to_double(tab
->time_window
.time_width
)
463 * NANOSECONDS_PER_SECOND
, /* page size */
465 gtk_adjustment_changed(adjustment
);
467 g_object_set(G_OBJECT(adjustment
),
470 ltt_time_sub(tab
->time_window
.start_time
, time_span
.start_time
))
471 * NANOSECONDS_PER_SECOND
, /* value */
473 gtk_adjustment_value_changed(adjustment
);
475 /* set the time bar. The value callbacks will change their nsec themself */
477 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry1
),
478 (double)time_span
.start_time
.tv_sec
,
479 (double)time_span
.end_time
.tv_sec
);
482 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry3
),
483 (double)time_span
.start_time
.tv_sec
,
484 (double)time_span
.end_time
.tv_sec
);
486 /* current seconds */
487 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry5
),
488 (double)time_span
.start_time
.tv_sec
,
489 (double)time_span
.end_time
.tv_sec
);
492 /* Finally, call the update hooks of the viewers */
494 LttvAttributeValue value
;
498 g_assert( lttv_iattribute_find_by_path(tab
->attributes
,
499 "hooks/updatetraceset", LTTV_POINTER
, &value
));
501 tmp
= (LttvHooks
*)*(value
.v_pointer
);
502 if(tmp
== NULL
) retval
= 1;
503 else lttv_hooks_call(tmp
,traceset
);
505 time_change_manager(tab
, new_time_window
);
506 current_time_change_manager(tab
, new_current_time
);
512 * Function to set/update filter for the viewers
513 * @param tab viewer's tab
514 * @param filter filter of the main window.
517 * 0 : filters updated
518 * 1 : no filter hooks to update; not an error.
521 int SetFilter(Tab
* tab
, gpointer filter
)
524 LttvAttributeValue value
;
526 g_assert(lttv_iattribute_find_by_path(tab
->attributes
,
527 "hooks/updatefilter", LTTV_POINTER
, &value
));
529 tmp
= (LttvHooks
*)*(value
.v_pointer
);
531 if(tmp
== NULL
) return 1;
532 lttv_hooks_call(tmp
,filter
);
540 * Function to redraw each viewer belonging to the current tab
541 * @param tab viewer's tab
544 void update_traceset(Tab
*tab
)
546 LttvAttributeValue value
;
548 g_assert(lttv_iattribute_find_by_path(tab
->attributes
,
549 "hooks/updatetraceset", LTTV_POINTER
, &value
));
550 tmp
= (LttvHooks
*)*(value
.v_pointer
);
551 if(tmp
== NULL
) return;
552 lttv_hooks_call(tmp
, NULL
);
556 /* get_label function is used to get user input, it displays an input
557 * box, which allows user to input a string
560 void get_label_string (GtkWidget
* text
, gchar
* label
)
562 GtkEntry
* entry
= (GtkEntry
*)text
;
563 if(strlen(gtk_entry_get_text(entry
))!=0)
564 strcpy(label
,gtk_entry_get_text(entry
));
567 gboolean
get_label(MainWindow
* mw
, gchar
* str
, gchar
* dialogue_title
, gchar
* label_str
)
569 GtkWidget
* dialogue
;
574 dialogue
= gtk_dialog_new_with_buttons(dialogue_title
,NULL
,
576 GTK_STOCK_OK
,GTK_RESPONSE_ACCEPT
,
577 GTK_STOCK_CANCEL
,GTK_RESPONSE_REJECT
,
580 label
= gtk_label_new(label_str
);
581 gtk_widget_show(label
);
583 text
= gtk_entry_new();
584 gtk_widget_show(text
);
586 gtk_box_pack_start(GTK_BOX(GTK_DIALOG(dialogue
)->vbox
), label
,TRUE
, TRUE
,0);
587 gtk_box_pack_start(GTK_BOX(GTK_DIALOG(dialogue
)->vbox
), text
,FALSE
, FALSE
,0);
589 id
= gtk_dialog_run(GTK_DIALOG(dialogue
));
591 case GTK_RESPONSE_ACCEPT
:
592 get_label_string(text
,str
);
593 gtk_widget_destroy(dialogue
);
595 case GTK_RESPONSE_REJECT
:
597 gtk_widget_destroy(dialogue
);
604 /* get_window_data_struct function is actually a lookup function,
605 * given a widget which is in the tree of the main window, it will
606 * return the MainWindow data structure associated with main window
609 MainWindow
* get_window_data_struct(GtkWidget
* widget
)
612 MainWindow
* mw_data
;
614 mw
= lookup_widget(widget
, "MWindow");
616 g_info("Main window does not exist\n");
620 mw_data
= (MainWindow
*) g_object_get_data(G_OBJECT(mw
),"main_window_data");
622 g_warning("Main window data does not exist\n");
629 /* create_new_window function, just constructs a new main window
632 void create_new_window(GtkWidget
* widget
, gpointer user_data
, gboolean clone
)
634 MainWindow
* parent
= get_window_data_struct(widget
);
637 g_info("Clone : use the same traceset\n");
638 construct_main_window(parent
);
640 g_info("Empty : traceset is set to NULL\n");
641 construct_main_window(NULL
);
645 /* Get the currently focused viewer.
646 * If no viewer is focused, use the first one.
648 * If no viewer available, return NULL.
650 GtkWidget
*viewer_container_focus(GtkWidget
*container
)
654 widget
= (GtkWidget
*)g_object_get_data(G_OBJECT(container
),
658 g_debug("no widget focused");
659 GList
*children
= gtk_container_get_children(GTK_CONTAINER(container
));
662 widget
= GTK_WIDGET(children
->data
);
663 g_object_set_data(G_OBJECT(container
),
673 gint
viewer_container_position(GtkWidget
*container
, GtkWidget
*child
)
676 if(child
== NULL
) return -1;
680 memset(&value
, 0, sizeof(GValue
));
681 g_value_init(&value
, G_TYPE_INT
);
682 gtk_container_child_get_property(GTK_CONTAINER(container
),
686 pos
= g_value_get_int(&value
);
692 /* move_*_viewer functions move the selected view up/down in
696 void move_down_viewer(GtkWidget
* widget
, gpointer user_data
)
698 MainWindow
* mw
= get_window_data_struct(widget
);
699 GtkWidget
* notebook
= lookup_widget(widget
, "MNotebook");
701 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook
),
702 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
)));
708 tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
711 //gtk_multivpaned_widget_move_up(GTK_MULTIVPANED(tab->multivpaned));
713 /* change the position in the vbox */
714 GtkWidget
*focus_widget
;
716 focus_widget
= viewer_container_focus(tab
->viewer_container
);
717 position
= viewer_container_position(tab
->viewer_container
, focus_widget
);
720 /* can move up one position */
721 gtk_box_reorder_child(GTK_BOX(tab
->viewer_container
),
728 void move_up_viewer(GtkWidget
* widget
, gpointer user_data
)
730 MainWindow
* mw
= get_window_data_struct(widget
);
731 GtkWidget
* notebook
= lookup_widget(widget
, "MNotebook");
733 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook
),
734 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
)));
740 tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
743 //gtk_multivpaned_widget_move_down(GTK_MULTIVPANED(tab->multivpaned));
744 /* change the position in the vbox */
745 GtkWidget
*focus_widget
;
747 focus_widget
= viewer_container_focus(tab
->viewer_container
);
748 position
= viewer_container_position(tab
->viewer_container
, focus_widget
);
752 g_list_length(gtk_container_get_children(
753 GTK_CONTAINER(tab
->viewer_container
)))-1
755 /* can move down one position */
756 gtk_box_reorder_child(GTK_BOX(tab
->viewer_container
),
764 /* delete_viewer deletes the selected viewer in the current tab
767 void delete_viewer(GtkWidget
* widget
, gpointer user_data
)
769 MainWindow
* mw
= get_window_data_struct(widget
);
770 GtkWidget
* notebook
= lookup_widget(widget
, "MNotebook");
772 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook
),
773 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
)));
779 tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
782 //gtk_multivpaned_widget_delete(GTK_MULTIVPANED(tab->multivpaned));
784 GtkWidget
*focus_widget
= viewer_container_focus(tab
->viewer_container
);
786 if(focus_widget
!= NULL
)
787 gtk_widget_destroy(focus_widget
);
789 g_object_set_data(G_OBJECT(tab
->viewer_container
), "focused_viewer", NULL
);
793 /* open_traceset will open a traceset saved in a file
794 * Right now, it is not finished yet, (not working)
798 void open_traceset(GtkWidget
* widget
, gpointer user_data
)
802 LttvTraceset
* traceset
;
803 MainWindow
* mw_data
= get_window_data_struct(widget
);
804 GtkFileSelection
* file_selector
=
805 (GtkFileSelection
*)gtk_file_selection_new("Select a traceset");
807 gtk_file_selection_hide_fileop_buttons(file_selector
);
809 gtk_window_set_transient_for(GTK_WINDOW(file_selector
),
810 GTK_WINDOW(mw_data
->mwindow
));
812 id
= gtk_dialog_run(GTK_DIALOG(file_selector
));
814 case GTK_RESPONSE_ACCEPT
:
815 case GTK_RESPONSE_OK
:
816 dir
= gtk_file_selection_get_selections (file_selector
);
817 traceset
= lttv_traceset_load(dir
[0]);
818 g_info("Open a trace set %s\n", dir
[0]);
821 case GTK_RESPONSE_REJECT
:
822 case GTK_RESPONSE_CANCEL
:
824 gtk_widget_destroy((GtkWidget
*)file_selector
);
830 /* lttvwindow_process_pending_requests
832 * This internal function gets called by g_idle, taking care of the pending
833 * requests. It is responsible for concatenation of time intervals and position
834 * requests. It does it with the following algorithm organizing process traceset
835 * calls. Here is the detailed description of the way it works :
837 * - Events Requests Servicing Algorithm
839 * Data structures necessary :
841 * List of requests added to context : list_in
842 * List of requests not added to context : list_out
847 * list_out : many events requests
849 * FIXME : insert rest of algorithm here
853 #define list_out tab->events_requests
855 gboolean
lttvwindow_process_pending_requests(Tab
*tab
)
858 LttvTracesetContext
*tsc
;
859 LttvTracefileContext
*tfc
;
860 GSList
*list_in
= NULL
;
864 LttvTracesetContextPosition
*end_position
;
867 g_critical("Foreground processing : tab does not exist. Processing removed.");
871 /* There is no events requests pending : we should never have been called! */
872 g_assert(g_slist_length(list_out
) != 0);
874 tsc
= LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
);
876 //set the cursor to be X shape, indicating that the computer is busy in doing its job
878 new = gdk_cursor_new(GDK_X_CURSOR
);
879 widget
= lookup_widget(tab
->mw
->mwindow
, "MToolbar1");
880 win
= gtk_widget_get_parent_window(widget
);
881 gdk_window_set_cursor(win
, new);
882 gdk_cursor_unref(new);
883 gdk_window_stick(win
);
884 gdk_window_unstick(win
);
887 g_debug("SIZE events req len : %d", g_slist_length(list_out
));
889 /* Preliminary check for no trace in traceset */
890 /* Unregister the routine if empty, empty list_out too */
891 if(lttv_traceset_number(tsc
->ts
) == 0) {
893 /* - For each req in list_out */
894 GSList
*iter
= list_out
;
896 while(iter
!= NULL
) {
898 gboolean remove
= FALSE
;
899 gboolean free_data
= FALSE
;
900 EventsRequest
*events_request
= (EventsRequest
*)iter
->data
;
902 /* - Call end request for req */
903 if(events_request
->servicing
== TRUE
)
904 lttv_hooks_call(events_request
->after_request
, (gpointer
)tsc
);
906 /* - remove req from list_out */
907 /* Destroy the request */
914 GSList
*remove_iter
= iter
;
916 iter
= g_slist_next(iter
);
917 if(free_data
) events_request_free((EventsRequest
*)remove_iter
->data
);
918 list_out
= g_slist_remove_link(list_out
, remove_iter
);
919 } else { // not remove
920 iter
= g_slist_next(iter
);
925 /* 0.1 Lock Traces */
930 iter_trace
<lttv_traceset_number(tsc
->ts
);
932 LttvTrace
*trace_v
= lttv_traceset_get(tsc
->ts
, iter_trace
);
934 if(lttvwindowtraces_lock(trace_v
) != 0) {
935 g_critical("Foreground processing : Unable to get trace lock");
936 return TRUE
; /* Cannot get lock, try later */
941 /* 0.2 Seek tracefiles positions to context position */
942 //g_assert(lttv_process_traceset_seek_position(tsc, sync_position) == 0);
943 lttv_process_traceset_synchronize_tracefiles(tsc
);
946 /* Events processing algorithm implementation */
947 /* Warning : the gtk_events_pending takes a LOT of cpu time. So what we do
948 * instead is to leave the control to GTK and take it back.
950 /* A. Servicing loop */
951 //while( (g_slist_length(list_in) != 0 || g_slist_length(list_out) != 0)) {
952 if((g_slist_length(list_in
) != 0 || g_slist_length(list_out
) != 0)) {
954 /* 1. If list_in is empty (need a seek) */
955 if( g_slist_length(list_in
) == 0 ) {
957 /* list in is empty, need a seek */
959 /* 1.1 Add requests to list_in */
960 GSList
*ltime
= NULL
;
964 /* 1.1.1 Find all time requests with the lowest start time in list_out
967 if(g_slist_length(list_out
) > 0)
968 ltime
= g_slist_append(ltime
, g_slist_nth_data(list_out
, 0));
969 for(iter
=g_slist_nth(list_out
,1);iter
!=NULL
;iter
=g_slist_next(iter
)) {
970 /* Find all time requests with the lowest start time in list_out */
971 EventsRequest
*event_request_ltime
= (EventsRequest
*)g_slist_nth_data(ltime
, 0);
972 EventsRequest
*event_request_list_out
= (EventsRequest
*)iter
->data
;
975 comp
= ltt_time_compare(event_request_ltime
->start_time
,
976 event_request_list_out
->start_time
);
978 ltime
= g_slist_append(ltime
, event_request_list_out
);
980 /* Remove all elements from ltime, and add current */
982 ltime
= g_slist_delete_link(ltime
, g_slist_nth(ltime
, 0));
983 ltime
= g_slist_append(ltime
, event_request_list_out
);
987 /* 1.1.2 Find all position requests with the lowest position in list_out
990 if(g_slist_length(list_out
) > 0)
991 lpos
= g_slist_append(lpos
, g_slist_nth_data(list_out
, 0));
992 for(iter
=g_slist_nth(list_out
,1);iter
!=NULL
;iter
=g_slist_next(iter
)) {
993 /* Find all position requests with the lowest position in list_out */
994 EventsRequest
*event_request_lpos
= (EventsRequest
*)g_slist_nth_data(lpos
, 0);
995 EventsRequest
*event_request_list_out
= (EventsRequest
*)iter
->data
;
998 if(event_request_lpos
->start_position
!= NULL
999 && event_request_list_out
->start_position
!= NULL
)
1001 comp
= lttv_traceset_context_pos_pos_compare
1002 (event_request_lpos
->start_position
,
1003 event_request_list_out
->start_position
);
1008 lpos
= g_slist_append(lpos
, event_request_list_out
);
1010 /* Remove all elements from lpos, and add current */
1012 lpos
= g_slist_delete_link(lpos
, g_slist_nth(lpos
, 0));
1013 lpos
= g_slist_append(lpos
, event_request_list_out
);
1018 EventsRequest
*event_request_lpos
= (EventsRequest
*)g_slist_nth_data(lpos
, 0);
1019 EventsRequest
*event_request_ltime
= (EventsRequest
*)g_slist_nth_data(ltime
, 0);
1020 LttTime lpos_start_time
;
1022 if(event_request_lpos
!= NULL
1023 && event_request_lpos
->start_position
!= NULL
) {
1024 lpos_start_time
= lttv_traceset_context_position_get_time(
1025 event_request_lpos
->start_position
);
1028 /* 1.1.3 If lpos.start time < ltime */
1029 if(event_request_lpos
!= NULL
1030 && event_request_lpos
->start_position
!= NULL
1031 && ltt_time_compare(lpos_start_time
,
1032 event_request_ltime
->start_time
)<0) {
1033 /* Add lpos to list_in, remove them from list_out */
1034 for(iter
=lpos
;iter
!=NULL
;iter
=g_slist_next(iter
)) {
1035 /* Add to list_in */
1036 EventsRequest
*event_request_lpos
=
1037 (EventsRequest
*)iter
->data
;
1039 list_in
= g_slist_append(list_in
, event_request_lpos
);
1040 /* Remove from list_out */
1041 list_out
= g_slist_remove(list_out
, event_request_lpos
);
1044 /* 1.1.4 (lpos.start time >= ltime) */
1045 /* Add ltime to list_in, remove them from list_out */
1047 for(iter
=ltime
;iter
!=NULL
;iter
=g_slist_next(iter
)) {
1048 /* Add to list_in */
1049 EventsRequest
*event_request_ltime
=
1050 (EventsRequest
*)iter
->data
;
1052 list_in
= g_slist_append(list_in
, event_request_ltime
);
1053 /* Remove from list_out */
1054 list_out
= g_slist_remove(list_out
, event_request_ltime
);
1059 g_slist_free(ltime
);
1064 tfc
= lttv_traceset_context_get_current_tfc(tsc
);
1065 g_assert(g_slist_length(list_in
)>0);
1066 EventsRequest
*events_request
= g_slist_nth_data(list_in
, 0);
1069 /* 1.2.1 If first request in list_in is a time request */
1070 if(events_request
->start_position
== NULL
) {
1071 /* - If first req in list_in start time != current time */
1072 if(tfc
== NULL
|| ltt_time_compare(events_request
->start_time
,
1073 tfc
->timestamp
) != 0)
1074 /* - Seek to that time */
1075 g_debug("SEEK TIME : %lu, %lu", events_request
->start_time
.tv_sec
,
1076 events_request
->start_time
.tv_nsec
);
1077 //lttv_process_traceset_seek_time(tsc, events_request->start_time);
1078 lttv_state_traceset_seek_time_closest(LTTV_TRACESET_STATE(tsc
),
1079 events_request
->start_time
);
1081 /* Process the traceset with only state hooks */
1083 lttv_process_traceset_middle(tsc
,
1084 events_request
->start_time
,
1087 g_assert(seek_count
< LTTV_STATE_SAVE_INTERVAL
);
1093 /* Else, the first request in list_in is a position request */
1094 /* If first req in list_in pos != current pos */
1095 g_assert(events_request
->start_position
!= NULL
);
1096 g_debug("SEEK POS time : %lu, %lu",
1097 lttv_traceset_context_position_get_time(
1098 events_request
->start_position
).tv_sec
,
1099 lttv_traceset_context_position_get_time(
1100 events_request
->start_position
).tv_nsec
);
1102 g_debug("SEEK POS context time : %lu, %lu",
1103 lttv_traceset_context_get_current_tfc(tsc
)->timestamp
.tv_sec
,
1104 lttv_traceset_context_get_current_tfc(tsc
)->timestamp
.tv_nsec
);
1105 g_assert(events_request
->start_position
!= NULL
);
1106 if(lttv_traceset_context_ctx_pos_compare(tsc
,
1107 events_request
->start_position
) != 0) {
1108 /* 1.2.2.1 Seek to that position */
1109 g_debug("SEEK POSITION");
1110 //lttv_process_traceset_seek_position(tsc, events_request->start_position);
1111 pos_time
= lttv_traceset_context_position_get_time(
1112 events_request
->start_position
);
1114 lttv_state_traceset_seek_time_closest(LTTV_TRACESET_STATE(tsc
),
1117 /* Process the traceset with only state hooks */
1119 lttv_process_traceset_middle(tsc
,
1122 events_request
->start_position
);
1123 g_assert(lttv_traceset_context_ctx_pos_compare(tsc
,
1124 events_request
->start_position
) == 0);
1131 /* 1.3 Add hooks and call before request for all list_in members */
1133 GSList
*iter
= NULL
;
1135 for(iter
=list_in
;iter
!=NULL
;iter
=g_slist_next(iter
)) {
1136 EventsRequest
*events_request
= (EventsRequest
*)iter
->data
;
1137 /* 1.3.1 If !servicing */
1138 if(events_request
->servicing
== FALSE
) {
1139 /* - begin request hooks called
1140 * - servicing = TRUE
1142 lttv_hooks_call(events_request
->before_request
, (gpointer
)tsc
);
1143 events_request
->servicing
= TRUE
;
1145 /* 1.3.2 call before chunk
1146 * 1.3.3 events hooks added
1148 if(events_request
->trace
== -1)
1149 lttv_process_traceset_begin(tsc
,
1150 events_request
->before_chunk_traceset
,
1151 events_request
->before_chunk_trace
,
1152 events_request
->before_chunk_tracefile
,
1153 events_request
->event
,
1154 events_request
->event_by_id
);
1156 guint nb_trace
= lttv_traceset_number(tsc
->ts
);
1157 g_assert((guint
)events_request
->trace
< nb_trace
&&
1158 events_request
->trace
> -1);
1159 LttvTraceContext
*tc
= tsc
->traces
[events_request
->trace
];
1161 lttv_hooks_call(events_request
->before_chunk_traceset
, tsc
);
1163 lttv_trace_context_add_hooks(tc
,
1164 events_request
->before_chunk_trace
,
1165 events_request
->before_chunk_tracefile
,
1166 events_request
->event
,
1167 events_request
->event_by_id
);
1172 /* 2. Else, list_in is not empty, we continue a read */
1175 /* 2.0 For each req of list_in */
1176 GSList
*iter
= list_in
;
1178 while(iter
!= NULL
) {
1180 EventsRequest
*events_request
= (EventsRequest
*)iter
->data
;
1182 /* - Call before chunk
1183 * - events hooks added
1185 if(events_request
->trace
== -1)
1186 lttv_process_traceset_begin(tsc
,
1187 events_request
->before_chunk_traceset
,
1188 events_request
->before_chunk_trace
,
1189 events_request
->before_chunk_tracefile
,
1190 events_request
->event
,
1191 events_request
->event_by_id
);
1193 guint nb_trace
= lttv_traceset_number(tsc
->ts
);
1194 g_assert((guint
)events_request
->trace
< nb_trace
&&
1195 events_request
->trace
> -1);
1196 LttvTraceContext
*tc
= tsc
->traces
[events_request
->trace
];
1198 lttv_hooks_call(events_request
->before_chunk_traceset
, tsc
);
1200 lttv_trace_context_add_hooks(tc
,
1201 events_request
->before_chunk_trace
,
1202 events_request
->before_chunk_tracefile
,
1203 events_request
->event
,
1204 events_request
->event_by_id
);
1207 iter
= g_slist_next(iter
);
1212 tfc
= lttv_traceset_context_get_current_tfc(tsc
);
1214 /* 2.1 For each req of list_out */
1215 GSList
*iter
= list_out
;
1217 while(iter
!= NULL
) {
1219 gboolean remove
= FALSE
;
1220 gboolean free_data
= FALSE
;
1221 EventsRequest
*events_request
= (EventsRequest
*)iter
->data
;
1223 /* if req.start time == current context time
1224 * or req.start position == current position*/
1225 if( ltt_time_compare(events_request
->start_time
,
1226 tfc
->timestamp
) == 0
1228 (events_request
->start_position
!= NULL
1230 lttv_traceset_context_ctx_pos_compare(tsc
,
1231 events_request
->start_position
) == 0)
1233 /* - Add to list_in, remove from list_out */
1234 list_in
= g_slist_append(list_in
, events_request
);
1238 /* - If !servicing */
1239 if(events_request
->servicing
== FALSE
) {
1240 /* - begin request hooks called
1241 * - servicing = TRUE
1243 lttv_hooks_call(events_request
->before_request
, (gpointer
)tsc
);
1244 events_request
->servicing
= TRUE
;
1246 /* call before chunk
1247 * events hooks added
1249 if(events_request
->trace
== -1)
1250 lttv_process_traceset_begin(tsc
,
1251 events_request
->before_chunk_traceset
,
1252 events_request
->before_chunk_trace
,
1253 events_request
->before_chunk_tracefile
,
1254 events_request
->event
,
1255 events_request
->event_by_id
);
1257 guint nb_trace
= lttv_traceset_number(tsc
->ts
);
1258 g_assert((guint
)events_request
->trace
< nb_trace
&&
1259 events_request
->trace
> -1);
1260 LttvTraceContext
*tc
= tsc
->traces
[events_request
->trace
];
1262 lttv_hooks_call(events_request
->before_chunk_traceset
, tsc
);
1264 lttv_trace_context_add_hooks(tc
,
1265 events_request
->before_chunk_trace
,
1266 events_request
->before_chunk_tracefile
,
1267 events_request
->event
,
1268 events_request
->event_by_id
);
1277 GSList
*remove_iter
= iter
;
1279 iter
= g_slist_next(iter
);
1280 if(free_data
) events_request_free((EventsRequest
*)remove_iter
->data
);
1281 list_out
= g_slist_remove_link(list_out
, remove_iter
);
1282 } else { // not remove
1283 iter
= g_slist_next(iter
);
1289 /* 3. Find end criterions */
1294 /* 3.1.1 Find lowest end time in list_in */
1295 g_assert(g_slist_length(list_in
)>0);
1296 end_time
= ((EventsRequest
*)g_slist_nth_data(list_in
,0))->end_time
;
1298 for(iter
=g_slist_nth(list_in
,1);iter
!=NULL
;iter
=g_slist_next(iter
)) {
1299 EventsRequest
*events_request
= (EventsRequest
*)iter
->data
;
1301 if(ltt_time_compare(events_request
->end_time
,
1303 end_time
= events_request
->end_time
;
1306 /* 3.1.2 Find lowest start time in list_out */
1307 for(iter
=list_out
;iter
!=NULL
;iter
=g_slist_next(iter
)) {
1308 EventsRequest
*events_request
= (EventsRequest
*)iter
->data
;
1310 if(ltt_time_compare(events_request
->start_time
,
1312 end_time
= events_request
->start_time
;
1317 /* 3.2 Number of events */
1319 /* 3.2.1 Find lowest number of events in list_in */
1322 end_nb_events
= ((EventsRequest
*)g_slist_nth_data(list_in
,0))->num_events
;
1324 for(iter
=g_slist_nth(list_in
,1);iter
!=NULL
;iter
=g_slist_next(iter
)) {
1325 EventsRequest
*events_request
= (EventsRequest
*)iter
->data
;
1327 if(events_request
->num_events
< end_nb_events
)
1328 end_nb_events
= events_request
->num_events
;
1331 /* 3.2.2 Use min(CHUNK_NUM_EVENTS, min num events in list_in) as
1334 end_nb_events
= MIN(CHUNK_NUM_EVENTS
, end_nb_events
);
1338 /* 3.3 End position */
1340 /* 3.3.1 Find lowest end position in list_in */
1343 end_position
=((EventsRequest
*)g_slist_nth_data(list_in
,0))->end_position
;
1345 for(iter
=g_slist_nth(list_in
,1);iter
!=NULL
;iter
=g_slist_next(iter
)) {
1346 EventsRequest
*events_request
= (EventsRequest
*)iter
->data
;
1348 if(events_request
->end_position
!= NULL
&& end_position
!= NULL
&&
1349 lttv_traceset_context_pos_pos_compare(events_request
->end_position
,
1351 end_position
= events_request
->end_position
;
1356 /* 3.3.2 Find lowest start position in list_out */
1359 for(iter
=list_out
;iter
!=NULL
;iter
=g_slist_next(iter
)) {
1360 EventsRequest
*events_request
= (EventsRequest
*)iter
->data
;
1362 if(events_request
->end_position
!= NULL
&& end_position
!= NULL
&&
1363 lttv_traceset_context_pos_pos_compare(events_request
->end_position
,
1365 end_position
= events_request
->end_position
;
1370 /* 4. Call process traceset middle */
1371 g_debug("Calling process traceset middle with %p, %lu sec %lu nsec, %u nb ev, %p end pos", tsc
, end_time
.tv_sec
, end_time
.tv_nsec
, end_nb_events
, end_position
);
1372 count
= lttv_process_traceset_middle(tsc
, end_time
, end_nb_events
, end_position
);
1374 tfc
= lttv_traceset_context_get_current_tfc(tsc
);
1376 g_debug("Context time after middle : %lu, %lu", tfc
->timestamp
.tv_sec
,
1377 tfc
->timestamp
.tv_nsec
);
1379 g_debug("End of trace reached after middle.");
1383 /* 5. After process traceset middle */
1384 tfc
= lttv_traceset_context_get_current_tfc(tsc
);
1386 /* - if current context time > traceset.end time */
1387 if(tfc
== NULL
|| ltt_time_compare(tfc
->timestamp
,
1388 tsc
->time_span
.end_time
) > 0) {
1389 /* - For each req in list_in */
1390 GSList
*iter
= list_in
;
1392 while(iter
!= NULL
) {
1394 gboolean remove
= FALSE
;
1395 gboolean free_data
= FALSE
;
1396 EventsRequest
*events_request
= (EventsRequest
*)iter
->data
;
1398 /* - Remove events hooks for req
1399 * - Call end chunk for req
1402 if(events_request
->trace
== -1)
1403 lttv_process_traceset_end(tsc
,
1404 events_request
->after_chunk_traceset
,
1405 events_request
->after_chunk_trace
,
1406 events_request
->after_chunk_tracefile
,
1407 events_request
->event
,
1408 events_request
->event_by_id
);
1411 guint nb_trace
= lttv_traceset_number(tsc
->ts
);
1412 g_assert(events_request
->trace
< nb_trace
&&
1413 events_request
->trace
> -1);
1414 LttvTraceContext
*tc
= tsc
->traces
[events_request
->trace
];
1416 lttv_trace_context_remove_hooks(tc
,
1417 events_request
->after_chunk_trace
,
1418 events_request
->after_chunk_tracefile
,
1419 events_request
->event
,
1420 events_request
->event_by_id
);
1421 lttv_hooks_call(events_request
->after_chunk_traceset
, tsc
);
1426 /* - Call end request for req */
1427 lttv_hooks_call(events_request
->after_request
, (gpointer
)tsc
);
1429 /* - remove req from list_in */
1430 /* Destroy the request */
1437 GSList
*remove_iter
= iter
;
1439 iter
= g_slist_next(iter
);
1440 if(free_data
) events_request_free((EventsRequest
*)remove_iter
->data
);
1441 list_in
= g_slist_remove_link(list_in
, remove_iter
);
1442 } else { // not remove
1443 iter
= g_slist_next(iter
);
1448 /* 5.1 For each req in list_in */
1449 GSList
*iter
= list_in
;
1451 while(iter
!= NULL
) {
1453 gboolean remove
= FALSE
;
1454 gboolean free_data
= FALSE
;
1455 EventsRequest
*events_request
= (EventsRequest
*)iter
->data
;
1457 /* - Remove events hooks for req
1458 * - Call end chunk for req
1460 if(events_request
->trace
== -1)
1461 lttv_process_traceset_end(tsc
,
1462 events_request
->after_chunk_traceset
,
1463 events_request
->after_chunk_trace
,
1464 events_request
->after_chunk_tracefile
,
1465 events_request
->event
,
1466 events_request
->event_by_id
);
1469 guint nb_trace
= lttv_traceset_number(tsc
->ts
);
1470 g_assert(events_request
->trace
< nb_trace
&&
1471 events_request
->trace
> -1);
1472 LttvTraceContext
*tc
= tsc
->traces
[events_request
->trace
];
1474 lttv_trace_context_remove_hooks(tc
,
1475 events_request
->after_chunk_trace
,
1476 events_request
->after_chunk_tracefile
,
1477 events_request
->event
,
1478 events_request
->event_by_id
);
1480 lttv_hooks_call(events_request
->after_chunk_traceset
, tsc
);
1483 /* - req.num -= count */
1484 g_assert(events_request
->num_events
>= count
);
1485 events_request
->num_events
-= count
;
1487 g_assert(tfc
!= NULL
);
1488 /* - if req.num == 0
1490 * current context time >= req.end time
1492 * req.end pos == current pos
1494 * req.stop_flag == TRUE
1496 if( events_request
->num_events
== 0
1498 events_request
->stop_flag
== TRUE
1500 ltt_time_compare(tfc
->timestamp
,
1501 events_request
->end_time
) >= 0
1503 (events_request
->end_position
!= NULL
1505 lttv_traceset_context_ctx_pos_compare(tsc
,
1506 events_request
->end_position
) == 0)
1509 g_assert(events_request
->servicing
== TRUE
);
1510 /* - Call end request for req
1511 * - remove req from list_in */
1512 lttv_hooks_call(events_request
->after_request
, (gpointer
)tsc
);
1513 /* - remove req from list_in */
1514 /* Destroy the request */
1522 GSList
*remove_iter
= iter
;
1524 iter
= g_slist_next(iter
);
1525 if(free_data
) events_request_free((EventsRequest
*)remove_iter
->data
);
1526 list_in
= g_slist_remove_link(list_in
, remove_iter
);
1527 } else { // not remove
1528 iter
= g_slist_next(iter
);
1534 /* End of removed servicing loop : leave control to GTK instead. */
1535 // if(gtk_events_pending()) break;
1538 /* B. When interrupted between chunks */
1541 GSList
*iter
= list_in
;
1543 /* 1. for each request in list_in */
1544 while(iter
!= NULL
) {
1546 gboolean remove
= FALSE
;
1547 gboolean free_data
= FALSE
;
1548 EventsRequest
*events_request
= (EventsRequest
*)iter
->data
;
1550 /* 1.1. Use current postition as start position */
1551 if(events_request
->start_position
!= NULL
)
1552 lttv_traceset_context_position_destroy(events_request
->start_position
);
1553 events_request
->start_position
= lttv_traceset_context_position_new(tsc
);
1554 lttv_traceset_context_position_save(tsc
, events_request
->start_position
);
1556 /* 1.2. Remove start time */
1557 events_request
->start_time
= ltt_time_infinite
;
1559 /* 1.3. Move from list_in to list_out */
1562 list_out
= g_slist_append(list_out
, events_request
);
1567 GSList
*remove_iter
= iter
;
1569 iter
= g_slist_next(iter
);
1570 if(free_data
) events_request_free((EventsRequest
*)remove_iter
->data
);
1571 list_in
= g_slist_remove_link(list_in
, remove_iter
);
1572 } else { // not remove
1573 iter
= g_slist_next(iter
);
1579 /* C Unlock Traces */
1581 lttv_process_traceset_get_sync_data(tsc
);
1582 //lttv_traceset_context_position_save(tsc, sync_position);
1587 iter_trace
<lttv_traceset_number(tsc
->ts
);
1589 LttvTrace
*trace_v
= lttv_traceset_get(tsc
->ts
, iter_trace
);
1591 lttvwindowtraces_unlock(trace_v
);
1595 //set the cursor back to normal
1596 gdk_window_set_cursor(win
, NULL
);
1599 g_assert(g_slist_length(list_in
) == 0);
1601 if( g_slist_length(list_out
) == 0 ) {
1602 /* Put tab's request pending flag back to normal */
1603 tab
->events_request_pending
= FALSE
;
1604 g_debug("remove the idle fct");
1605 return FALSE
; /* Remove the idle function */
1607 g_debug("leave the idle fct");
1608 return TRUE
; /* Leave the idle function */
1610 /* We do not use simili-round-robin, it may require to read 1 meg buffers
1611 * again and again if many tracesets use the same tracefiles. */
1612 /* Hack for round-robin idle functions */
1613 /* It will put the idle function at the end of the pool */
1614 /*g_idle_add_full((G_PRIORITY_HIGH_IDLE + 21),
1615 (GSourceFunc)execute_events_requests,
1625 static void lttvwindow_add_trace(Tab
*tab
, LttvTrace
*trace_v
)
1627 LttvTraceset
*traceset
= tab
->traceset_info
->traceset
;
1629 guint num_traces
= lttv_traceset_number(traceset
);
1631 //Verify if trace is already present.
1632 for(i
=0; i
<num_traces
; i
++)
1634 LttvTrace
* trace
= lttv_traceset_get(traceset
, i
);
1635 if(trace
== trace_v
)
1639 //Keep a reference to the traces so they are not freed.
1640 for(i
=0; i
<lttv_traceset_number(traceset
); i
++)
1642 LttvTrace
* trace
= lttv_traceset_get(traceset
, i
);
1643 lttv_trace_ref(trace
);
1646 //remove state update hooks
1647 lttv_state_remove_event_hooks(
1648 (LttvTracesetState
*)tab
->traceset_info
->traceset_context
);
1650 lttv_context_fini(LTTV_TRACESET_CONTEXT(
1651 tab
->traceset_info
->traceset_context
));
1652 g_object_unref(tab
->traceset_info
->traceset_context
);
1654 lttv_traceset_add(traceset
, trace_v
);
1655 lttv_trace_ref(trace_v
); /* local ref */
1657 /* Create new context */
1658 tab
->traceset_info
->traceset_context
=
1659 g_object_new(LTTV_TRACESET_STATS_TYPE
, NULL
);
1661 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->
1666 //add state update hooks
1667 lttv_state_add_event_hooks(
1668 (LttvTracesetState
*)tab
->traceset_info
->traceset_context
);
1669 //Remove local reference to the traces.
1670 for(i
=0; i
<lttv_traceset_number(traceset
); i
++)
1672 LttvTrace
* trace
= lttv_traceset_get(traceset
, i
);
1673 lttv_trace_unref(trace
);
1677 //add_trace_into_traceset_selector(GTK_MULTIVPANED(tab->multivpaned), lttv_trace(trace_v));
1680 /* add_trace adds a trace into the current traceset. It first displays a
1681 * directory selection dialogue to let user choose a trace, then recreates
1682 * tracset_context, and redraws all the viewer of the current tab
1685 void add_trace(GtkWidget
* widget
, gpointer user_data
)
1688 LttvTrace
* trace_v
;
1689 LttvTraceset
* traceset
;
1691 char abs_path
[PATH_MAX
];
1693 MainWindow
* mw_data
= get_window_data_struct(widget
);
1694 GtkWidget
* notebook
= lookup_widget(widget
, "MNotebook");
1696 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook
),
1697 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
)));
1701 tab
= create_new_tab(widget
, NULL
);
1703 tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
1706 //GtkDirSelection * file_selector = (GtkDirSelection *)gtk_dir_selection_new("Select a trace");
1707 GtkFileSelection
* file_selector
= (GtkFileSelection
*)gtk_file_selection_new("Select a trace");
1708 gtk_widget_hide( (file_selector
)->file_list
->parent
) ;
1709 gtk_file_selection_hide_fileop_buttons(file_selector
);
1710 gtk_window_set_transient_for(GTK_WINDOW(file_selector
),
1711 GTK_WINDOW(mw_data
->mwindow
));
1713 if(remember_trace_dir
[0] != '\0')
1714 gtk_file_selection_set_filename(file_selector
, remember_trace_dir
);
1716 id
= gtk_dialog_run(GTK_DIALOG(file_selector
));
1718 case GTK_RESPONSE_ACCEPT
:
1719 case GTK_RESPONSE_OK
:
1720 dir
= gtk_file_selection_get_filename (file_selector
);
1721 strncpy(remember_trace_dir
, dir
, PATH_MAX
);
1722 strncat(remember_trace_dir
, "/", PATH_MAX
);
1723 if(!dir
|| strlen(dir
) == 0){
1724 gtk_widget_destroy((GtkWidget
*)file_selector
);
1727 get_absolute_pathname(dir
, abs_path
);
1728 trace_v
= lttvwindowtraces_get_trace_by_name(abs_path
);
1729 if(trace_v
== NULL
) {
1730 trace
= ltt_trace_open(abs_path
);
1732 g_warning("cannot open trace %s", abs_path
);
1734 GtkWidget
*dialogue
=
1735 gtk_message_dialog_new(
1736 GTK_WINDOW(gtk_widget_get_toplevel(widget
)),
1737 GTK_DIALOG_MODAL
|GTK_DIALOG_DESTROY_WITH_PARENT
,
1740 "Cannot open trace : maybe you should enter in the trace"
1741 "directory to select it ?");
1742 gtk_dialog_run(GTK_DIALOG(dialogue
));
1743 gtk_widget_destroy(dialogue
);
1746 trace_v
= lttv_trace_new(trace
);
1747 lttvwindowtraces_add_trace(trace_v
);
1748 lttvwindow_add_trace(tab
, trace_v
);
1751 lttvwindow_add_trace(tab
, trace_v
);
1754 gtk_widget_destroy((GtkWidget
*)file_selector
);
1756 //update current tab
1757 //update_traceset(mw_data);
1759 /* Call the updatetraceset hooks */
1761 traceset
= tab
->traceset_info
->traceset
;
1762 SetTraceset(tab
, traceset
);
1763 // in expose now call_pending_read_hooks(mw_data);
1765 //lttvwindow_report_current_time(mw_data,&(tab->current_time));
1767 case GTK_RESPONSE_REJECT
:
1768 case GTK_RESPONSE_CANCEL
:
1770 gtk_widget_destroy((GtkWidget
*)file_selector
);
1775 /* remove_trace removes a trace from the current traceset if all viewers in
1776 * the current tab are not interested in the trace. It first displays a
1777 * dialogue, which shows all traces in the current traceset, to let user choose
1778 * a trace, then it checks if all viewers unselect the trace, if it is true,
1779 * it will remove the trace, recreate the traceset_contex,
1780 * and redraws all the viewer of the current tab. If there is on trace in the
1781 * current traceset, it will delete all viewers of the current tab
1783 * It destroys the filter tree. FIXME... we should request for an update
1787 void remove_trace(GtkWidget
*widget
, gpointer user_data
)
1790 LttvTrace
* trace_v
;
1791 LttvTraceset
* traceset
;
1792 gint i
, j
, nb_trace
, index
=-1;
1793 char ** name
, *remove_trace_name
;
1794 MainWindow
* mw_data
= get_window_data_struct(widget
);
1795 GtkWidget
* notebook
= lookup_widget(widget
, "MNotebook");
1797 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook
),
1798 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
)));
1804 tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
1807 nb_trace
=lttv_traceset_number(tab
->traceset_info
->traceset
);
1808 name
= g_new(char*,nb_trace
);
1809 for(i
= 0; i
< nb_trace
; i
++){
1810 trace_v
= lttv_traceset_get(tab
->traceset_info
->traceset
, i
);
1811 trace
= lttv_trace(trace_v
);
1812 name
[i
] = g_quark_to_string(ltt_trace_name(trace
));
1815 remove_trace_name
= get_remove_trace(mw_data
, name
, nb_trace
);
1818 if(remove_trace_name
){
1820 /* yuk, cut n paste from old code.. should be better (MD)*/
1821 for(i
= 0; i
<nb_trace
; i
++) {
1822 if(strcmp(remove_trace_name
,name
[i
]) == 0){
1827 traceset
= tab
->traceset_info
->traceset
;
1828 //Keep a reference to the traces so they are not freed.
1829 for(j
=0; j
<lttv_traceset_number(traceset
); j
++)
1831 LttvTrace
* trace
= lttv_traceset_get(traceset
, j
);
1832 lttv_trace_ref(trace
);
1835 //remove state update hooks
1836 lttv_state_remove_event_hooks(
1837 (LttvTracesetState
*)tab
->traceset_info
->traceset_context
);
1838 lttv_context_fini(LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
));
1839 g_object_unref(tab
->traceset_info
->traceset_context
);
1841 trace_v
= lttv_traceset_get(traceset
, index
);
1843 lttv_traceset_remove(traceset
, index
);
1844 lttv_trace_unref(trace_v
); // Remove local reference
1846 if(lttv_trace_get_ref_number(trace_v
) <= 1) {
1847 /* ref 1 : lttvwindowtraces only*/
1848 ltt_trace_close(lttv_trace(trace_v
));
1849 /* lttvwindowtraces_remove_trace takes care of destroying
1850 * the traceset linked with the trace_v and also of destroying
1851 * the trace_v at the same time.
1853 lttvwindowtraces_remove_trace(trace_v
);
1856 tab
->traceset_info
->traceset_context
=
1857 g_object_new(LTTV_TRACESET_STATS_TYPE
, NULL
);
1859 LTTV_TRACESET_CONTEXT(tab
->
1860 traceset_info
->traceset_context
),traceset
);
1861 //add state update hooks
1862 lttv_state_add_event_hooks(
1863 (LttvTracesetState
*)tab
->traceset_info
->traceset_context
);
1865 //Remove local reference to the traces.
1866 for(j
=0; j
<lttv_traceset_number(traceset
); j
++)
1868 LttvTrace
* trace
= lttv_traceset_get(traceset
, j
);
1869 lttv_trace_unref(trace
);
1872 SetTraceset(tab
, (gpointer
)traceset
);
1878 void remove_trace(GtkWidget
* widget
, gpointer user_data
)
1881 LttvTrace
* trace_v
;
1882 LttvTraceset
* traceset
;
1883 gint i
, j
, nb_trace
;
1884 char ** name
, *remove_trace_name
;
1885 MainWindow
* mw_data
= get_window_data_struct(widget
);
1886 LttvTracesetSelector
* s
;
1887 LttvTraceSelector
* t
;
1890 GtkWidget
* notebook
= lookup_widget(widget
, "MNotebook");
1892 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook
),
1893 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
)));
1899 tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
1902 nb_trace
=lttv_traceset_number(tab
->traceset_info
->traceset
);
1903 name
= g_new(char*,nb_trace
);
1904 for(i
= 0; i
< nb_trace
; i
++){
1905 trace_v
= lttv_traceset_get(tab
->traceset_info
->traceset
, i
);
1906 trace
= lttv_trace(trace_v
);
1907 name
[i
] = ltt_trace_name(trace
);
1910 remove_trace_name
= get_remove_trace(name
, nb_trace
);
1912 if(remove_trace_name
){
1913 for(i
=0; i
<nb_trace
; i
++){
1914 if(strcmp(remove_trace_name
,name
[i
]) == 0){
1915 //unselect the trace from the current viewer
1917 w
= gtk_multivpaned_get_widget(GTK_MULTIVPANED(tab
->multivpaned
));
1919 s
= g_object_get_data(G_OBJECT(w
), "Traceset_Selector");
1921 t
= lttv_traceset_selector_trace_get(s
,i
);
1922 lttv_trace_selector_set_selected(t
, FALSE
);
1925 //check if other viewers select the trace
1926 w
= gtk_multivpaned_get_first_widget(GTK_MULTIVPANED(tab
->multivpaned
));
1928 s
= g_object_get_data(G_OBJECT(w
), "Traceset_Selector");
1930 t
= lttv_traceset_selector_trace_get(s
,i
);
1931 selected
= lttv_trace_selector_get_selected(t
);
1934 w
= gtk_multivpaned_get_next_widget(GTK_MULTIVPANED(tab
->multivpaned
));
1936 }else selected
= FALSE
;
1938 //if no viewer selects the trace, remove it
1940 remove_trace_from_traceset_selector(GTK_MULTIVPANED(tab
->multivpaned
), i
);
1942 traceset
= tab
->traceset_info
->traceset
;
1943 //Keep a reference to the traces so they are not freed.
1944 for(j
=0; j
<lttv_traceset_number(traceset
); j
++)
1946 LttvTrace
* trace
= lttv_traceset_get(traceset
, j
);
1947 lttv_trace_ref(trace
);
1950 //remove state update hooks
1951 lttv_state_remove_event_hooks(
1952 (LttvTracesetState
*)tab
->traceset_info
->traceset_context
);
1953 lttv_context_fini(LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
));
1954 g_object_unref(tab
->traceset_info
->traceset_context
);
1957 trace_v
= lttv_traceset_get(traceset
, i
);
1959 if(lttv_trace_get_ref_number(trace_v
) <= 2) {
1960 /* ref 2 : traceset, local */
1961 lttvwindowtraces_remove_trace(trace_v
);
1962 ltt_trace_close(lttv_trace(trace_v
));
1965 lttv_traceset_remove(traceset
, i
);
1966 lttv_trace_unref(trace_v
); // Remove local reference
1968 if(!lttv_trace_get_ref_number(trace_v
))
1969 lttv_trace_destroy(trace_v
);
1971 tab
->traceset_info
->traceset_context
=
1972 g_object_new(LTTV_TRACESET_STATS_TYPE
, NULL
);
1974 LTTV_TRACESET_CONTEXT(tab
->
1975 traceset_info
->traceset_context
),traceset
);
1976 //add state update hooks
1977 lttv_state_add_event_hooks(
1978 (LttvTracesetState
*)tab
->traceset_info
->traceset_context
);
1980 //Remove local reference to the traces.
1981 for(j
=0; j
<lttv_traceset_number(traceset
); j
++)
1983 LttvTrace
* trace
= lttv_traceset_get(traceset
, j
);
1984 lttv_trace_unref(trace
);
1988 //update current tab
1989 //update_traceset(mw_data);
1992 SetTraceset(tab
, (gpointer
)traceset
);
1993 // in expose now call_pending_read_hooks(mw_data);
1995 //lttvwindow_report_current_time(mw_data,&(tab->current_time));
1998 // while(tab->multi_vpaned->num_children){
1999 // gtk_multi_vpaned_widget_delete(tab->multi_vpaned);
2013 /* Redraw all the viewers in the current tab */
2014 void redraw(GtkWidget
*widget
, gpointer user_data
)
2016 GtkWidget
* notebook
= lookup_widget(widget
, "MNotebook");
2017 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook
),
2018 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
)));
2023 tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
2027 LttvAttributeValue value
;
2029 g_assert(lttv_iattribute_find_by_path(tab
->attributes
, "hooks/redraw", LTTV_POINTER
, &value
));
2031 tmp
= (LttvHooks
*)*(value
.v_pointer
);
2033 lttv_hooks_call(tmp
,NULL
);
2037 void continue_processing(GtkWidget
*widget
, gpointer user_data
)
2039 GtkWidget
* notebook
= lookup_widget(widget
, "MNotebook");
2040 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook
),
2041 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
)));
2046 tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
2050 LttvAttributeValue value
;
2052 g_assert(lttv_iattribute_find_by_path(tab
->attributes
,
2053 "hooks/continue", LTTV_POINTER
, &value
));
2055 tmp
= (LttvHooks
*)*(value
.v_pointer
);
2057 lttv_hooks_call(tmp
,NULL
);
2060 /* Stop the processing for the calling main window's current tab.
2061 * It removes every processing requests that are in its list. It does not call
2062 * the end request hooks, because the request is not finished.
2065 void stop_processing(GtkWidget
*widget
, gpointer user_data
)
2067 GtkWidget
* notebook
= lookup_widget(widget
, "MNotebook");
2068 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook
),
2069 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
)));
2074 tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
2076 GSList
*iter
= tab
->events_requests
;
2078 while(iter
!= NULL
) {
2079 GSList
*remove_iter
= iter
;
2080 iter
= g_slist_next(iter
);
2082 g_free(remove_iter
->data
);
2083 tab
->events_requests
=
2084 g_slist_remove_link(tab
->events_requests
, remove_iter
);
2086 tab
->events_request_pending
= FALSE
;
2087 g_idle_remove_by_data(tab
);
2088 g_assert(g_slist_length(tab
->events_requests
) == 0);
2092 /* save will save the traceset to a file
2093 * Not implemented yet FIXME
2096 void save(GtkWidget
* widget
, gpointer user_data
)
2101 void save_as(GtkWidget
* widget
, gpointer user_data
)
2103 g_info("Save as\n");
2107 /* zoom will change the time_window of all the viewers of the
2108 * current tab, and redisplay them. The main functionality is to
2109 * determine the new time_window of the current tab
2112 void zoom(GtkWidget
* widget
, double size
)
2114 TimeInterval time_span
;
2115 TimeWindow new_time_window
;
2116 LttTime current_time
, time_delta
;
2117 MainWindow
* mw_data
= get_window_data_struct(widget
);
2118 LttvTracesetContext
*tsc
;
2119 GtkWidget
* notebook
= lookup_widget(widget
, "MNotebook");
2121 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook
),
2122 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
)));
2128 tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
2131 if(size
== 1) return;
2133 tsc
= LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
);
2134 time_span
= tsc
->time_span
;
2135 new_time_window
= tab
->time_window
;
2136 current_time
= tab
->current_time
;
2138 time_delta
= ltt_time_sub(time_span
.end_time
,time_span
.start_time
);
2140 new_time_window
.start_time
= time_span
.start_time
;
2141 new_time_window
.time_width
= time_delta
;
2142 new_time_window
.time_width_double
= ltt_time_to_double(time_delta
);
2143 new_time_window
.end_time
= ltt_time_add(new_time_window
.start_time
,
2144 new_time_window
.time_width
) ;
2146 new_time_window
.time_width
= ltt_time_div(new_time_window
.time_width
, size
);
2147 new_time_window
.time_width_double
=
2148 ltt_time_to_double(new_time_window
.time_width
);
2149 if(ltt_time_compare(new_time_window
.time_width
,time_delta
) > 0)
2150 { /* Case where zoom out is bigger than trace length */
2151 new_time_window
.start_time
= time_span
.start_time
;
2152 new_time_window
.time_width
= time_delta
;
2153 new_time_window
.time_width_double
= ltt_time_to_double(time_delta
);
2154 new_time_window
.end_time
= ltt_time_add(new_time_window
.start_time
,
2155 new_time_window
.time_width
) ;
2159 /* Center the image on the current time */
2160 new_time_window
.start_time
=
2161 ltt_time_sub(current_time
,
2162 ltt_time_from_double(new_time_window
.time_width_double
/2.0));
2163 new_time_window
.end_time
= ltt_time_add(new_time_window
.start_time
,
2164 new_time_window
.time_width
) ;
2165 /* If on borders, don't fall off */
2166 if(ltt_time_compare(new_time_window
.start_time
, time_span
.start_time
) <0)
2168 new_time_window
.start_time
= time_span
.start_time
;
2169 new_time_window
.end_time
= ltt_time_add(new_time_window
.start_time
,
2170 new_time_window
.time_width
) ;
2174 if(ltt_time_compare(new_time_window
.end_time
,
2175 time_span
.end_time
) > 0)
2177 new_time_window
.start_time
=
2178 ltt_time_sub(time_span
.end_time
, new_time_window
.time_width
);
2180 new_time_window
.end_time
= ltt_time_add(new_time_window
.start_time
,
2181 new_time_window
.time_width
) ;
2188 if(ltt_time_compare(new_time_window
.time_width
, ltt_time_zero
) == 0) {
2189 g_warning("Zoom more than 1 ns impossible");
2191 time_change_manager(tab
, new_time_window
);
2195 void zoom_in(GtkWidget
* widget
, gpointer user_data
)
2200 void zoom_out(GtkWidget
* widget
, gpointer user_data
)
2205 void zoom_extended(GtkWidget
* widget
, gpointer user_data
)
2210 void go_to_time(GtkWidget
* widget
, gpointer user_data
)
2212 g_info("Go to time\n");
2215 void show_time_frame(GtkWidget
* widget
, gpointer user_data
)
2217 g_info("Show time frame\n");
2221 /* callback function */
2224 on_empty_traceset_activate (GtkMenuItem
*menuitem
,
2227 create_new_window((GtkWidget
*)menuitem
, user_data
, FALSE
);
2232 on_clone_traceset_activate (GtkMenuItem
*menuitem
,
2235 create_new_window((GtkWidget
*)menuitem
, user_data
, TRUE
);
2239 /* create_new_tab calls create_tab to construct a new tab in the main window
2242 Tab
*create_new_tab(GtkWidget
* widget
, gpointer user_data
){
2243 gchar label
[PATH_MAX
];
2244 MainWindow
* mw_data
= get_window_data_struct(widget
);
2246 GtkNotebook
* notebook
= (GtkNotebook
*)lookup_widget(widget
, "MNotebook");
2247 if(notebook
== NULL
){
2248 g_info("Notebook does not exist\n");
2251 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook
),
2252 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
)));
2258 copy_tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
2261 strcpy(label
,"Page");
2262 if(get_label(mw_data
, label
,"Get the name of the tab","Please input tab's name"))
2263 return (create_tab (mw_data
, copy_tab
, notebook
, label
));
2269 on_tab_activate (GtkMenuItem
*menuitem
,
2272 create_new_tab((GtkWidget
*)menuitem
, user_data
);
2277 on_open_activate (GtkMenuItem
*menuitem
,
2280 open_traceset((GtkWidget
*)menuitem
, user_data
);
2285 on_close_activate (GtkMenuItem
*menuitem
,
2288 MainWindow
* mw_data
= get_window_data_struct((GtkWidget
*)menuitem
);
2289 main_window_destructor(mw_data
);
2293 /* remove the current tab from the main window
2297 on_close_tab_activate (GtkWidget
*widget
,
2301 GtkWidget
* notebook
;
2303 MainWindow
* mw_data
= get_window_data_struct(widget
);
2304 notebook
= lookup_widget(widget
, "MNotebook");
2305 if(notebook
== NULL
){
2306 g_info("Notebook does not exist\n");
2310 page_num
= gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
));
2312 gtk_notebook_remove_page(GTK_NOTEBOOK(notebook
), page_num
);
2317 on_close_tab_X_clicked (GtkWidget
*widget
,
2321 GtkWidget
*notebook
= lookup_widget(widget
, "MNotebook");
2322 if(notebook
== NULL
){
2323 g_info("Notebook does not exist\n");
2327 if((page_num
= gtk_notebook_page_num(GTK_NOTEBOOK(notebook
), widget
)) != -1)
2328 gtk_notebook_remove_page(GTK_NOTEBOOK(notebook
), page_num
);
2334 on_add_trace_activate (GtkMenuItem
*menuitem
,
2337 add_trace((GtkWidget
*)menuitem
, user_data
);
2342 on_remove_trace_activate (GtkMenuItem
*menuitem
,
2345 remove_trace((GtkWidget
*)menuitem
, user_data
);
2350 on_save_activate (GtkMenuItem
*menuitem
,
2353 save((GtkWidget
*)menuitem
, user_data
);
2358 on_save_as_activate (GtkMenuItem
*menuitem
,
2361 save_as((GtkWidget
*)menuitem
, user_data
);
2366 on_quit_activate (GtkMenuItem
*menuitem
,
2374 on_cut_activate (GtkMenuItem
*menuitem
,
2382 on_copy_activate (GtkMenuItem
*menuitem
,
2390 on_paste_activate (GtkMenuItem
*menuitem
,
2398 on_delete_activate (GtkMenuItem
*menuitem
,
2406 on_zoom_in_activate (GtkMenuItem
*menuitem
,
2409 zoom_in((GtkWidget
*)menuitem
, user_data
);
2414 on_zoom_out_activate (GtkMenuItem
*menuitem
,
2417 zoom_out((GtkWidget
*)menuitem
, user_data
);
2422 on_zoom_extended_activate (GtkMenuItem
*menuitem
,
2425 zoom_extended((GtkWidget
*)menuitem
, user_data
);
2430 on_go_to_time_activate (GtkMenuItem
*menuitem
,
2433 go_to_time((GtkWidget
*)menuitem
, user_data
);
2438 on_show_time_frame_activate (GtkMenuItem
*menuitem
,
2441 show_time_frame((GtkWidget
*)menuitem
, user_data
);
2446 on_move_viewer_up_activate (GtkMenuItem
*menuitem
,
2449 move_up_viewer((GtkWidget
*)menuitem
, user_data
);
2454 on_move_viewer_down_activate (GtkMenuItem
*menuitem
,
2457 move_down_viewer((GtkWidget
*)menuitem
, user_data
);
2462 on_remove_viewer_activate (GtkMenuItem
*menuitem
,
2465 delete_viewer((GtkWidget
*)menuitem
, user_data
);
2469 on_trace_facility_activate (GtkMenuItem
*menuitem
,
2472 g_info("Trace facility selector: %s\n");
2476 /* Dispaly a file selection dialogue to let user select a library, then call
2477 * lttv_library_load().
2481 on_load_library_activate (GtkMenuItem
*menuitem
,
2484 GError
*error
= NULL
;
2485 MainWindow
* mw_data
= get_window_data_struct((GtkWidget
*)menuitem
);
2487 gchar load_module_path_alter
[PATH_MAX
];
2491 gchar
*load_module_path
;
2492 name
= g_ptr_array_new();
2493 nb
= lttv_library_path_number();
2494 /* ask for the library path */
2498 path
= lttv_library_path_get(i
);
2499 g_ptr_array_add(name
, path
);
2502 load_module_path
= get_selection(mw_data
,
2503 (char **)(name
->pdata
), name
->len
,
2504 "Select a library path", "Library paths");
2505 if(load_module_path
!= NULL
)
2506 strncpy(load_module_path_alter
, load_module_path
, PATH_MAX
-1); // -1 for /
2508 g_ptr_array_free(name
, TRUE
);
2510 if(load_module_path
== NULL
) return;
2514 /* Make sure the module path ends with a / */
2515 gchar
*ptr
= load_module_path_alter
;
2517 ptr
= strchr(ptr
, '\0');
2519 if(*(ptr
-1) != '/') {
2526 /* Ask for the library to load : list files in the previously selected
2528 gchar str
[PATH_MAX
];
2531 GtkFileSelection
* file_selector
=
2532 (GtkFileSelection
*)gtk_file_selection_new("Select a module");
2533 gtk_file_selection_set_filename(file_selector
, load_module_path_alter
);
2534 gtk_file_selection_hide_fileop_buttons(file_selector
);
2536 gtk_window_set_transient_for(GTK_WINDOW(file_selector
),
2537 GTK_WINDOW(mw_data
->mwindow
));
2540 id
= gtk_dialog_run(GTK_DIALOG(file_selector
));
2542 case GTK_RESPONSE_ACCEPT
:
2543 case GTK_RESPONSE_OK
:
2544 dir
= gtk_file_selection_get_selections (file_selector
);
2545 strncpy(str
,dir
[0],PATH_MAX
);
2546 strncpy(remember_plugins_dir
,dir
[0],PATH_MAX
);
2547 /* only keep file name */
2549 str1
= strrchr(str
,'/');
2552 str1
= strrchr(str
,'\\');
2557 if(*str1
== 'l' && *(str1
+1)== 'i' && *(str1
+2)=='b')
2559 remove info after
. */
2563 str2
= strrchr(str2
, '.');
2564 if(str2
!= NULL
) *str2
= '\0';
2566 lttv_module_require(str1
, &error
);
2568 lttv_library_load(str1
, &error
);
2569 if(error
!= NULL
) g_warning("%s", error
->message
);
2570 else g_info("Load library: %s\n", str
);
2572 case GTK_RESPONSE_REJECT
:
2573 case GTK_RESPONSE_CANCEL
:
2575 gtk_widget_destroy((GtkWidget
*)file_selector
);
2586 /* Display all loaded modules, let user to select a module to unload
2587 * by calling lttv_module_unload
2591 on_unload_library_activate (GtkMenuItem
*menuitem
,
2594 MainWindow
* mw_data
= get_window_data_struct((GtkWidget
*)menuitem
);
2596 LttvLibrary
*library
= NULL
;
2601 name
= g_ptr_array_new();
2602 nb
= lttv_library_number();
2603 LttvLibraryInfo
*lib_info
= g_new(LttvLibraryInfo
,nb
);
2604 /* ask for the library name */
2607 LttvLibrary
*iter_lib
= lttv_library_get(i
);
2608 lttv_library_info(iter_lib
, &lib_info
[i
]);
2610 gchar
*path
= lib_info
[i
].name
;
2611 g_ptr_array_add(name
, path
);
2613 lib_name
= get_selection(mw_data
, (char **)(name
->pdata
), name
->len
,
2614 "Select a library", "Libraries");
2615 if(lib_name
!= NULL
) {
2617 if(strcmp(lib_name
, lib_info
[i
].name
) == 0) {
2618 library
= lttv_library_get(i
);
2623 g_ptr_array_free(name
, TRUE
);
2626 if(lib_name
== NULL
) return;
2628 if(library
!= NULL
) lttv_library_unload(library
);
2632 /* Dispaly a file selection dialogue to let user select a module, then call
2633 * lttv_module_require().
2637 on_load_module_activate (GtkMenuItem
*menuitem
,
2640 GError
*error
= NULL
;
2641 MainWindow
* mw_data
= get_window_data_struct((GtkWidget
*)menuitem
);
2643 LttvLibrary
*library
= NULL
;
2648 name
= g_ptr_array_new();
2649 nb
= lttv_library_number();
2650 LttvLibraryInfo
*lib_info
= g_new(LttvLibraryInfo
,nb
);
2651 /* ask for the library name */
2654 LttvLibrary
*iter_lib
= lttv_library_get(i
);
2655 lttv_library_info(iter_lib
, &lib_info
[i
]);
2657 gchar
*path
= lib_info
[i
].name
;
2658 g_ptr_array_add(name
, path
);
2660 lib_name
= get_selection(mw_data
,(char **)(name
->pdata
), name
->len
,
2661 "Select a library", "Libraries");
2662 if(lib_name
!= NULL
) {
2664 if(strcmp(lib_name
, lib_info
[i
].name
) == 0) {
2665 library
= lttv_library_get(i
);
2670 g_ptr_array_free(name
, TRUE
);
2673 if(lib_name
== NULL
) return;
2676 //LttvModule *module;
2677 gchar module_name_out
[PATH_MAX
];
2679 /* Ask for the module to load : list modules in the selected lib */
2683 nb
= lttv_library_module_number(library
);
2684 LttvModuleInfo
*module_info
= g_new(LttvModuleInfo
,nb
);
2685 name
= g_ptr_array_new();
2686 /* ask for the module name */
2689 LttvModule
*iter_module
= lttv_library_module_get(library
, i
);
2690 lttv_module_info(iter_module
, &module_info
[i
]);
2692 gchar
*path
= module_info
[i
].name
;
2693 g_ptr_array_add(name
, path
);
2695 module_name
= get_selection(mw_data
, (char **)(name
->pdata
), name
->len
,
2696 "Select a module", "Modules");
2697 if(module_name
!= NULL
) {
2699 if(strcmp(module_name
, module_info
[i
].name
) == 0) {
2700 strncpy(module_name_out
, module_name
, PATH_MAX
);
2701 //module = lttv_library_module_get(i);
2707 g_ptr_array_free(name
, TRUE
);
2708 g_free(module_info
);
2710 if(module_name
== NULL
) return;
2713 lttv_module_require(module_name_out
, &error
);
2714 if(error
!= NULL
) g_warning("%s", error
->message
);
2715 else g_info("Load module: %s", module_name_out
);
2722 gchar str
[PATH_MAX
];
2725 GtkFileSelection
* file_selector
=
2726 (GtkFileSelection
*)gtk_file_selection_new("Select a module");
2727 gtk_file_selection_set_filename(file_selector
, load_module_path_alter
);
2728 gtk_file_selection_hide_fileop_buttons(file_selector
);
2731 id
= gtk_dialog_run(GTK_DIALOG(file_selector
));
2733 case GTK_RESPONSE_ACCEPT
:
2734 case GTK_RESPONSE_OK
:
2735 dir
= gtk_file_selection_get_selections (file_selector
);
2736 strncpy(str
,dir
[0],PATH_MAX
);
2737 strncpy(remember_plugins_dir
,dir
[0],PATH_MAX
);
2739 /* only keep file name */
2741 str1
= strrchr(str
,'/');
2744 str1
= strrchr(str
,'\\');
2749 if(*str1
== 'l' && *(str1
+1)== 'i' && *(str1
+2)=='b')
2751 remove info after
. */
2755 str2
= strrchr(str2
, '.');
2756 if(str2
!= NULL
) *str2
= '\0';
2758 lttv_module_require(str1
, &error
);
2760 lttv_library_load(str1
, &error
);
2761 if(error
!= NULL
) g_warning(error
->message
);
2762 else g_info("Load library: %s\n", str
);
2764 case GTK_RESPONSE_REJECT
:
2765 case GTK_RESPONSE_CANCEL
:
2767 gtk_widget_destroy((GtkWidget
*)file_selector
);
2779 /* Display all loaded modules, let user to select a module to unload
2780 * by calling lttv_module_unload
2784 on_unload_module_activate (GtkMenuItem
*menuitem
,
2787 GError
*error
= NULL
;
2788 MainWindow
* mw_data
= get_window_data_struct((GtkWidget
*)menuitem
);
2790 LttvLibrary
*library
;
2795 name
= g_ptr_array_new();
2796 nb
= lttv_library_number();
2797 LttvLibraryInfo
*lib_info
= g_new(LttvLibraryInfo
,nb
);
2798 /* ask for the library name */
2801 LttvLibrary
*iter_lib
= lttv_library_get(i
);
2802 lttv_library_info(iter_lib
, &lib_info
[i
]);
2804 gchar
*path
= lib_info
[i
].name
;
2805 g_ptr_array_add(name
, path
);
2807 lib_name
= get_selection(mw_data
, (char **)(name
->pdata
), name
->len
,
2808 "Select a library", "Libraries");
2809 if(lib_name
!= NULL
) {
2811 if(strcmp(lib_name
, lib_info
[i
].name
) == 0) {
2812 library
= lttv_library_get(i
);
2817 g_ptr_array_free(name
, TRUE
);
2820 if(lib_name
== NULL
) return;
2823 LttvModule
*module
= NULL
;
2825 /* Ask for the module to load : list modules in the selected lib */
2829 nb
= lttv_library_module_number(library
);
2830 LttvModuleInfo
*module_info
= g_new(LttvModuleInfo
,nb
);
2831 name
= g_ptr_array_new();
2832 /* ask for the module name */
2835 LttvModule
*iter_module
= lttv_library_module_get(library
, i
);
2836 lttv_module_info(iter_module
, &module_info
[i
]);
2838 gchar
*path
= module_info
[i
].name
;
2839 if(module_info
[i
].use_count
> 0) g_ptr_array_add(name
, path
);
2841 module_name
= get_selection(mw_data
, (char **)(name
->pdata
), name
->len
,
2842 "Select a module", "Modules");
2843 if(module_name
!= NULL
) {
2845 if(strcmp(module_name
, module_info
[i
].name
) == 0) {
2846 module
= lttv_library_module_get(library
, i
);
2852 g_ptr_array_free(name
, TRUE
);
2853 g_free(module_info
);
2855 if(module_name
== NULL
) return;
2858 LttvModuleInfo module_info
;
2859 lttv_module_info(module
, &module_info
);
2860 g_info("Release module: %s\n", module_info
.name
);
2862 lttv_module_release(module
);
2866 /* Display a directory dialogue to let user select a path for library searching
2870 on_add_library_search_path_activate (GtkMenuItem
*menuitem
,
2873 MainWindow
* mw_data
= get_window_data_struct((GtkWidget
*)menuitem
);
2874 //GtkDirSelection * file_selector = (GtkDirSelection *)gtk_dir_selection_new("Select library path");
2875 GtkFileSelection
* file_selector
= (GtkFileSelection
*)gtk_file_selection_new("Select a trace");
2876 gtk_widget_hide( (file_selector
)->file_list
->parent
) ;
2878 gtk_window_set_transient_for(GTK_WINDOW(file_selector
),
2879 GTK_WINDOW(mw_data
->mwindow
));
2884 if(remember_plugins_dir
[0] != '\0')
2885 gtk_file_selection_set_filename(file_selector
, remember_plugins_dir
);
2887 id
= gtk_dialog_run(GTK_DIALOG(file_selector
));
2889 case GTK_RESPONSE_ACCEPT
:
2890 case GTK_RESPONSE_OK
:
2891 dir
= gtk_file_selection_get_filename (file_selector
);
2892 strncpy(remember_plugins_dir
,dir
,PATH_MAX
);
2893 strncat(remember_plugins_dir
,"/",PATH_MAX
);
2894 lttv_library_path_add(dir
);
2895 case GTK_RESPONSE_REJECT
:
2896 case GTK_RESPONSE_CANCEL
:
2898 gtk_widget_destroy((GtkWidget
*)file_selector
);
2904 /* Display a directory dialogue to let user select a path for library searching
2908 on_remove_library_search_path_activate (GtkMenuItem
*menuitem
,
2911 MainWindow
* mw_data
= get_window_data_struct((GtkWidget
*)menuitem
);
2913 const char *lib_path
;
2918 name
= g_ptr_array_new();
2919 nb
= lttv_library_path_number();
2920 /* ask for the library name */
2923 gchar
*path
= lttv_library_path_get(i
);
2924 g_ptr_array_add(name
, path
);
2926 lib_path
= get_selection(mw_data
, (char **)(name
->pdata
), name
->len
,
2927 "Select a library path", "Library paths");
2929 g_ptr_array_free(name
, TRUE
);
2931 if(lib_path
== NULL
) return;
2934 lttv_library_path_remove(lib_path
);
2938 on_color_activate (GtkMenuItem
*menuitem
,
2946 on_save_configuration_activate (GtkMenuItem
*menuitem
,
2949 g_info("Save configuration\n");
2954 on_content_activate (GtkMenuItem
*menuitem
,
2957 g_info("Content\n");
2962 on_about_close_activate (GtkButton
*button
,
2965 GtkWidget
*about_widget
= GTK_WIDGET(user_data
);
2967 gtk_widget_destroy(about_widget
);
2971 on_about_activate (GtkMenuItem
*menuitem
,
2974 MainWindow
*main_window
= get_window_data_struct(GTK_WIDGET(menuitem
));
2975 GtkWidget
*window_widget
= main_window
->mwindow
;
2976 GtkWidget
*about_widget
= gtk_window_new(GTK_WINDOW_TOPLEVEL
);
2977 GtkWindow
*about_window
= GTK_WINDOW(about_widget
);
2978 gint window_width
, window_height
;
2980 gtk_window_set_title(about_window
, "About Linux Trace Toolkit");
2982 gtk_window_set_resizable(about_window
, FALSE
);
2983 gtk_window_set_transient_for(GTK_WINDOW(window_widget
), about_window
);
2984 gtk_window_set_destroy_with_parent(about_window
, TRUE
);
2985 gtk_window_set_modal(about_window
, FALSE
);
2987 /* Put the about window at the center of the screen */
2988 gtk_window_get_size(about_window
, &window_width
, &window_height
);
2989 gtk_window_move (about_window
,
2990 (gdk_screen_width() - window_width
)/2,
2991 (gdk_screen_height() - window_height
)/2);
2993 GtkWidget
*vbox
= gtk_vbox_new(FALSE
, 1);
2995 gtk_container_add(GTK_CONTAINER(about_widget
), vbox
);
2999 GtkWidget
*label1
= gtk_label_new("");
3000 gtk_misc_set_padding(GTK_MISC(label1
), 10, 20);
3001 gtk_label_set_markup(GTK_LABEL(label1
), "\
3002 <big>Linux Trace Toolkit</big>");
3003 gtk_label_set_justify(GTK_LABEL(label1
), GTK_JUSTIFY_CENTER
);
3005 GtkWidget
*label2
= gtk_label_new("");
3006 gtk_misc_set_padding(GTK_MISC(label2
), 10, 20);
3007 gtk_label_set_markup(GTK_LABEL(label2
), "\
3010 Michel Dagenais (New trace format, lttv main)\n\
3011 Mathieu Desnoyers (Kernel Tracer, Directory structure, build with automake/conf,\n\
3012 lttv gui, control flow view, gui cooperative trace reading\n\
3013 scheduler with interruptible foreground and background\n\
3014 computation, detailed event list (rewrite), trace reading\n\
3015 library (rewrite))\n\
3016 Benoit Des Ligneris, Eric Clement (Cluster adaptation, work in progress)\n\
3017 Xang-Xiu Yang (new trace reading library and converter, lttv gui, \n\
3018 detailed event list and statistics view)\n\
3019 Tom Zanussi (RelayFS)\n\
3021 Strongly inspired from the original Linux Trace Toolkit Visualizer made by\n\
3024 GtkWidget
*label3
= gtk_label_new("");
3025 gtk_label_set_markup(GTK_LABEL(label3
), "\
3026 Linux Trace Toolkit Viewer, Copyright (C) 2004\n\
3028 Mathieu Desnoyers\n\
3030 Linux Trace Toolkit comes with ABSOLUTELY NO WARRANTY.\n\
3031 This is free software, and you are welcome to redistribute it\n\
3032 under certain conditions. See COPYING for details.");
3033 gtk_misc_set_padding(GTK_MISC(label3
), 10, 20);
3035 gtk_box_pack_start_defaults(GTK_BOX(vbox
), label1
);
3036 gtk_box_pack_start_defaults(GTK_BOX(vbox
), label2
);
3037 gtk_box_pack_start_defaults(GTK_BOX(vbox
), label3
);
3039 GtkWidget
*hbox
= gtk_hbox_new(TRUE
, 0);
3040 gtk_box_pack_end(GTK_BOX(vbox
), hbox
, FALSE
, FALSE
, 0);
3041 GtkWidget
*close_button
= gtk_button_new_with_mnemonic("_Close");
3042 gtk_box_pack_end(GTK_BOX(hbox
), close_button
, FALSE
, FALSE
, 0);
3043 gtk_container_set_border_width(GTK_CONTAINER(close_button
), 20);
3045 g_signal_connect(G_OBJECT(close_button
), "clicked",
3046 G_CALLBACK(on_about_close_activate
),
3047 (gpointer
)about_widget
);
3049 gtk_widget_show_all(about_widget
);
3054 on_button_new_clicked (GtkButton
*button
,
3057 create_new_window((GtkWidget
*)button
, user_data
, TRUE
);
3061 on_button_new_tab_clicked (GtkButton
*button
,
3064 create_new_tab((GtkWidget
*)button
, user_data
);
3068 on_button_open_clicked (GtkButton
*button
,
3071 open_traceset((GtkWidget
*)button
, user_data
);
3076 on_button_add_trace_clicked (GtkButton
*button
,
3079 add_trace((GtkWidget
*)button
, user_data
);
3084 on_button_remove_trace_clicked (GtkButton
*button
,
3087 remove_trace((GtkWidget
*)button
, user_data
);
3091 on_button_redraw_clicked (GtkButton
*button
,
3094 redraw((GtkWidget
*)button
, user_data
);
3098 on_button_continue_processing_clicked (GtkButton
*button
,
3101 continue_processing((GtkWidget
*)button
, user_data
);
3105 on_button_stop_processing_clicked (GtkButton
*button
,
3108 stop_processing((GtkWidget
*)button
, user_data
);
3114 on_button_save_clicked (GtkButton
*button
,
3117 save((GtkWidget
*)button
, user_data
);
3122 on_button_save_as_clicked (GtkButton
*button
,
3125 save_as((GtkWidget
*)button
, user_data
);
3130 on_button_zoom_in_clicked (GtkButton
*button
,
3133 zoom_in((GtkWidget
*)button
, user_data
);
3138 on_button_zoom_out_clicked (GtkButton
*button
,
3141 zoom_out((GtkWidget
*)button
, user_data
);
3146 on_button_zoom_extended_clicked (GtkButton
*button
,
3149 zoom_extended((GtkWidget
*)button
, user_data
);
3154 on_button_go_to_time_clicked (GtkButton
*button
,
3157 go_to_time((GtkWidget
*)button
, user_data
);
3162 on_button_show_time_frame_clicked (GtkButton
*button
,
3165 show_time_frame((GtkWidget
*)button
, user_data
);
3170 on_button_move_up_clicked (GtkButton
*button
,
3173 move_up_viewer((GtkWidget
*)button
, user_data
);
3178 on_button_move_down_clicked (GtkButton
*button
,
3181 move_down_viewer((GtkWidget
*)button
, user_data
);
3186 on_button_delete_viewer_clicked (GtkButton
*button
,
3189 delete_viewer((GtkWidget
*)button
, user_data
);
3193 on_MWindow_destroy (GtkWidget
*widget
,
3196 MainWindow
*main_window
= get_window_data_struct(widget
);
3197 LttvIAttribute
*attributes
= main_window
->attributes
;
3198 LttvAttributeValue value
;
3200 //This is unnecessary, since widgets will be destroyed
3201 //by the main window widget anyway.
3202 //remove_all_menu_toolbar_constructors(main_window, NULL);
3204 g_assert(lttv_iattribute_find_by_path(attributes
,
3205 "viewers/menu", LTTV_POINTER
, &value
));
3206 lttv_menus_destroy((LttvMenus
*)*(value
.v_pointer
));
3208 g_assert(lttv_iattribute_find_by_path(attributes
,
3209 "viewers/toolbar", LTTV_POINTER
, &value
));
3210 lttv_toolbars_destroy((LttvToolbars
*)*(value
.v_pointer
));
3212 g_object_unref(main_window
->attributes
);
3213 g_main_window_list
= g_slist_remove(g_main_window_list
, main_window
);
3215 g_info("There are now : %d windows\n",g_slist_length(g_main_window_list
));
3216 if(g_slist_length(g_main_window_list
) == 0)
3221 on_MWindow_configure (GtkWidget
*widget
,
3222 GdkEventConfigure
*event
,
3225 MainWindow
* mw_data
= get_window_data_struct((GtkWidget
*)widget
);
3227 // MD : removed time width modification upon resizing of the main window.
3228 // The viewers will redraw themselves completely, without time interval
3231 if(mw_data->window_width){
3232 time_span = LTTV_TRACESET_CONTEXT(tab->traceset_info->traceset_context)->Time_Span ;
3233 time_win = tab->time_window;
3234 ratio = width / mw_data->window_width;
3235 tab->time_window.time_width = ltt_time_mul(time_win.time_width,ratio);
3236 time = ltt_time_sub(time_span->endTime, time_win.start_time);
3237 if(ltt_time_compare(time, tab->time_window.time_width) < 0){
3238 tab->time_window.time_width = time;
3244 mw_data->window_width = (int)width;
3253 on_MNotebook_switch_page (GtkNotebook
*notebook
,
3254 GtkNotebookPage
*page
,
3262 void time_change_manager (Tab
*tab
,
3263 TimeWindow new_time_window
)
3265 /* Only one source of time change */
3266 if(tab
->time_manager_lock
== TRUE
) return;
3268 tab
->time_manager_lock
= TRUE
;
3270 LttvTracesetContext
*tsc
= LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
);
3271 TimeInterval time_span
= tsc
->time_span
;
3272 LttTime start_time
= new_time_window
.start_time
;
3273 LttTime end_time
= new_time_window
.end_time
;
3275 g_assert(ltt_time_compare(start_time
, end_time
) < 0);
3278 GtkAdjustment
*adjustment
= gtk_range_get_adjustment(GTK_RANGE(tab
->scrollbar
));
3279 LttTime upper
= ltt_time_sub(time_span
.end_time
, time_span
.start_time
);
3281 gtk_range_set_increments(GTK_RANGE(tab
->scrollbar
),
3282 ltt_time_to_double(new_time_window
.time_width
)
3283 / SCROLL_STEP_PER_PAGE
3284 * NANOSECONDS_PER_SECOND
, /* step increment */
3285 ltt_time_to_double(new_time_window
.time_width
)
3286 * NANOSECONDS_PER_SECOND
); /* page increment */
3287 gtk_range_set_range(GTK_RANGE(tab
->scrollbar
),
3289 ltt_time_to_double(upper
)
3290 * NANOSECONDS_PER_SECOND
); /* upper */
3292 g_object_set(G_OBJECT(adjustment
),
3296 ltt_time_to_double(upper
), /* upper */
3298 new_time_window
.time_width_double
3299 / SCROLL_STEP_PER_PAGE
, /* step increment */
3301 new_time_window
.time_width_double
,
3302 /* page increment */
3304 new_time_window
.time_width_double
, /* page size */
3306 gtk_adjustment_changed(adjustment
);
3308 // g_object_set(G_OBJECT(adjustment),
3310 // ltt_time_to_double(
3311 // ltt_time_sub(start_time, time_span.start_time))
3314 //gtk_adjustment_value_changed(adjustment);
3315 gtk_range_set_value(GTK_RANGE(tab
->scrollbar
),
3317 ltt_time_sub(start_time
, time_span
.start_time
)) /* value */);
3319 /* set the time bar. */
3321 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry1
),
3322 (double)time_span
.start_time
.tv_sec
,
3323 (double)time_span
.end_time
.tv_sec
);
3324 gtk_spin_button_set_value(GTK_SPIN_BUTTON(tab
->MEntry1
),
3325 (double)start_time
.tv_sec
);
3327 /* start nanoseconds */
3328 if(start_time
.tv_sec
== time_span
.start_time
.tv_sec
) {
3329 /* can be both beginning and end at the same time. */
3330 if(start_time
.tv_sec
== time_span
.end_time
.tv_sec
) {
3331 /* If we are at the end, max nsec to end.. -1 (not zero length) */
3332 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry2
),
3333 (double)time_span
.start_time
.tv_nsec
,
3334 (double)time_span
.end_time
.tv_nsec
-1);
3336 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry2
),
3337 (double)time_span
.start_time
.tv_nsec
,
3338 (double)NANOSECONDS_PER_SECOND
-1);
3340 } else if(start_time
.tv_sec
== time_span
.end_time
.tv_sec
) {
3341 /* If we are at the end, max nsec to end.. -1 (not zero length) */
3342 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry2
),
3344 (double)time_span
.end_time
.tv_nsec
-1);
3345 } else /* anywhere else */
3346 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry2
),
3348 (double)NANOSECONDS_PER_SECOND
-1);
3349 gtk_spin_button_set_value(GTK_SPIN_BUTTON(tab
->MEntry2
),
3350 (double)start_time
.tv_nsec
);
3353 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry3
),
3354 (double)time_span
.start_time
.tv_sec
,
3355 (double)time_span
.end_time
.tv_sec
);
3356 gtk_spin_button_set_value(GTK_SPIN_BUTTON(tab
->MEntry3
),
3357 (double)end_time
.tv_sec
);
3359 /* end nanoseconds */
3360 if(end_time
.tv_sec
== time_span
.start_time
.tv_sec
) {
3361 /* can be both beginning and end at the same time. */
3362 if(end_time
.tv_sec
== time_span
.end_time
.tv_sec
) {
3363 /* If we are at the end, max nsec to end.. */
3364 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry4
),
3365 (double)time_span
.start_time
.tv_nsec
+1,
3366 (double)time_span
.end_time
.tv_nsec
);
3368 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry4
),
3369 (double)time_span
.start_time
.tv_nsec
+1,
3370 (double)NANOSECONDS_PER_SECOND
-1);
3373 else if(end_time
.tv_sec
== time_span
.end_time
.tv_sec
) {
3374 /* If we are at the end, max nsec to end.. */
3375 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry4
),
3377 (double)time_span
.end_time
.tv_nsec
);
3379 else /* anywhere else */
3380 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry4
),
3382 (double)NANOSECONDS_PER_SECOND
-1);
3383 gtk_spin_button_set_value(GTK_SPIN_BUTTON(tab
->MEntry4
),
3384 (double)end_time
.tv_nsec
);
3386 /* call viewer hooks for new time window */
3387 set_time_window(tab
, &new_time_window
);
3389 tab
->time_manager_lock
= FALSE
;
3393 /* value changed for frame start s
3395 * Check time span : if ns is out of range, clip it the nearest good value.
3398 on_MEntry1_value_changed (GtkSpinButton
*spinbutton
,
3401 Tab
*tab
=(Tab
*)user_data
;
3402 LttvTracesetContext
* tsc
=
3403 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
);
3404 TimeInterval time_span
= tsc
->time_span
;
3405 gint value
= gtk_spin_button_get_value_as_int(spinbutton
);
3407 TimeWindow new_time_window
= tab
->time_window
;
3409 LttTime end_time
= new_time_window
.end_time
;
3411 new_time_window
.start_time
.tv_sec
= value
;
3413 /* start nanoseconds */
3414 if(new_time_window
.start_time
.tv_sec
== time_span
.start_time
.tv_sec
) {
3415 if(new_time_window
.start_time
.tv_sec
== time_span
.end_time
.tv_sec
) {
3416 if(new_time_window
.start_time
.tv_nsec
> time_span
.end_time
.tv_nsec
)
3417 new_time_window
.start_time
.tv_nsec
= time_span
.end_time
.tv_nsec
-1;
3418 if(new_time_window
.start_time
.tv_nsec
< time_span
.start_time
.tv_nsec
)
3419 new_time_window
.start_time
.tv_nsec
= time_span
.start_time
.tv_nsec
;
3421 if(new_time_window
.start_time
.tv_nsec
< time_span
.start_time
.tv_nsec
)
3422 new_time_window
.start_time
.tv_nsec
= time_span
.start_time
.tv_nsec
;
3425 else if(new_time_window
.start_time
.tv_sec
== time_span
.end_time
.tv_sec
) {
3426 if(new_time_window
.start_time
.tv_nsec
> time_span
.end_time
.tv_nsec
)
3427 new_time_window
.start_time
.tv_nsec
= time_span
.end_time
.tv_nsec
-1;
3430 if(ltt_time_compare(new_time_window
.start_time
, end_time
) >= 0) {
3431 /* Then, we must push back end time : keep the same time width
3432 * if possible, else end traceset time */
3433 end_time
= LTT_TIME_MIN(ltt_time_add(new_time_window
.start_time
,
3434 new_time_window
.time_width
),
3435 time_span
.end_time
);
3438 /* Fix the time width to fit start time and end time */
3439 new_time_window
.time_width
= ltt_time_sub(end_time
,
3440 new_time_window
.start_time
);
3441 new_time_window
.time_width_double
=
3442 ltt_time_to_double(new_time_window
.time_width
);
3444 new_time_window
.end_time
= end_time
;
3446 time_change_manager(tab
, new_time_window
);
3451 on_MEntry2_value_changed (GtkSpinButton
*spinbutton
,
3454 Tab
*tab
=(Tab
*)user_data
;
3455 LttvTracesetContext
* tsc
=
3456 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
);
3457 TimeInterval time_span
= tsc
->time_span
;
3458 gint value
= gtk_spin_button_get_value_as_int(spinbutton
);
3460 TimeWindow new_time_window
= tab
->time_window
;
3462 LttTime end_time
= new_time_window
.end_time
;
3464 new_time_window
.start_time
.tv_nsec
= value
;
3466 if(ltt_time_compare(new_time_window
.start_time
, end_time
) >= 0) {
3467 /* Then, we must push back end time : keep the same time width
3468 * if possible, else end traceset time */
3469 end_time
= LTT_TIME_MIN(ltt_time_add(new_time_window
.start_time
,
3470 new_time_window
.time_width
),
3471 time_span
.end_time
);
3474 /* Fix the time width to fit start time and end time */
3475 new_time_window
.time_width
= ltt_time_sub(end_time
,
3476 new_time_window
.start_time
);
3477 new_time_window
.time_width_double
=
3478 ltt_time_to_double(new_time_window
.time_width
);
3480 new_time_window
.end_time
= end_time
;
3482 time_change_manager(tab
, new_time_window
);
3487 on_MEntry3_value_changed (GtkSpinButton
*spinbutton
,
3490 Tab
*tab
=(Tab
*)user_data
;
3491 LttvTracesetContext
* tsc
=
3492 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
);
3493 TimeInterval time_span
= tsc
->time_span
;
3494 gint value
= gtk_spin_button_get_value_as_int(spinbutton
);
3496 TimeWindow new_time_window
= tab
->time_window
;
3498 LttTime end_time
= new_time_window
.end_time
;
3500 end_time
.tv_sec
= value
;
3502 /* end nanoseconds */
3503 if(end_time
.tv_sec
== time_span
.start_time
.tv_sec
) {
3504 if(end_time
.tv_sec
== time_span
.end_time
.tv_sec
) {
3505 if(end_time
.tv_nsec
> time_span
.end_time
.tv_nsec
)
3506 end_time
.tv_nsec
= time_span
.end_time
.tv_nsec
;
3507 if(end_time
.tv_nsec
< time_span
.start_time
.tv_nsec
)
3508 end_time
.tv_nsec
= time_span
.start_time
.tv_nsec
+1;
3510 if(end_time
.tv_nsec
< time_span
.start_time
.tv_nsec
)
3511 end_time
.tv_nsec
= time_span
.start_time
.tv_nsec
+1;
3514 else if(end_time
.tv_sec
== time_span
.end_time
.tv_sec
) {
3515 if(end_time
.tv_nsec
> time_span
.end_time
.tv_nsec
)
3516 end_time
.tv_nsec
= time_span
.end_time
.tv_nsec
;
3519 if(ltt_time_compare(new_time_window
.start_time
, end_time
) >= 0) {
3520 /* Then, we must push front start time : keep the same time width
3521 * if possible, else end traceset time */
3522 new_time_window
.start_time
= LTT_TIME_MAX(
3523 ltt_time_sub(end_time
,
3524 new_time_window
.time_width
),
3525 time_span
.start_time
);
3528 /* Fix the time width to fit start time and end time */
3529 new_time_window
.time_width
= ltt_time_sub(end_time
,
3530 new_time_window
.start_time
);
3531 new_time_window
.time_width_double
=
3532 ltt_time_to_double(new_time_window
.time_width
);
3534 new_time_window
.end_time
= end_time
;
3536 time_change_manager(tab
, new_time_window
);
3541 on_MEntry4_value_changed (GtkSpinButton
*spinbutton
,
3544 Tab
*tab
=(Tab
*)user_data
;
3545 LttvTracesetContext
* tsc
=
3546 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
);
3547 TimeInterval time_span
= tsc
->time_span
;
3548 gint value
= gtk_spin_button_get_value_as_int(spinbutton
);
3550 TimeWindow new_time_window
= tab
->time_window
;
3552 LttTime end_time
= new_time_window
.end_time
;
3554 end_time
.tv_nsec
= value
;
3556 if(ltt_time_compare(new_time_window
.start_time
, end_time
) >= 0) {
3557 /* Then, we must push front start time : keep the same time width
3558 * if possible, else end traceset time */
3559 new_time_window
.start_time
= LTT_TIME_MAX(
3560 ltt_time_sub(end_time
,
3561 new_time_window
.time_width
),
3562 time_span
.start_time
);
3565 /* Fix the time width to fit start time and end time */
3566 new_time_window
.time_width
= ltt_time_sub(end_time
,
3567 new_time_window
.start_time
);
3568 new_time_window
.time_width_double
=
3569 ltt_time_to_double(new_time_window
.time_width
);
3570 new_time_window
.end_time
= end_time
;
3572 time_change_manager(tab
, new_time_window
);
3577 void current_time_change_manager (Tab
*tab
,
3578 LttTime new_current_time
)
3580 /* Only one source of time change */
3581 if(tab
->current_time_manager_lock
== TRUE
) return;
3583 tab
->current_time_manager_lock
= TRUE
;
3585 LttvTracesetContext
*tsc
= LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
);
3586 TimeInterval time_span
= tsc
->time_span
;
3588 /* current seconds */
3589 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry5
),
3590 (double)time_span
.start_time
.tv_sec
,
3591 (double)time_span
.end_time
.tv_sec
);
3592 gtk_spin_button_set_value(GTK_SPIN_BUTTON(tab
->MEntry5
),
3593 (double)new_current_time
.tv_sec
);
3596 /* start nanoseconds */
3597 if(new_current_time
.tv_sec
== time_span
.start_time
.tv_sec
) {
3598 /* can be both beginning and end at the same time. */
3599 if(new_current_time
.tv_sec
== time_span
.end_time
.tv_sec
) {
3600 /* If we are at the end, max nsec to end.. */
3601 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry6
),
3602 (double)time_span
.start_time
.tv_nsec
,
3603 (double)time_span
.end_time
.tv_nsec
);
3605 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry6
),
3606 (double)time_span
.start_time
.tv_nsec
,
3607 (double)NANOSECONDS_PER_SECOND
-1);
3609 } else if(new_current_time
.tv_sec
== time_span
.end_time
.tv_sec
) {
3610 /* If we are at the end, max nsec to end.. */
3611 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry6
),
3613 (double)time_span
.end_time
.tv_nsec
);
3614 } else /* anywhere else */
3615 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry6
),
3617 (double)NANOSECONDS_PER_SECOND
-1);
3619 gtk_spin_button_set_value(GTK_SPIN_BUTTON(tab
->MEntry6
),
3620 (double)new_current_time
.tv_nsec
);
3622 set_current_time(tab
, &new_current_time
);
3624 tab
->current_time_manager_lock
= FALSE
;
3627 void current_position_change_manager(Tab
*tab
,
3628 LttvTracesetContextPosition
*pos
)
3630 LttvTracesetContext
*tsc
=
3631 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
);
3632 TimeInterval time_span
= tsc
->time_span
;
3634 g_assert(lttv_process_traceset_seek_position(tsc
, pos
) == 0);
3635 LttTime new_time
= lttv_traceset_context_position_get_time(pos
);
3636 /* Put the context in a state coherent position */
3637 lttv_state_traceset_seek_time_closest((LttvTracesetState
*)tsc
, ltt_time_zero
);
3639 current_time_change_manager(tab
, new_time
);
3641 set_current_position(tab
, pos
);
3646 on_MEntry5_value_changed (GtkSpinButton
*spinbutton
,
3649 Tab
*tab
= (Tab
*)user_data
;
3650 LttvTracesetContext
* tsc
=
3651 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
);
3652 TimeInterval time_span
= tsc
->time_span
;
3653 gint value
= gtk_spin_button_get_value_as_int(spinbutton
);
3654 LttTime new_current_time
= tab
->current_time
;
3655 new_current_time
.tv_sec
= value
;
3657 /* current nanoseconds */
3658 if(new_current_time
.tv_sec
== time_span
.start_time
.tv_sec
) {
3659 if(new_current_time
.tv_sec
== time_span
.end_time
.tv_sec
) {
3660 if(new_current_time
.tv_nsec
> time_span
.end_time
.tv_nsec
)
3661 new_current_time
.tv_nsec
= time_span
.end_time
.tv_nsec
;
3662 if(new_current_time
.tv_nsec
< time_span
.start_time
.tv_nsec
)
3663 new_current_time
.tv_nsec
= time_span
.start_time
.tv_nsec
;
3665 if(new_current_time
.tv_nsec
< time_span
.start_time
.tv_nsec
)
3666 new_current_time
.tv_nsec
= time_span
.start_time
.tv_nsec
;
3669 else if(new_current_time
.tv_sec
== time_span
.end_time
.tv_sec
) {
3670 if(new_current_time
.tv_nsec
> time_span
.end_time
.tv_nsec
)
3671 new_current_time
.tv_nsec
= time_span
.end_time
.tv_nsec
;
3674 current_time_change_manager(tab
, new_current_time
);
3678 on_MEntry6_value_changed (GtkSpinButton
*spinbutton
,
3681 Tab
*tab
= (Tab
*)user_data
;
3682 gint value
= gtk_spin_button_get_value_as_int(spinbutton
);
3683 LttTime new_current_time
= tab
->current_time
;
3684 new_current_time
.tv_nsec
= value
;
3686 current_time_change_manager(tab
, new_current_time
);
3690 void scroll_value_changed_cb(GtkWidget
*scrollbar
,
3693 Tab
*tab
= (Tab
*)user_data
;
3694 TimeWindow new_time_window
;
3696 GtkAdjustment
*adjust
= gtk_range_get_adjustment(GTK_RANGE(scrollbar
));
3697 gdouble value
= gtk_adjustment_get_value(adjust
);
3698 // gdouble upper, lower, ratio, page_size;
3700 LttvTracesetContext
* tsc
=
3701 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
);
3702 TimeInterval time_span
= tsc
->time_span
;
3704 time
= ltt_time_add(ltt_time_from_double(value
),
3705 time_span
.start_time
);
3707 new_time_window
.start_time
= time
;
3709 page_size
= adjust
->page_size
;
3711 new_time_window
.time_width
=
3712 ltt_time_from_double(page_size
);
3714 new_time_window
.time_width_double
=
3717 new_time_window
.end_time
= ltt_time_add(new_time_window
.start_time
,
3718 new_time_window
.time_width
);
3721 time_change_manager(tab
, new_time_window
);
3723 //time_window = tab->time_window;
3725 lower
= adjust
->lower
;
3726 upper
= adjust
->upper
;
3727 ratio
= (value
- lower
) / (upper
- lower
);
3728 g_info("lower %lu, upper %lu, value %lu, ratio %lu", lower
, upper
, value
, ratio
);
3730 //time = ltt_time_sub(time_span->end_time, time_span->start_time);
3731 //time = ltt_time_mul(time, (float)ratio);
3732 //time = ltt_time_add(time_span->start_time, time);
3733 time
= ltt_time_add(ltt_time_from_double(value
),
3734 time_span
.start_time
);
3736 time_window
.start_time
= time
;
3738 page_size
= adjust
->page_size
;
3740 time_window
.time_width
=
3741 ltt_time_from_double(page_size
);
3742 //time = ltt_time_sub(time_span.end_time, time);
3743 //if(ltt_time_compare(time,time_window.time_width) < 0){
3744 // time_window.time_width = time;
3747 /* call viewer hooks for new time window */
3748 set_time_window(tab
, &time_window
);
3753 /* Display a dialogue showing all eventtypes and traces, let user to select the interested
3754 * eventtypes, tracefiles and traces (filter)
3757 /* Select a trace which will be removed from traceset
3760 char * get_remove_trace(MainWindow
*mw_data
,
3761 char ** all_trace_name
, int nb_trace
)
3763 return get_selection(mw_data
, all_trace_name
, nb_trace
,
3764 "Select a trace", "Trace pathname");
3768 /* Select a module which will be loaded
3771 char * get_load_module(MainWindow
*mw_data
,
3772 char ** load_module_name
, int nb_module
)
3774 return get_selection(mw_data
, load_module_name
, nb_module
,
3775 "Select a module to load", "Module name");
3781 /* Select a module which will be unloaded
3784 char * get_unload_module(MainWindow
*mw_data
,
3785 char ** loaded_module_name
, int nb_module
)
3787 return get_selection(mw_data
, loaded_module_name
, nb_module
,
3788 "Select a module to unload", "Module name");
3792 /* Display a dialogue which shows all selectable items, let user to
3793 * select one of them
3796 char * get_selection(MainWindow
*mw_data
,
3797 char ** loaded_module_name
, int nb_module
,
3798 char *title
, char * column_title
)
3800 GtkWidget
* dialogue
;
3801 GtkWidget
* scroll_win
;
3803 GtkListStore
* store
;
3804 GtkTreeViewColumn
* column
;
3805 GtkCellRenderer
* renderer
;
3806 GtkTreeSelection
* select
;
3809 char * unload_module_name
= NULL
;
3811 dialogue
= gtk_dialog_new_with_buttons(title
,
3814 GTK_STOCK_OK
,GTK_RESPONSE_ACCEPT
,
3815 GTK_STOCK_CANCEL
,GTK_RESPONSE_REJECT
,
3817 gtk_window_set_default_size((GtkWindow
*)dialogue
, 500, 200);
3818 gtk_window_set_transient_for(GTK_WINDOW(dialogue
),
3819 GTK_WINDOW(mw_data
->mwindow
));
3821 scroll_win
= gtk_scrolled_window_new (NULL
, NULL
);
3822 gtk_widget_show ( scroll_win
);
3823 gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(scroll_win
),
3824 GTK_POLICY_AUTOMATIC
, GTK_POLICY_AUTOMATIC
);
3826 store
= gtk_list_store_new (N_COLUMNS
,G_TYPE_STRING
);
3827 tree
= gtk_tree_view_new_with_model(GTK_TREE_MODEL (store
));
3828 gtk_widget_show ( tree
);
3829 g_object_unref (G_OBJECT (store
));
3831 renderer
= gtk_cell_renderer_text_new ();
3832 column
= gtk_tree_view_column_new_with_attributes (column_title
,
3834 "text", MODULE_COLUMN
,
3836 gtk_tree_view_column_set_alignment (column
, 0.5);
3837 gtk_tree_view_column_set_fixed_width (column
, 150);
3838 gtk_tree_view_append_column (GTK_TREE_VIEW (tree
), column
);
3840 select
= gtk_tree_view_get_selection (GTK_TREE_VIEW (tree
));
3841 gtk_tree_selection_set_mode (select
, GTK_SELECTION_SINGLE
);
3843 gtk_container_add (GTK_CONTAINER (scroll_win
), tree
);
3845 gtk_box_pack_start(GTK_BOX(GTK_DIALOG(dialogue
)->vbox
), scroll_win
,TRUE
, TRUE
,0);
3847 for(i
=0;i
<nb_module
;i
++){
3848 gtk_list_store_append (store
, &iter
);
3849 gtk_list_store_set (store
, &iter
, MODULE_COLUMN
,loaded_module_name
[i
],-1);
3852 id
= gtk_dialog_run(GTK_DIALOG(dialogue
));
3853 GtkTreeModel
**store_model
= (GtkTreeModel
**)&store
;
3855 case GTK_RESPONSE_ACCEPT
:
3856 case GTK_RESPONSE_OK
:
3857 if (gtk_tree_selection_get_selected (select
, store_model
, &iter
)){
3858 gtk_tree_model_get ((GtkTreeModel
*)store
, &iter
, MODULE_COLUMN
, &unload_module_name
, -1);
3860 case GTK_RESPONSE_REJECT
:
3861 case GTK_RESPONSE_CANCEL
:
3863 gtk_widget_destroy(dialogue
);
3867 return unload_module_name
;
3871 /* Insert all menu entry and tool buttons into this main window
3876 void add_all_menu_toolbar_constructors(MainWindow
* mw
, gpointer user_data
)
3880 lttvwindow_viewer_constructor constructor
;
3881 LttvMenus
* global_menu
, * instance_menu
;
3882 LttvToolbars
* global_toolbar
, * instance_toolbar
;
3883 LttvMenuClosure
*menu_item
;
3884 LttvToolbarClosure
*toolbar_item
;
3885 LttvAttributeValue value
;
3886 LttvIAttribute
*global_attributes
= LTTV_IATTRIBUTE(lttv_global_attributes());
3887 LttvIAttribute
*attributes
= mw
->attributes
;
3888 GtkWidget
* tool_menu_title_menu
, *new_widget
, *pixmap
;
3890 g_assert(lttv_iattribute_find_by_path(global_attributes
,
3891 "viewers/menu", LTTV_POINTER
, &value
));
3892 if(*(value
.v_pointer
) == NULL
)
3893 *(value
.v_pointer
) = lttv_menus_new();
3894 global_menu
= (LttvMenus
*)*(value
.v_pointer
);
3896 g_assert(lttv_iattribute_find_by_path(attributes
,
3897 "viewers/menu", LTTV_POINTER
, &value
));
3898 if(*(value
.v_pointer
) == NULL
)
3899 *(value
.v_pointer
) = lttv_menus_new();
3900 instance_menu
= (LttvMenus
*)*(value
.v_pointer
);
3904 g_assert(lttv_iattribute_find_by_path(global_attributes
,
3905 "viewers/toolbar", LTTV_POINTER
, &value
));
3906 if(*(value
.v_pointer
) == NULL
)
3907 *(value
.v_pointer
) = lttv_toolbars_new();
3908 global_toolbar
= (LttvToolbars
*)*(value
.v_pointer
);
3910 g_assert(lttv_iattribute_find_by_path(attributes
,
3911 "viewers/toolbar", LTTV_POINTER
, &value
));
3912 if(*(value
.v_pointer
) == NULL
)
3913 *(value
.v_pointer
) = lttv_toolbars_new();
3914 instance_toolbar
= (LttvToolbars
*)*(value
.v_pointer
);
3916 /* Add missing menu entries to window instance */
3917 for(i
=0;i
<global_menu
->len
;i
++) {
3918 menu_item
= &g_array_index(global_menu
, LttvMenuClosure
, i
);
3920 //add menu_item to window instance;
3921 constructor
= menu_item
->con
;
3922 tool_menu_title_menu
= lookup_widget(mw
->mwindow
,"ToolMenuTitle_menu");
3924 gtk_menu_item_new_with_mnemonic (menu_item
->menu_text
);
3925 gtk_container_add (GTK_CONTAINER (tool_menu_title_menu
),
3927 g_signal_connect ((gpointer
) new_widget
, "activate",
3928 G_CALLBACK (insert_viewer_wrap
),
3930 gtk_widget_show (new_widget
);
3931 lttv_menus_add(instance_menu
, menu_item
->con
,
3932 menu_item
->menu_path
,
3933 menu_item
->menu_text
,
3938 /* Add missing toolbar entries to window instance */
3939 for(i
=0;i
<global_toolbar
->len
;i
++) {
3940 toolbar_item
= &g_array_index(global_toolbar
, LttvToolbarClosure
, i
);
3942 //add toolbar_item to window instance;
3943 constructor
= toolbar_item
->con
;
3944 tool_menu_title_menu
= lookup_widget(mw
->mwindow
,"MToolbar1");
3945 pixbuf
= gdk_pixbuf_new_from_xpm_data((const char**)toolbar_item
->pixmap
);
3946 pixmap
= gtk_image_new_from_pixbuf(pixbuf
);
3948 gtk_toolbar_append_element (GTK_TOOLBAR (tool_menu_title_menu
),
3949 GTK_TOOLBAR_CHILD_BUTTON
,
3952 toolbar_item
->tooltip
, NULL
,
3953 pixmap
, NULL
, NULL
);
3954 gtk_label_set_use_underline(
3955 GTK_LABEL (((GtkToolbarChild
*) (
3956 g_list_last (GTK_TOOLBAR
3957 (tool_menu_title_menu
)->children
)->data
))->label
),
3959 gtk_container_set_border_width (GTK_CONTAINER (new_widget
), 1);
3960 g_signal_connect ((gpointer
) new_widget
,
3962 G_CALLBACK (insert_viewer_wrap
),
3964 gtk_widget_show (new_widget
);
3966 lttv_toolbars_add(instance_toolbar
, toolbar_item
->con
,
3967 toolbar_item
->tooltip
,
3968 toolbar_item
->pixmap
,
3976 /* Create a main window
3979 MainWindow
*construct_main_window(MainWindow
* parent
)
3981 g_debug("construct_main_window()");
3982 GtkWidget
* new_window
; /* New generated main window */
3983 MainWindow
* new_m_window
;/* New main window structure */
3984 GtkNotebook
* notebook
;
3985 LttvIAttribute
*attributes
=
3986 LTTV_IATTRIBUTE(g_object_new(LTTV_ATTRIBUTE_TYPE
, NULL
));
3987 LttvAttributeValue value
;
3990 new_m_window
= g_new(MainWindow
, 1);
3992 // Add the object's information to the module's array
3993 g_main_window_list
= g_slist_append(g_main_window_list
, new_m_window
);
3995 new_window
= create_MWindow();
3996 gtk_widget_show (new_window
);
3998 new_m_window
->mwindow
= new_window
;
3999 new_m_window
->attributes
= attributes
;
4001 g_assert(lttv_iattribute_find_by_path(attributes
,
4002 "viewers/menu", LTTV_POINTER
, &value
));
4003 *(value
.v_pointer
) = lttv_menus_new();
4005 g_assert(lttv_iattribute_find_by_path(attributes
,
4006 "viewers/toolbar", LTTV_POINTER
, &value
));
4007 *(value
.v_pointer
) = lttv_toolbars_new();
4009 add_all_menu_toolbar_constructors(new_m_window
, NULL
);
4011 g_object_set_data_full(G_OBJECT(new_window
),
4013 (gpointer
)new_m_window
,
4014 (GDestroyNotify
)g_free
);
4015 //create a default tab
4016 notebook
= (GtkNotebook
*)lookup_widget(new_m_window
->mwindow
, "MNotebook");
4017 if(notebook
== NULL
){
4018 g_info("Notebook does not exist\n");
4019 /* FIXME : destroy partially created widgets */
4020 g_free(new_m_window
);
4023 //gtk_notebook_popup_enable (GTK_NOTEBOOK(notebook));
4024 //for now there is no name field in LttvTraceset structure
4025 //Use "Traceset" as the label for the default tab
4027 GtkWidget
* parent_notebook
= lookup_widget(parent
->mwindow
, "MNotebook");
4028 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(parent_notebook
),
4029 gtk_notebook_get_current_page(GTK_NOTEBOOK(parent_notebook
)));
4035 parent_tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
4037 new_tab
= create_tab(new_m_window
, parent_tab
, notebook
, "Traceset");
4039 new_tab
= create_tab(new_m_window
, NULL
, notebook
, "Traceset");
4042 /* Insert default viewers */
4044 LttvAttributeType type
;
4045 LttvAttributeName name
;
4046 LttvAttributeValue value
;
4047 LttvAttribute
*attribute
;
4049 LttvIAttribute
*attributes_global
=
4050 LTTV_IATTRIBUTE(lttv_global_attributes());
4052 g_assert(attribute
=
4053 LTTV_ATTRIBUTE(lttv_iattribute_find_subdir(
4054 LTTV_IATTRIBUTE(attributes_global
),
4055 LTTV_VIEWER_CONSTRUCTORS
)));
4057 name
= g_quark_from_string("guievents");
4058 type
= lttv_iattribute_get_by_name(LTTV_IATTRIBUTE(attribute
),
4060 if(type
== LTTV_POINTER
) {
4061 lttvwindow_viewer_constructor viewer_constructor
=
4062 (lttvwindow_viewer_constructor
)*value
.v_pointer
;
4063 insert_viewer(new_window
, viewer_constructor
);
4066 name
= g_quark_from_string("guicontrolflow");
4067 type
= lttv_iattribute_get_by_name(LTTV_IATTRIBUTE(attribute
),
4069 if(type
== LTTV_POINTER
) {
4070 lttvwindow_viewer_constructor viewer_constructor
=
4071 (lttvwindow_viewer_constructor
)*value
.v_pointer
;
4072 insert_viewer(new_window
, viewer_constructor
);
4075 name
= g_quark_from_string("guistatistics");
4076 type
= lttv_iattribute_get_by_name(LTTV_IATTRIBUTE(attribute
),
4078 if(type
== LTTV_POINTER
) {
4079 lttvwindow_viewer_constructor viewer_constructor
=
4080 (lttvwindow_viewer_constructor
)*value
.v_pointer
;
4081 insert_viewer(new_window
, viewer_constructor
);
4085 g_info("There are now : %d windows\n",g_slist_length(g_main_window_list
));
4087 return new_m_window
;
4091 /* Free the memory occupied by a tab structure
4095 void tab_destructor(Tab
* tab
)
4097 int i
, nb
, ref_count
;
4100 gtk_object_destroy(GTK_OBJECT(tab
->tooltips
));
4103 g_object_unref(tab
->attributes
);
4105 if(tab
->interrupted_state
)
4106 g_object_unref(tab
->interrupted_state
);
4109 if(tab
->traceset_info
->traceset_context
!= NULL
){
4110 //remove state update hooks
4111 lttv_state_remove_event_hooks(
4112 (LttvTracesetState
*)tab
->traceset_info
->
4114 lttv_context_fini(LTTV_TRACESET_CONTEXT(tab
->traceset_info
->
4116 g_object_unref(tab
->traceset_info
->traceset_context
);
4118 if(tab
->traceset_info
->traceset
!= NULL
) {
4119 nb
= lttv_traceset_number(tab
->traceset_info
->traceset
);
4120 for(i
= 0 ; i
< nb
; i
++) {
4121 trace
= lttv_traceset_get(tab
->traceset_info
->traceset
, i
);
4122 ref_count
= lttv_trace_get_ref_number(trace
);
4124 ltt_trace_close(lttv_trace(trace
));
4128 lttv_filter_destroy(tab
->filter
);
4129 lttv_traceset_destroy(tab
->traceset_info
->traceset
);
4130 /* Remove the idle events requests processing function of the tab */
4131 g_idle_remove_by_data(tab
);
4133 g_slist_free(tab
->events_requests
);
4134 g_free(tab
->traceset_info
);
4139 /* Create a tab and insert it into the current main window
4142 Tab
* create_tab(MainWindow
* mw
, Tab
*copy_tab
,
4143 GtkNotebook
* notebook
, char * label
)
4148 //create a new tab data structure
4151 //construct and initialize the traceset_info
4152 tab
->traceset_info
= g_new(TracesetInfo
,1);
4155 tab
->traceset_info
->traceset
=
4156 lttv_traceset_copy(copy_tab
->traceset_info
->traceset
);
4158 /* Copy the previous tab's filter */
4159 /* We can clone the filter, as we copy the trace set also */
4160 /* The filter must always be in sync with the trace set */
4161 tab
->filter
= lttv_filter_clone(copy_tab
->filter
);
4163 tab
->traceset_info
->traceset
= lttv_traceset_new();
4167 lttv_attribute_write_xml(
4168 lttv_traceset_attribute(tab
->traceset_info
->traceset
),
4174 tab
->time_manager_lock
= FALSE
;
4175 tab
->current_time_manager_lock
= FALSE
;
4177 //FIXME copy not implemented in lower level
4178 tab
->traceset_info
->traceset_context
=
4179 g_object_new(LTTV_TRACESET_STATS_TYPE
, NULL
);
4180 g_assert(tab
->traceset_info
->traceset_context
!= NULL
);
4182 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
),
4183 tab
->traceset_info
->traceset
);
4184 //add state update hooks
4185 lttv_state_add_event_hooks(
4186 (LttvTracesetState
*)tab
->traceset_info
->traceset_context
);
4188 //determine the current_time and time_window of the tab
4190 if(copy_tab
!= NULL
){
4191 tab
->time_window
= copy_tab
->time_window
;
4192 tab
->current_time
= copy_tab
->current_time
;
4194 tab
->time_window
.start_time
=
4195 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
)->
4196 time_span
.start_time
;
4197 if(DEFAULT_TIME_WIDTH_S
<
4198 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
)->
4199 time_span
.end_time
.tv_sec
)
4200 tmp_time
.tv_sec
= DEFAULT_TIME_WIDTH_S
;
4203 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
)->
4204 time_span
.end_time
.tv_sec
;
4205 tmp_time
.tv_nsec
= 0;
4206 tab
->time_window
.time_width
= tmp_time
;
4207 tab
->current_time
.tv_sec
=
4208 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
)->
4209 time_span
.start_time
.tv_sec
;
4210 tab
->current_time
.tv_nsec
=
4211 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
)->
4212 time_span
.start_time
.tv_nsec
;
4215 tab
->attributes
= LTTV_IATTRIBUTE(g_object_new(LTTV_ATTRIBUTE_TYPE
, NULL
));
4216 tab
->interrupted_state
= g_object_new(LTTV_ATTRIBUTE_TYPE
, NULL
);
4218 tab
->vbox
= gtk_vbox_new(FALSE
, 2);
4219 tab
->viewer_container
= gtk_vbox_new(TRUE
, 2);
4220 tab
->scrollbar
= gtk_hscrollbar_new(NULL
);
4221 //tab->multivpaned = gtk_multi_vpaned_new();
4223 gtk_box_pack_start(GTK_BOX(tab
->vbox
),
4224 tab
->viewer_container
,
4226 TRUE
, /* Give the extra space to the child */
4227 0); /* No padding */
4230 // tab->time_window = copy_tab->time_window;
4231 // tab->current_time = copy_tab->current_time;
4234 /* Create the timebar */
4236 tab
->MTimebar
= gtk_hbox_new(FALSE
, 2);
4237 gtk_widget_show(tab
->MTimebar
);
4238 tab
->tooltips
= gtk_tooltips_new();
4240 tab
->MEventBox1a
= gtk_event_box_new();
4241 gtk_widget_show(tab
->MEventBox1a
);
4242 gtk_tooltips_set_tip(tab
->tooltips
, tab
->MEventBox1a
,
4243 "Paste Start and End Times Here", "");
4244 tab
->MText1a
= gtk_label_new("Time Frame ");
4245 gtk_widget_show(tab
->MText1a
);
4246 gtk_container_add(GTK_CONTAINER(tab
->MEventBox1a
), tab
->MText1a
);
4247 tab
->MEventBox1b
= gtk_event_box_new();
4248 gtk_widget_show(tab
->MEventBox1b
);
4249 gtk_tooltips_set_tip(tab
->tooltips
, tab
->MEventBox1b
,
4250 "Paste Start Time Here", "");
4251 tab
->MText1b
= gtk_label_new("start: ");
4252 gtk_widget_show(tab
->MText1b
);
4253 gtk_container_add(GTK_CONTAINER(tab
->MEventBox1b
), tab
->MText1b
);
4254 tab
->MText2
= gtk_label_new("s");
4255 gtk_widget_show(tab
->MText2
);
4256 tab
->MText3a
= gtk_label_new("ns");
4257 gtk_widget_show(tab
->MText3a
);
4258 tab
->MEventBox3b
= gtk_event_box_new();
4259 gtk_widget_show(tab
->MEventBox3b
);
4260 gtk_tooltips_set_tip(tab
->tooltips
, tab
->MEventBox3b
,
4261 "Paste End Time Here", "");
4262 tab
->MText3b
= gtk_label_new("end:");
4263 gtk_widget_show(tab
->MText3b
);
4264 gtk_container_add(GTK_CONTAINER(tab
->MEventBox3b
), tab
->MText3b
);
4265 tab
->MText4
= gtk_label_new("s");
4266 gtk_widget_show(tab
->MText4
);
4267 tab
->MText5a
= gtk_label_new("ns");
4268 gtk_widget_show(tab
->MText5a
);
4269 tab
->MEventBox5b
= gtk_event_box_new();
4270 gtk_widget_show(tab
->MEventBox5b
);
4271 gtk_tooltips_set_tip(tab
->tooltips
, tab
->MEventBox5b
,
4272 "Paste Current Time Here", "");
4273 tab
->MText5b
= gtk_label_new("Current Time:");
4274 gtk_widget_show(tab
->MText5b
);
4275 gtk_container_add(GTK_CONTAINER(tab
->MEventBox5b
), tab
->MText5b
);
4276 tab
->MText6
= gtk_label_new("s");
4277 gtk_widget_show(tab
->MText6
);
4278 tab
->MText7
= gtk_label_new("ns");
4279 gtk_widget_show(tab
->MText7
);
4281 tab
->MEntry1
= gtk_spin_button_new_with_range(0.0, 1.0, 1.0);
4282 gtk_spin_button_set_digits(GTK_SPIN_BUTTON(tab
->MEntry1
),0);
4283 gtk_spin_button_set_snap_to_ticks(GTK_SPIN_BUTTON(tab
->MEntry1
),TRUE
);
4284 gtk_widget_show(tab
->MEntry1
);
4285 tab
->MEntry2
= gtk_spin_button_new_with_range(0.0, 1.0, 1.0);
4286 gtk_spin_button_set_digits(GTK_SPIN_BUTTON(tab
->MEntry2
),0);
4287 gtk_spin_button_set_snap_to_ticks(GTK_SPIN_BUTTON(tab
->MEntry2
),TRUE
);
4288 gtk_widget_show(tab
->MEntry2
);
4289 tab
->MEntry3
= gtk_spin_button_new_with_range(0.0, 1.0, 1.0);
4290 gtk_spin_button_set_digits(GTK_SPIN_BUTTON(tab
->MEntry3
),0);
4291 gtk_spin_button_set_snap_to_ticks(GTK_SPIN_BUTTON(tab
->MEntry3
),TRUE
);
4292 gtk_widget_show(tab
->MEntry3
);
4293 tab
->MEntry4
= gtk_spin_button_new_with_range(0.0, 1.0, 1.0);
4294 gtk_spin_button_set_digits(GTK_SPIN_BUTTON(tab
->MEntry4
),0);
4295 gtk_spin_button_set_snap_to_ticks(GTK_SPIN_BUTTON(tab
->MEntry4
),TRUE
);
4296 gtk_widget_show(tab
->MEntry4
);
4297 tab
->MEntry5
= gtk_spin_button_new_with_range(0.0, 1.0, 1.0);
4298 gtk_spin_button_set_digits(GTK_SPIN_BUTTON(tab
->MEntry5
),0);
4299 gtk_spin_button_set_snap_to_ticks(GTK_SPIN_BUTTON(tab
->MEntry5
),TRUE
);
4300 gtk_widget_show(tab
->MEntry5
);
4301 tab
->MEntry6
= gtk_spin_button_new_with_range(0.0, 1.0, 1.0);
4302 gtk_spin_button_set_digits(GTK_SPIN_BUTTON(tab
->MEntry6
),0);
4303 gtk_spin_button_set_snap_to_ticks(GTK_SPIN_BUTTON(tab
->MEntry6
),TRUE
);
4304 gtk_widget_show(tab
->MEntry6
);
4307 GtkWidget
*temp_widget
;
4309 gtk_box_pack_start (GTK_BOX (tab
->MTimebar
), tab
->MEventBox1a
, FALSE
,
4311 gtk_box_pack_start (GTK_BOX (tab
->MTimebar
), tab
->MEventBox1b
, FALSE
,
4313 gtk_box_pack_start (GTK_BOX (tab
->MTimebar
), tab
->MEntry1
, FALSE
, FALSE
, 0);
4314 gtk_box_pack_start (GTK_BOX (tab
->MTimebar
), tab
->MText2
, FALSE
, FALSE
, 0);
4315 gtk_box_pack_start (GTK_BOX (tab
->MTimebar
), tab
->MEntry2
, FALSE
, FALSE
, 0);
4316 gtk_box_pack_start (GTK_BOX (tab
->MTimebar
), tab
->MText3a
, FALSE
, FALSE
, 0);
4317 temp_widget
= gtk_vseparator_new();
4318 gtk_widget_show(temp_widget
);
4319 gtk_box_pack_start (GTK_BOX (tab
->MTimebar
), temp_widget
, FALSE
, FALSE
, 0);
4320 gtk_box_pack_start (GTK_BOX (tab
->MTimebar
), tab
->MEventBox3b
, FALSE
,
4322 gtk_box_pack_start (GTK_BOX (tab
->MTimebar
), tab
->MEntry3
, FALSE
, FALSE
, 0);
4323 gtk_box_pack_start (GTK_BOX (tab
->MTimebar
), tab
->MText4
, FALSE
, FALSE
, 0);
4324 gtk_box_pack_start (GTK_BOX (tab
->MTimebar
), tab
->MEntry4
, FALSE
, FALSE
, 0);
4325 gtk_box_pack_start (GTK_BOX (tab
->MTimebar
), tab
->MText5a
, FALSE
, FALSE
, 0);
4326 temp_widget
= gtk_vseparator_new();
4327 gtk_widget_show(temp_widget
);
4328 gtk_box_pack_end (GTK_BOX (tab
->MTimebar
), tab
->MText7
, FALSE
, FALSE
, 0);
4329 gtk_box_pack_end (GTK_BOX (tab
->MTimebar
), tab
->MEntry6
, FALSE
, FALSE
, 0);
4330 gtk_box_pack_end (GTK_BOX (tab
->MTimebar
), tab
->MText6
, FALSE
, FALSE
, 0);
4331 gtk_box_pack_end (GTK_BOX (tab
->MTimebar
), tab
->MEntry5
, FALSE
, FALSE
, 0);
4332 gtk_box_pack_end (GTK_BOX (tab
->MTimebar
), tab
->MEventBox5b
, FALSE
,
4334 gtk_box_pack_end (GTK_BOX (tab
->MTimebar
), temp_widget
, FALSE
, FALSE
, 0);
4337 //GtkWidget *test = gtk_button_new_with_label("drop");
4338 //gtk_button_set_relief(GTK_BUTTON(test), GTK_RELIEF_NONE);
4339 //gtk_widget_show(test);
4340 //gtk_box_pack_end(GTK_BOX (tab->MTimebar), test, FALSE, FALSE, 0);
4341 //gtk_widget_add_events(tab->MText1, GDK_ALL_EVENTS_MASK);//GDK_BUTTON_PRESS_MASK);
4342 /*GtkWidget *event_box = gtk_event_box_new();
4343 gtk_widget_show(event_box);
4344 gtk_tooltips_set_tip(tooltips, event_box,
4345 "Paste Current Time Here", "");
4346 gtk_box_pack_end(GTK_BOX (tab->MTimebar), event_box, FALSE, FALSE, 0);
4347 GtkWidget *test = gtk_label_new("drop");
4348 gtk_container_add(GTK_CONTAINER(event_box), test);
4349 gtk_widget_show(test);
4350 g_signal_connect (G_OBJECT(event_box),
4351 "button-press-event",
4352 G_CALLBACK (on_MText1_paste),
4356 g_signal_connect (G_OBJECT(tab
->MEventBox1a
),
4357 "button-press-event",
4358 G_CALLBACK (on_MEventBox1a_paste
),
4361 g_signal_connect (G_OBJECT(tab
->MEventBox1b
),
4362 "button-press-event",
4363 G_CALLBACK (on_MEventBox1b_paste
),
4365 g_signal_connect (G_OBJECT(tab
->MEventBox3b
),
4366 "button-press-event",
4367 G_CALLBACK (on_MEventBox3b_paste
),
4369 g_signal_connect (G_OBJECT(tab
->MEventBox5b
),
4370 "button-press-event",
4371 G_CALLBACK (on_MEventBox5b_paste
),
4375 gtk_box_pack_end(GTK_BOX(tab
->vbox
),
4377 FALSE
, /* Do not expand */
4378 FALSE
, /* Fill has no effect here (expand false) */
4379 0); /* No padding */
4381 gtk_box_pack_end(GTK_BOX(tab
->vbox
),
4383 FALSE
, /* Do not expand */
4384 FALSE
, /* Fill has no effect here (expand false) */
4385 0); /* No padding */
4387 g_object_set_data(G_OBJECT(tab
->viewer_container
), "focused_viewer", NULL
);
4393 // Display a label with a X
4394 GtkWidget *w_hbox = gtk_hbox_new(FALSE, 4);
4395 GtkWidget *w_label = gtk_label_new (label);
4396 GtkWidget *pixmap = create_pixmap(GTK_WIDGET(notebook), "close.png");
4397 GtkWidget *w_button = gtk_button_new ();
4398 gtk_container_add(GTK_CONTAINER(w_button), pixmap);
4399 //GtkWidget *w_button = gtk_button_new_with_label("x");
4401 gtk_button_set_relief(GTK_BUTTON(w_button), GTK_RELIEF_NONE);
4403 gtk_box_pack_start(GTK_BOX(w_hbox), w_label, TRUE, TRUE, 0);
4404 gtk_box_pack_end(GTK_BOX(w_hbox), w_button, FALSE,
4407 g_signal_connect_swapped (w_button, "clicked",
4408 G_CALLBACK (on_close_tab_X_clicked),
4411 gtk_widget_set_state(w_button, GTK_STATE_ACTIVE);
4413 gtk_widget_show (w_label);
4414 gtk_widget_show (pixmap);
4415 gtk_widget_show (w_button);
4416 gtk_widget_show (w_hbox);
4418 tab->label = w_hbox;
4422 tab
->label
= gtk_label_new (label
);
4424 gtk_widget_show(tab
->label
);
4425 gtk_widget_show(tab
->scrollbar
);
4426 gtk_widget_show(tab
->viewer_container
);
4427 gtk_widget_show(tab
->vbox
);
4428 //gtk_widget_show(tab->multivpaned);
4431 /* Start with empty events requests list */
4432 tab
->events_requests
= NULL
;
4433 tab
->events_request_pending
= FALSE
;
4435 g_object_set_data_full(
4436 G_OBJECT(tab
->vbox
),
4439 (GDestroyNotify
)tab_destructor
);
4441 g_signal_connect(G_OBJECT(tab
->scrollbar
), "value-changed",
4442 G_CALLBACK(scroll_value_changed_cb
), tab
);
4444 g_signal_connect ((gpointer
) tab
->MEntry1
, "value-changed",
4445 G_CALLBACK (on_MEntry1_value_changed
),
4447 g_signal_connect ((gpointer
) tab
->MEntry2
, "value-changed",
4448 G_CALLBACK (on_MEntry2_value_changed
),
4450 g_signal_connect ((gpointer
) tab
->MEntry3
, "value-changed",
4451 G_CALLBACK (on_MEntry3_value_changed
),
4453 g_signal_connect ((gpointer
) tab
->MEntry4
, "value-changed",
4454 G_CALLBACK (on_MEntry4_value_changed
),
4456 g_signal_connect ((gpointer
) tab
->MEntry5
, "value-changed",
4457 G_CALLBACK (on_MEntry5_value_changed
),
4459 g_signal_connect ((gpointer
) tab
->MEntry6
, "value-changed",
4460 G_CALLBACK (on_MEntry6_value_changed
),
4463 //g_signal_connect(G_OBJECT(tab->scrollbar), "changed",
4464 // G_CALLBACK(scroll_value_changed_cb), tab);
4467 //insert tab into notebook
4468 gtk_notebook_append_page(notebook
,
4471 list
= gtk_container_get_children(GTK_CONTAINER(notebook
));
4472 gtk_notebook_set_current_page(notebook
,g_list_length(list
)-1);
4473 // always show : not if(g_list_length(list)>1)
4474 gtk_notebook_set_show_tabs(notebook
, TRUE
);
4477 lttvwindow_report_time_window(tab
, copy_tab
->time_window
);
4478 lttvwindow_report_current_time(tab
, copy_tab
->current_time
);
4480 TimeWindow time_window
;
4482 time_window
.start_time
= ltt_time_zero
;
4483 time_window
.end_time
= ltt_time_add(time_window
.start_time
,
4484 lttvwindow_default_time_width
);
4485 time_window
.time_width
= lttvwindow_default_time_width
;
4486 time_window
.time_width_double
= ltt_time_to_double(time_window
.time_width
);
4488 lttvwindow_report_time_window(tab
, time_window
);
4489 lttvwindow_report_current_time(tab
, ltt_time_zero
);
4492 LttvTraceset
*traceset
= tab
->traceset_info
->traceset
;
4493 SetTraceset(tab
, traceset
);
4499 * execute_events_requests
4501 * Idle function that executes the pending requests for a tab.
4503 * @return return value : TRUE : keep the idle function, FALSE : remove it.
4505 gboolean
execute_events_requests(Tab
*tab
)
4507 return ( lttvwindow_process_pending_requests(tab
) );
4511 void create_main_window_with_trace(gchar
*path
)
4513 if(path
== NULL
) return;
4516 MainWindow
*mw
= construct_main_window(NULL
);
4517 GtkWidget
*widget
= mw
->mwindow
;
4519 GtkWidget
* notebook
= lookup_widget(widget
, "MNotebook");
4520 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook
),
4521 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
)));
4525 tab
= create_new_tab(widget
, NULL
);
4527 tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
4531 gchar abs_path
[PATH_MAX
];
4535 get_absolute_pathname(path
, abs_path
);
4536 trace_v
= lttvwindowtraces_get_trace_by_name(abs_path
);
4537 if(trace_v
== NULL
) {
4538 trace
= ltt_trace_open(abs_path
);
4540 g_warning("cannot open trace %s", abs_path
);
4542 GtkWidget
*dialogue
=
4543 gtk_message_dialog_new(
4544 GTK_WINDOW(gtk_widget_get_toplevel(widget
)),
4545 GTK_DIALOG_MODAL
|GTK_DIALOG_DESTROY_WITH_PARENT
,
4548 "Cannot open trace : maybe you should enter in the directory"
4550 gtk_dialog_run(GTK_DIALOG(dialogue
));
4551 gtk_widget_destroy(dialogue
);
4553 trace_v
= lttv_trace_new(trace
);
4554 lttvwindowtraces_add_trace(trace_v
);
4555 lttvwindow_add_trace(tab
, trace_v
);
4558 lttvwindow_add_trace(tab
, trace_v
);
4561 LttvTraceset
*traceset
;
4563 traceset
= tab
->traceset_info
->traceset
;
4564 SetTraceset(tab
, traceset
);