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
28 #include "callbacks.h"
29 #include "interface.h"
31 #include <ltt/trace.h>
32 #include <ltt/facility.h>
34 #include <ltt/event.h>
35 #include <lttv/lttv.h>
36 #include <lttv/module.h>
37 #include <lttv/iattribute.h>
38 #include <lttv/stats.h>
39 #include <lttvwindow/mainwindow.h>
40 #include <lttvwindow/mainwindow-private.h>
41 #include <lttvwindow/menu.h>
42 #include <lttvwindow/toolbar.h>
43 #include <lttvwindow/lttvwindow.h>
44 #include <lttvwindow/lttvwindowtraces.h>
45 #include <lttvwindow/gtkdirsel.h>
46 #include <lttvwindow/lttvfilter.h>
49 #define DEFAULT_TIME_WIDTH_S 1
51 extern LttvTrace
*g_init_trace
;
54 /** Array containing instanced objects. */
55 extern GSList
* g_main_window_list
;
57 /** MD : keep old directory. */
58 static char remember_plugins_dir
[PATH_MAX
] = "";
59 static char remember_trace_dir
[PATH_MAX
] = "";
62 MainWindow
* get_window_data_struct(GtkWidget
* widget
);
63 char * get_load_module(char ** load_module_name
, int nb_module
);
64 char * get_unload_module(char ** loaded_module_name
, int nb_module
);
65 char * get_remove_trace(char ** all_trace_name
, int nb_trace
);
66 char * get_selection(char ** all_name
, int nb
, char *title
, char * column_title
);
67 gboolean
get_filter_selection(LttvTracesetSelector
*s
, char *title
, char * column_title
);
68 Tab
* create_tab(MainWindow
* mw
, Tab
*copy_tab
,
69 GtkNotebook
* notebook
, char * label
);
71 static void insert_viewer(GtkWidget
* widget
, lttvwindow_viewer_constructor constructor
);
72 void update_filter(LttvTracesetSelector
*s
, GtkTreeStore
*store
);
74 void checkbox_changed(GtkTreeView
*treeview
,
76 GtkTreeViewColumn
*arg2
,
78 void remove_trace_from_traceset_selector(GtkWidget
* paned
, unsigned i
);
79 void add_trace_into_traceset_selector(GtkWidget
* paned
, LttTrace
* trace
);
80 Tab
*create_new_tab(GtkWidget
* widget
, gpointer user_data
);
82 LttvTracesetSelector
* construct_traceset_selector(LttvTraceset
* traceset
);
84 static gboolean
lttvwindow_process_pending_requests(Tab
*tab
);
98 /* Construct a selector(filter), which will be associated with a viewer,
99 * and provides an interface for user to select interested events and traces
102 LttvTracesetSelector
* construct_traceset_selector(LttvTraceset
* traceset
)
104 LttvTracesetSelector
* s
;
105 LttvTraceSelector
* trace
;
106 LttvTracefileSelector
* tracefile
;
107 LttvEventtypeSelector
* eventtype
;
109 int nb_trace
, nb_tracefile
, nb_control
, nb_per_cpu
, nb_facility
, nb_event
;
116 s
= lttv_traceset_selector_new(lttv_traceset_name(traceset
));
117 nb_trace
= lttv_traceset_number(traceset
);
118 for(i
=0;i
<nb_trace
;i
++){
119 trace_v
= lttv_traceset_get(traceset
, i
);
120 t
= lttv_trace(trace_v
);
121 trace
= lttv_trace_selector_new(t
);
122 lttv_traceset_selector_trace_add(s
, trace
);
124 nb_facility
= ltt_trace_facility_number(t
);
125 for(k
=0;k
<nb_facility
;k
++){
126 fac
= ltt_trace_facility_get(t
,k
);
127 nb_event
= (int) ltt_facility_eventtype_number(fac
);
128 for(m
=0;m
<nb_event
;m
++){
129 et
= ltt_facility_eventtype_get(fac
,m
);
130 eventtype
= lttv_eventtype_selector_new(et
);
131 lttv_trace_selector_eventtype_add(trace
, eventtype
);
135 nb_control
= ltt_trace_control_tracefile_number(t
);
136 nb_per_cpu
= ltt_trace_per_cpu_tracefile_number(t
);
137 nb_tracefile
= nb_control
+ nb_per_cpu
;
139 for(j
= 0 ; j
< nb_tracefile
; j
++) {
141 tf
= ltt_trace_control_tracefile_get(t
, j
);
143 tf
= ltt_trace_per_cpu_tracefile_get(t
, j
- nb_control
);
144 tracefile
= lttv_tracefile_selector_new(tf
);
145 lttv_trace_selector_tracefile_add(trace
, tracefile
);
146 lttv_eventtype_selector_copy(trace
, tracefile
);
153 static gboolean
viewer_grab_focus(GtkWidget
*widget
, GdkEventButton
*event
,
156 GtkWidget
*viewer_container
= GTK_WIDGET(data
);
158 g_debug("FOCUS GRABBED");
159 g_object_set_data(G_OBJECT(viewer_container
), "focused_viewer", widget
);
163 /* insert_viewer function constructs an instance of a viewer first,
164 * then inserts the widget of the instance into the container of the
169 insert_viewer_wrap(GtkWidget
*menuitem
, gpointer user_data
)
173 insert_viewer((GtkWidget
*)menuitem
, (lttvwindow_viewer_constructor
)user_data
);
174 // selected_hook(&val);
178 /* internal functions */
179 void insert_viewer(GtkWidget
* widget
, lttvwindow_viewer_constructor constructor
)
181 GtkWidget
* viewer_container
;
182 MainWindow
* mw_data
= get_window_data_struct(widget
);
183 GtkWidget
* notebook
= lookup_widget(widget
, "MNotebook");
185 LttvTracesetSelector
* s
;
186 TimeInterval
* time_interval
;
187 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook
),
188 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
)));
192 tab
= create_new_tab(widget
, NULL
);
194 tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
197 viewer_container
= tab
->viewer_container
;
199 s
= construct_traceset_selector(tab
->traceset_info
->traceset
);
200 viewer
= (GtkWidget
*)constructor(tab
, s
, "Traceset_Selector");
203 //gtk_multivpaned_widget_add(GTK_MULTIVPANED(multivpaned), viewer);
205 gtk_box_pack_end(GTK_BOX(viewer_container
),
211 g_signal_connect (G_OBJECT(viewer
),
212 "button-press-event",
213 G_CALLBACK (viewer_grab_focus
),
214 (gpointer
)viewer_container
);
216 // We unref here, because it is now referenced by the viewer_container!
217 // not for a box ... g_object_unref(G_OBJECT(viewer));
219 // The viewer will show itself when it receives a show notify
220 // So we call the show notify hooks here. It will
221 // typically add hooks for reading, we call process trace, and the
222 // end of reading hook will call gtk_widget_show and unregister the
224 // Note that show notify gets the time_requested through the call_data.
225 //show_viewer(mw_data);
226 // in expose now call_pending_read_hooks(mw_data);
231 * Function to set/update traceset for the viewers
232 * @param tab viewer's tab
233 * @param traceset traceset of the main window.
235 * 0 : traceset updated
236 * 1 : no traceset hooks to update; not an error.
239 int SetTraceset(Tab
* tab
, LttvTraceset
*traceset
)
241 LttvTracesetContext
*tsc
=
242 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
);
243 TimeInterval time_span
= tsc
->time_span
;
244 TimeWindow new_time_window
;
245 LttTime new_current_time
;
247 /* Set the tab's time window and current time if
249 if(ltt_time_compare(tab
->time_window
.start_time
, time_span
.start_time
) < 0
250 || ltt_time_compare( ltt_time_add(tab
->time_window
.start_time
,
251 tab
->time_window
.time_width
),
252 time_span
.end_time
) > 0) {
253 new_time_window
.start_time
= time_span
.start_time
;
255 new_current_time
= time_span
.start_time
;
259 if(DEFAULT_TIME_WIDTH_S
< time_span
.end_time
.tv_sec
)
260 tmp_time
.tv_sec
= DEFAULT_TIME_WIDTH_S
;
262 tmp_time
.tv_sec
= time_span
.end_time
.tv_sec
;
263 tmp_time
.tv_nsec
= 0;
264 new_time_window
.time_width
= tmp_time
;
266 time_change_manager(tab
, new_time_window
);
267 current_time_change_manager(tab
, new_current_time
);
271 GtkAdjustment
*adjustment
= gtk_range_get_adjustment(GTK_RANGE(tab
->scrollbar
));
272 LttTime upper
= ltt_time_sub(time_span
.end_time
, time_span
.start_time
);
274 g_object_set(G_OBJECT(adjustment
),
278 ltt_time_to_double(upper
)
279 * NANOSECONDS_PER_SECOND
, /* upper */
281 ltt_time_to_double(tab
->time_window
.time_width
)
282 / SCROLL_STEP_PER_PAGE
283 * NANOSECONDS_PER_SECOND
, /* step increment */
285 ltt_time_to_double(tab
->time_window
.time_width
)
286 * NANOSECONDS_PER_SECOND
, /* page increment */
288 ltt_time_to_double(tab
->time_window
.time_width
)
289 * NANOSECONDS_PER_SECOND
, /* page size */
291 gtk_adjustment_changed(adjustment
);
293 g_object_set(G_OBJECT(adjustment
),
296 ltt_time_sub(tab
->time_window
.start_time
, time_span
.start_time
))
297 * NANOSECONDS_PER_SECOND
, /* value */
299 gtk_adjustment_value_changed(adjustment
);
301 /* set the time bar. The value callbacks will change their nsec themself */
303 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry1
),
304 (double)time_span
.start_time
.tv_sec
,
305 (double)time_span
.end_time
.tv_sec
);
308 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry3
),
309 (double)time_span
.start_time
.tv_sec
,
310 (double)time_span
.end_time
.tv_sec
);
312 /* current seconds */
313 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry5
),
314 (double)time_span
.start_time
.tv_sec
,
315 (double)time_span
.end_time
.tv_sec
);
318 /* Finally, call the update hooks of the viewers */
320 LttvAttributeValue value
;
324 g_assert( lttv_iattribute_find_by_path(tab
->attributes
,
325 "hooks/updatetraceset", LTTV_POINTER
, &value
));
327 tmp
= (LttvHooks
*)*(value
.v_pointer
);
328 if(tmp
== NULL
) retval
= 1;
329 else lttv_hooks_call(tmp
,traceset
);
336 * Function to set/update filter for the viewers
337 * @param tab viewer's tab
338 * @param filter filter of the main window.
341 * 0 : filters updated
342 * 1 : no filter hooks to update; not an error.
345 int SetFilter(Tab
* tab
, gpointer filter
)
348 LttvAttributeValue value
;
350 g_assert(lttv_iattribute_find_by_path(tab
->attributes
,
351 "hooks/updatefilter", LTTV_POINTER
, &value
));
353 tmp
= (LttvHooks
*)*(value
.v_pointer
);
355 if(tmp
== NULL
) return 1;
356 lttv_hooks_call(tmp
,filter
);
364 * Function to redraw each viewer belonging to the current tab
365 * @param tab viewer's tab
368 void update_traceset(Tab
*tab
)
370 LttvAttributeValue value
;
372 g_assert(lttv_iattribute_find_by_path(tab
->attributes
,
373 "hooks/updatetraceset", LTTV_POINTER
, &value
));
374 tmp
= (LttvHooks
*)*(value
.v_pointer
);
375 if(tmp
== NULL
) return;
376 lttv_hooks_call(tmp
, NULL
);
380 /* get_label function is used to get user input, it displays an input
381 * box, which allows user to input a string
384 void get_label_string (GtkWidget
* text
, gchar
* label
)
386 GtkEntry
* entry
= (GtkEntry
*)text
;
387 if(strlen(gtk_entry_get_text(entry
))!=0)
388 strcpy(label
,gtk_entry_get_text(entry
));
391 gboolean
get_label(MainWindow
* mw
, gchar
* str
, gchar
* dialogue_title
, gchar
* label_str
)
393 GtkWidget
* dialogue
;
398 dialogue
= gtk_dialog_new_with_buttons(dialogue_title
,NULL
,
400 GTK_STOCK_OK
,GTK_RESPONSE_ACCEPT
,
401 GTK_STOCK_CANCEL
,GTK_RESPONSE_REJECT
,
404 label
= gtk_label_new(label_str
);
405 gtk_widget_show(label
);
407 text
= gtk_entry_new();
408 gtk_widget_show(text
);
410 gtk_box_pack_start(GTK_BOX(GTK_DIALOG(dialogue
)->vbox
), label
,TRUE
, TRUE
,0);
411 gtk_box_pack_start(GTK_BOX(GTK_DIALOG(dialogue
)->vbox
), text
,FALSE
, FALSE
,0);
413 id
= gtk_dialog_run(GTK_DIALOG(dialogue
));
415 case GTK_RESPONSE_ACCEPT
:
416 get_label_string(text
,str
);
417 gtk_widget_destroy(dialogue
);
419 case GTK_RESPONSE_REJECT
:
421 gtk_widget_destroy(dialogue
);
428 /* get_window_data_struct function is actually a lookup function,
429 * given a widget which is in the tree of the main window, it will
430 * return the MainWindow data structure associated with main window
433 MainWindow
* get_window_data_struct(GtkWidget
* widget
)
436 MainWindow
* mw_data
;
438 mw
= lookup_widget(widget
, "MWindow");
440 g_printf("Main window does not exist\n");
444 mw_data
= (MainWindow
*) g_object_get_data(G_OBJECT(mw
),"main_window_data");
446 g_printf("Main window data does not exist\n");
453 /* create_new_window function, just constructs a new main window
456 void create_new_window(GtkWidget
* widget
, gpointer user_data
, gboolean clone
)
458 MainWindow
* parent
= get_window_data_struct(widget
);
461 g_printf("Clone : use the same traceset\n");
462 construct_main_window(parent
);
464 g_printf("Empty : traceset is set to NULL\n");
465 construct_main_window(NULL
);
469 GtkWidget
*viewer_container_focus(GtkWidget
*container
)
473 widget
= (GtkWidget
*)g_object_get_data(G_OBJECT(container
),
476 if(widget
== NULL
) g_debug("no widget focused");
482 gint
viewer_container_position(GtkWidget
*container
, GtkWidget
*child
)
485 if(child
== NULL
) return -1;
488 GValue value
= { 0, };
489 g_value_init(&value
, G_TYPE_INT
);
490 gtk_container_child_get_property(GTK_CONTAINER(container
),
494 pos
= g_value_get_int(&value
);
500 /* move_*_viewer functions move the selected view up/down in
504 void move_down_viewer(GtkWidget
* widget
, gpointer user_data
)
506 MainWindow
* mw
= get_window_data_struct(widget
);
507 GtkWidget
* notebook
= lookup_widget(widget
, "MNotebook");
509 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook
),
510 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
)));
516 tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
519 //gtk_multivpaned_widget_move_up(GTK_MULTIVPANED(tab->multivpaned));
521 /* change the position in the vbox */
522 GtkWidget
*focus_widget
;
524 focus_widget
= viewer_container_focus(tab
->viewer_container
);
525 position
= viewer_container_position(tab
->viewer_container
, focus_widget
);
528 /* can move up one position */
529 gtk_box_reorder_child(GTK_BOX(tab
->viewer_container
),
536 void move_up_viewer(GtkWidget
* widget
, gpointer user_data
)
538 MainWindow
* mw
= get_window_data_struct(widget
);
539 GtkWidget
* notebook
= lookup_widget(widget
, "MNotebook");
541 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook
),
542 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
)));
548 tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
551 //gtk_multivpaned_widget_move_down(GTK_MULTIVPANED(tab->multivpaned));
552 /* change the position in the vbox */
553 GtkWidget
*focus_widget
;
555 focus_widget
= viewer_container_focus(tab
->viewer_container
);
556 position
= viewer_container_position(tab
->viewer_container
, focus_widget
);
560 g_list_length(gtk_container_get_children(
561 GTK_CONTAINER(tab
->viewer_container
)))-1
563 /* can move down one position */
564 gtk_box_reorder_child(GTK_BOX(tab
->viewer_container
),
572 /* delete_viewer deletes the selected viewer in the current tab
575 void delete_viewer(GtkWidget
* widget
, gpointer user_data
)
577 MainWindow
* mw
= get_window_data_struct(widget
);
578 GtkWidget
* notebook
= lookup_widget(widget
, "MNotebook");
580 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook
),
581 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
)));
587 tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
590 //gtk_multivpaned_widget_delete(GTK_MULTIVPANED(tab->multivpaned));
592 GtkWidget
*focus_widget
= viewer_container_focus(tab
->viewer_container
);
594 if(focus_widget
!= NULL
)
595 gtk_widget_destroy(focus_widget
);
597 g_object_set_data(G_OBJECT(tab
->viewer_container
), "focused_viewer", NULL
);
601 /* open_traceset will open a traceset saved in a file
602 * Right now, it is not finished yet, (not working)
606 void open_traceset(GtkWidget
* widget
, gpointer user_data
)
610 LttvTraceset
* traceset
;
611 MainWindow
* mw_data
= get_window_data_struct(widget
);
612 GtkFileSelection
* file_selector
=
613 (GtkFileSelection
*)gtk_file_selection_new("Select a traceset");
615 gtk_file_selection_hide_fileop_buttons(file_selector
);
617 id
= gtk_dialog_run(GTK_DIALOG(file_selector
));
619 case GTK_RESPONSE_ACCEPT
:
620 case GTK_RESPONSE_OK
:
621 dir
= gtk_file_selection_get_selections (file_selector
);
622 traceset
= lttv_traceset_load(dir
[0]);
623 g_printf("Open a trace set %s\n", dir
[0]);
626 case GTK_RESPONSE_REJECT
:
627 case GTK_RESPONSE_CANCEL
:
629 gtk_widget_destroy((GtkWidget
*)file_selector
);
635 static void events_request_free(EventsRequest
*events_request
)
637 if(events_request
== NULL
) return;
639 if(events_request
->start_position
!= NULL
)
640 lttv_traceset_context_position_destroy(events_request
->start_position
);
641 if(events_request
->end_position
!= NULL
)
642 lttv_traceset_context_position_destroy(events_request
->end_position
);
643 if(events_request
->before_chunk_traceset
!= NULL
)
644 lttv_hooks_destroy(events_request
->before_chunk_traceset
);
645 if(events_request
->before_chunk_trace
!= NULL
)
646 lttv_hooks_destroy(events_request
->before_chunk_trace
);
647 if(events_request
->before_chunk_tracefile
!= NULL
)
648 lttv_hooks_destroy(events_request
->before_chunk_tracefile
);
649 if(events_request
->event
!= NULL
)
650 lttv_hooks_destroy(events_request
->event
);
651 if(events_request
->event_by_id
!= NULL
)
652 lttv_hooks_by_id_destroy(events_request
->event_by_id
);
653 if(events_request
->after_chunk_tracefile
!= NULL
)
654 lttv_hooks_destroy(events_request
->after_chunk_tracefile
);
655 if(events_request
->after_chunk_trace
!= NULL
)
656 lttv_hooks_destroy(events_request
->after_chunk_trace
);
657 if(events_request
->after_chunk_traceset
!= NULL
)
658 lttv_hooks_destroy(events_request
->after_chunk_traceset
);
659 if(events_request
->before_request
!= NULL
)
660 lttv_hooks_destroy(events_request
->before_request
);
661 if(events_request
->after_request
!= NULL
)
662 lttv_hooks_destroy(events_request
->after_request
);
664 g_free(events_request
);
669 /* lttvwindow_process_pending_requests
671 * This internal function gets called by g_idle, taking care of the pending
672 * requests. It is responsible for concatenation of time intervals and position
673 * requests. It does it with the following algorithm organizing process traceset
674 * calls. Here is the detailed description of the way it works :
676 * - Events Requests Servicing Algorithm
678 * Data structures necessary :
680 * List of requests added to context : list_in
681 * List of requests not added to context : list_out
686 * list_out : many events requests
688 * FIXME : insert rest of algorithm here
692 #define list_out tab->events_requests
694 gboolean
lttvwindow_process_pending_requests(Tab
*tab
)
696 unsigned max_nb_events
;
700 LttvTracesetContext
*tsc
;
701 LttvTracefileContext
*tfc
;
702 GSList
*list_in
= NULL
;
706 LttvTracesetContextPosition
*end_position
;
709 g_critical("Foreground processing : tab does not exist. Processing removed.");
713 /* There is no events requests pending : we should never have been called! */
714 g_assert(g_slist_length(list_out
) != 0);
716 tsc
= LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
);
718 //set the cursor to be X shape, indicating that the computer is busy in doing its job
720 new = gdk_cursor_new(GDK_X_CURSOR
);
721 widget
= lookup_widget(tab
->mw
->mwindow
, "MToolbar1");
722 win
= gtk_widget_get_parent_window(widget
);
723 gdk_window_set_cursor(win
, new);
724 gdk_cursor_unref(new);
725 gdk_window_stick(win
);
726 gdk_window_unstick(win
);
729 g_debug("SIZE events req len : %d", g_slist_length(list_out
));
731 /* Preliminary check for no trace in traceset */
732 /* Unregister the routine if empty, empty list_out too */
733 if(lttv_traceset_number(tsc
->ts
) == 0) {
735 /* - For each req in list_out */
736 GSList
*iter
= list_out
;
738 while(iter
!= NULL
) {
740 gboolean remove
= FALSE
;
741 gboolean free_data
= FALSE
;
742 EventsRequest
*events_request
= (EventsRequest
*)iter
->data
;
744 /* - Call end request for req */
745 if(events_request
->servicing
== TRUE
)
746 lttv_hooks_call(events_request
->after_request
, (gpointer
)tsc
);
748 /* - remove req from list_out */
749 /* Destroy the request */
756 GSList
*remove_iter
= iter
;
758 iter
= g_slist_next(iter
);
759 if(free_data
) events_request_free((EventsRequest
*)remove_iter
->data
);
760 list_out
= g_slist_remove_link(list_out
, remove_iter
);
761 } else { // not remove
762 iter
= g_slist_next(iter
);
767 /* 0.1 Lock Traces */
772 iter_trace
<lttv_traceset_number(tsc
->ts
);
774 LttvTrace
*trace_v
= lttv_traceset_get(tsc
->ts
, iter_trace
);
776 if(lttvwindowtraces_lock(trace_v
) != 0) {
777 g_critical("Foreground processing : Unable to get trace lock");
778 return TRUE
; /* Cannot get lock, try later */
783 /* 0.2 Seek tracefiles positions to context position */
784 lttv_process_traceset_synchronize_tracefiles(tsc
);
787 /* Events processing algorithm implementation */
788 /* Warning : the gtk_events_pending takes a LOT of cpu time. So what we do
789 * instead is to leave the control to GTK and take it back.
791 /* A. Servicing loop */
792 //while( (g_slist_length(list_in) != 0 || g_slist_length(list_out) != 0)) {
793 if((g_slist_length(list_in
) != 0 || g_slist_length(list_out
) != 0)) {
795 /* 1. If list_in is empty (need a seek) */
796 if( g_slist_length(list_in
) == 0 ) {
798 /* list in is empty, need a seek */
800 /* 1.1 Add requests to list_in */
801 GSList
*ltime
= NULL
;
805 /* 1.1.1 Find all time requests with the lowest start time in list_out
808 if(g_slist_length(list_out
) > 0)
809 ltime
= g_slist_append(ltime
, g_slist_nth_data(list_out
, 0));
810 for(iter
=g_slist_nth(list_out
,1);iter
!=NULL
;iter
=g_slist_next(iter
)) {
811 /* Find all time requests with the lowest start time in list_out */
812 guint index_ltime
= g_array_index(ltime
, guint
, 0);
813 EventsRequest
*event_request_ltime
= (EventsRequest
*)g_slist_nth_data(ltime
, 0);
814 EventsRequest
*event_request_list_out
= (EventsRequest
*)iter
->data
;
817 comp
= ltt_time_compare(event_request_ltime
->start_time
,
818 event_request_list_out
->start_time
);
820 ltime
= g_slist_append(ltime
, event_request_list_out
);
822 /* Remove all elements from ltime, and add current */
824 ltime
= g_slist_delete_link(ltime
, g_slist_nth(ltime
, 0));
825 ltime
= g_slist_append(ltime
, event_request_list_out
);
829 /* 1.1.2 Find all position requests with the lowest position in list_out
832 if(g_slist_length(list_out
) > 0)
833 lpos
= g_slist_append(lpos
, g_slist_nth_data(list_out
, 0));
834 for(iter
=g_slist_nth(list_out
,1);iter
!=NULL
;iter
=g_slist_next(iter
)) {
835 /* Find all position requests with the lowest position in list_out */
836 EventsRequest
*event_request_lpos
= (EventsRequest
*)g_slist_nth_data(lpos
, 0);
837 EventsRequest
*event_request_list_out
= (EventsRequest
*)iter
->data
;
840 if(event_request_lpos
->start_position
!= NULL
841 && event_request_list_out
->start_position
!= NULL
)
843 comp
= lttv_traceset_context_pos_pos_compare
844 (event_request_lpos
->start_position
,
845 event_request_list_out
->start_position
);
850 lpos
= g_slist_append(lpos
, event_request_list_out
);
852 /* Remove all elements from lpos, and add current */
854 lpos
= g_slist_delete_link(lpos
, g_slist_nth(lpos
, 0));
855 lpos
= g_slist_append(lpos
, event_request_list_out
);
860 EventsRequest
*event_request_lpos
= (EventsRequest
*)g_slist_nth_data(lpos
, 0);
861 EventsRequest
*event_request_ltime
= (EventsRequest
*)g_slist_nth_data(ltime
, 0);
862 LttTime lpos_start_time
;
864 if(event_request_lpos
!= NULL
865 && event_request_lpos
->start_position
!= NULL
) {
866 lpos_start_time
= lttv_traceset_context_position_get_time(
867 event_request_lpos
->start_position
);
870 /* 1.1.3 If lpos.start time < ltime */
871 if(event_request_lpos
!= NULL
872 && event_request_lpos
->start_position
!= NULL
873 && ltt_time_compare(lpos_start_time
,
874 event_request_ltime
->start_time
)<0) {
875 /* Add lpos to list_in, remove them from list_out */
876 for(iter
=lpos
;iter
!=NULL
;iter
=g_slist_next(iter
)) {
878 EventsRequest
*event_request_lpos
=
879 (EventsRequest
*)iter
->data
;
881 list_in
= g_slist_append(list_in
, event_request_lpos
);
882 /* Remove from list_out */
883 list_out
= g_slist_remove(list_out
, event_request_lpos
);
886 /* 1.1.4 (lpos.start time >= ltime) */
887 /* Add ltime to list_in, remove them from list_out */
889 for(iter
=ltime
;iter
!=NULL
;iter
=g_slist_next(iter
)) {
891 EventsRequest
*event_request_ltime
=
892 (EventsRequest
*)iter
->data
;
894 list_in
= g_slist_append(list_in
, event_request_ltime
);
895 /* Remove from list_out */
896 list_out
= g_slist_remove(list_out
, event_request_ltime
);
906 tfc
= lttv_traceset_context_get_current_tfc(tsc
);
907 g_assert(g_slist_length(list_in
)>0);
908 EventsRequest
*events_request
= g_slist_nth_data(list_in
, 0);
911 /* 1.2.1 If first request in list_in is a time request */
912 if(events_request
->start_position
== NULL
) {
913 /* - If first req in list_in start time != current time */
914 if(tfc
== NULL
|| ltt_time_compare(events_request
->start_time
,
915 tfc
->timestamp
) != 0)
916 /* - Seek to that time */
917 g_debug("SEEK TIME : %lu, %lu", events_request
->start_time
.tv_sec
,
918 events_request
->start_time
.tv_nsec
);
919 //lttv_process_traceset_seek_time(tsc, events_request->start_time);
920 lttv_state_traceset_seek_time_closest(LTTV_TRACESET_STATE(tsc
),
921 events_request
->start_time
);
923 /* Process the traceset with only state hooks */
925 lttv_process_traceset_middle(tsc
,
926 events_request
->start_time
,
932 /* Else, the first request in list_in is a position request */
933 /* If first req in list_in pos != current pos */
934 g_assert(events_request
->start_position
!= NULL
);
935 g_debug("SEEK POS time : %lu, %lu",
936 lttv_traceset_context_position_get_time(
937 events_request
->start_position
).tv_sec
,
938 lttv_traceset_context_position_get_time(
939 events_request
->start_position
).tv_nsec
);
941 g_debug("SEEK POS context time : %lu, %lu",
942 lttv_traceset_context_get_current_tfc(tsc
)->timestamp
.tv_sec
,
943 lttv_traceset_context_get_current_tfc(tsc
)->timestamp
.tv_nsec
);
944 g_assert(events_request
->start_position
!= NULL
);
945 if(lttv_traceset_context_ctx_pos_compare(tsc
,
946 events_request
->start_position
) != 0) {
947 /* 1.2.2.1 Seek to that position */
948 g_debug("SEEK POSITION");
949 //lttv_process_traceset_seek_position(tsc, events_request->start_position);
950 pos_time
= lttv_traceset_context_position_get_time(
951 events_request
->start_position
);
953 lttv_state_traceset_seek_time_closest(LTTV_TRACESET_STATE(tsc
),
956 /* Process the traceset with only state hooks */
958 lttv_process_traceset_middle(tsc
,
961 events_request
->start_position
);
962 g_assert(lttv_traceset_context_ctx_pos_compare(tsc
,
963 events_request
->start_position
) == 0);
970 /* 1.3 Add hooks and call before request for all list_in members */
974 for(iter
=list_in
;iter
!=NULL
;iter
=g_slist_next(iter
)) {
975 EventsRequest
*events_request
= (EventsRequest
*)iter
->data
;
976 /* 1.3.1 If !servicing */
977 if(events_request
->servicing
== FALSE
) {
978 /* - begin request hooks called
981 lttv_hooks_call(events_request
->before_request
, (gpointer
)tsc
);
982 events_request
->servicing
= TRUE
;
984 /* 1.3.2 call before chunk
985 * 1.3.3 events hooks added
987 lttv_process_traceset_begin(tsc
, events_request
->before_chunk_traceset
,
988 events_request
->before_chunk_trace
,
989 events_request
->before_chunk_tracefile
,
990 events_request
->event
,
991 events_request
->event_by_id
);
995 /* 2. Else, list_in is not empty, we continue a read */
998 /* 2.0 For each req of list_in */
999 GSList
*iter
= list_in
;
1001 while(iter
!= NULL
) {
1003 EventsRequest
*events_request
= (EventsRequest
*)iter
->data
;
1005 /* - Call before chunk
1006 * - events hooks added
1008 lttv_process_traceset_begin(tsc
, events_request
->before_chunk_traceset
,
1009 events_request
->before_chunk_trace
,
1010 events_request
->before_chunk_tracefile
,
1011 events_request
->event
,
1012 events_request
->event_by_id
);
1014 iter
= g_slist_next(iter
);
1019 tfc
= lttv_traceset_context_get_current_tfc(tsc
);
1021 /* 2.1 For each req of list_out */
1022 GSList
*iter
= list_out
;
1024 while(iter
!= NULL
) {
1026 gboolean remove
= FALSE
;
1027 gboolean free_data
= FALSE
;
1028 EventsRequest
*events_request
= (EventsRequest
*)iter
->data
;
1030 /* if req.start time == current context time
1031 * or req.start position == current position*/
1032 if( ltt_time_compare(events_request
->start_time
,
1033 tfc
->timestamp
) == 0
1035 (events_request
->start_position
!= NULL
1037 lttv_traceset_context_ctx_pos_compare(tsc
,
1038 events_request
->start_position
) == 0)
1040 /* - Add to list_in, remove from list_out */
1041 list_in
= g_slist_append(list_in
, events_request
);
1045 /* - If !servicing */
1046 if(events_request
->servicing
== FALSE
) {
1047 /* - begin request hooks called
1048 * - servicing = TRUE
1050 lttv_hooks_call(events_request
->before_request
, (gpointer
)tsc
);
1051 events_request
->servicing
= TRUE
;
1053 /* call before chunk
1054 * events hooks added
1056 lttv_process_traceset_begin(tsc
, events_request
->before_chunk_traceset
,
1057 events_request
->before_chunk_trace
,
1058 events_request
->before_chunk_tracefile
,
1059 events_request
->event
,
1060 events_request
->event_by_id
);
1066 GSList
*remove_iter
= iter
;
1068 iter
= g_slist_next(iter
);
1069 if(free_data
) events_request_free((EventsRequest
*)remove_iter
->data
);
1070 list_out
= g_slist_remove_link(list_out
, remove_iter
);
1071 } else { // not remove
1072 iter
= g_slist_next(iter
);
1078 /* 3. Find end criterions */
1083 /* 3.1.1 Find lowest end time in list_in */
1084 g_assert(g_slist_length(list_in
)>0);
1085 end_time
= ((EventsRequest
*)g_slist_nth_data(list_in
,0))->end_time
;
1087 for(iter
=g_slist_nth(list_in
,1);iter
!=NULL
;iter
=g_slist_next(iter
)) {
1088 EventsRequest
*events_request
= (EventsRequest
*)iter
->data
;
1090 if(ltt_time_compare(events_request
->end_time
,
1092 end_time
= events_request
->end_time
;
1095 /* 3.1.2 Find lowest start time in list_out */
1096 for(iter
=list_out
;iter
!=NULL
;iter
=g_slist_next(iter
)) {
1097 EventsRequest
*events_request
= (EventsRequest
*)iter
->data
;
1099 if(ltt_time_compare(events_request
->start_time
,
1101 end_time
= events_request
->start_time
;
1106 /* 3.2 Number of events */
1108 /* 3.2.1 Find lowest number of events in list_in */
1111 end_nb_events
= ((EventsRequest
*)g_slist_nth_data(list_in
,0))->num_events
;
1113 for(iter
=g_slist_nth(list_in
,1);iter
!=NULL
;iter
=g_slist_next(iter
)) {
1114 EventsRequest
*events_request
= (EventsRequest
*)iter
->data
;
1116 if(events_request
->num_events
< end_nb_events
)
1117 end_nb_events
= events_request
->num_events
;
1120 /* 3.2.2 Use min(CHUNK_NUM_EVENTS, min num events in list_in) as
1123 end_nb_events
= MIN(CHUNK_NUM_EVENTS
, end_nb_events
);
1127 /* 3.3 End position */
1129 /* 3.3.1 Find lowest end position in list_in */
1132 end_position
=((EventsRequest
*)g_slist_nth_data(list_in
,0))->end_position
;
1134 for(iter
=g_slist_nth(list_in
,1);iter
!=NULL
;iter
=g_slist_next(iter
)) {
1135 EventsRequest
*events_request
= (EventsRequest
*)iter
->data
;
1137 if(events_request
->end_position
!= NULL
&& end_position
!= NULL
&&
1138 lttv_traceset_context_pos_pos_compare(events_request
->end_position
,
1140 end_position
= events_request
->end_position
;
1145 /* 3.3.2 Find lowest start position in list_out */
1148 for(iter
=list_out
;iter
!=NULL
;iter
=g_slist_next(iter
)) {
1149 EventsRequest
*events_request
= (EventsRequest
*)iter
->data
;
1151 if(events_request
->end_position
!= NULL
&& end_position
!= NULL
&&
1152 lttv_traceset_context_pos_pos_compare(events_request
->end_position
,
1154 end_position
= events_request
->end_position
;
1159 /* 4. Call process traceset middle */
1160 g_debug("Calling process traceset middle with %p, %lu sec %lu nsec, %lu nb ev, %p end pos", tsc
, end_time
.tv_sec
, end_time
.tv_nsec
, end_nb_events
, end_position
);
1161 count
= lttv_process_traceset_middle(tsc
, end_time
, end_nb_events
, end_position
);
1163 tfc
= lttv_traceset_context_get_current_tfc(tsc
);
1165 g_debug("Context time after middle : %lu, %lu", tfc
->timestamp
.tv_sec
,
1166 tfc
->timestamp
.tv_nsec
);
1168 g_debug("End of trace reached after middle.");
1172 /* 5. After process traceset middle */
1173 tfc
= lttv_traceset_context_get_current_tfc(tsc
);
1175 /* - if current context time > traceset.end time */
1176 if(tfc
== NULL
|| ltt_time_compare(tfc
->timestamp
,
1177 tsc
->time_span
.end_time
) > 0) {
1178 /* - For each req in list_in */
1179 GSList
*iter
= list_in
;
1181 while(iter
!= NULL
) {
1183 gboolean remove
= FALSE
;
1184 gboolean free_data
= FALSE
;
1185 EventsRequest
*events_request
= (EventsRequest
*)iter
->data
;
1187 /* - Remove events hooks for req
1188 * - Call end chunk for req
1190 lttv_process_traceset_end(tsc
, events_request
->after_chunk_traceset
,
1191 events_request
->after_chunk_trace
,
1192 events_request
->after_chunk_tracefile
,
1193 events_request
->event
,
1194 events_request
->event_by_id
);
1195 /* - Call end request for req */
1196 lttv_hooks_call(events_request
->after_request
, (gpointer
)tsc
);
1198 /* - remove req from list_in */
1199 /* Destroy the request */
1206 GSList
*remove_iter
= iter
;
1208 iter
= g_slist_next(iter
);
1209 if(free_data
) events_request_free((EventsRequest
*)remove_iter
->data
);
1210 list_in
= g_slist_remove_link(list_in
, remove_iter
);
1211 } else { // not remove
1212 iter
= g_slist_next(iter
);
1217 /* 5.1 For each req in list_in */
1218 GSList
*iter
= list_in
;
1220 while(iter
!= NULL
) {
1222 gboolean remove
= FALSE
;
1223 gboolean free_data
= FALSE
;
1224 EventsRequest
*events_request
= (EventsRequest
*)iter
->data
;
1226 /* - Remove events hooks for req
1227 * - Call end chunk for req
1229 lttv_process_traceset_end(tsc
, events_request
->after_chunk_traceset
,
1230 events_request
->after_chunk_trace
,
1231 events_request
->after_chunk_tracefile
,
1232 events_request
->event
,
1233 events_request
->event_by_id
);
1235 /* - req.num -= count */
1236 g_assert(events_request
->num_events
>= count
);
1237 events_request
->num_events
-= count
;
1239 g_assert(tfc
!= NULL
);
1240 /* - if req.num == 0
1242 * current context time >= req.end time
1244 * req.end pos == current pos
1246 * req.stop_flag == TRUE
1248 if( events_request
->num_events
== 0
1250 events_request
->stop_flag
== TRUE
1252 ltt_time_compare(tfc
->timestamp
,
1253 events_request
->end_time
) >= 0
1255 (events_request
->end_position
!= NULL
1257 lttv_traceset_context_ctx_pos_compare(tsc
,
1258 events_request
->end_position
) == 0)
1261 g_assert(events_request
->servicing
== TRUE
);
1262 /* - Call end request for req
1263 * - remove req from list_in */
1264 lttv_hooks_call(events_request
->after_request
, (gpointer
)tsc
);
1265 /* - remove req from list_in */
1266 /* Destroy the request */
1274 GSList
*remove_iter
= iter
;
1276 iter
= g_slist_next(iter
);
1277 if(free_data
) events_request_free((EventsRequest
*)remove_iter
->data
);
1278 list_in
= g_slist_remove_link(list_in
, remove_iter
);
1279 } else { // not remove
1280 iter
= g_slist_next(iter
);
1286 /* End of removed servicing loop : leave control to GTK instead. */
1287 // if(gtk_events_pending()) break;
1290 /* B. When interrupted between chunks */
1293 GSList
*iter
= list_in
;
1295 /* 1. for each request in list_in */
1296 while(iter
!= NULL
) {
1298 gboolean remove
= FALSE
;
1299 gboolean free_data
= FALSE
;
1300 EventsRequest
*events_request
= (EventsRequest
*)iter
->data
;
1302 /* 1.1. Use current postition as start position */
1303 if(events_request
->start_position
!= NULL
)
1304 lttv_traceset_context_position_destroy(events_request
->start_position
);
1305 events_request
->start_position
= lttv_traceset_context_position_new();
1306 lttv_traceset_context_position_save(tsc
, events_request
->start_position
);
1308 /* 1.2. Remove start time */
1309 events_request
->start_time
= ltt_time_infinite
;
1311 /* 1.3. Move from list_in to list_out */
1314 list_out
= g_slist_append(list_out
, events_request
);
1319 GSList
*remove_iter
= iter
;
1321 iter
= g_slist_next(iter
);
1322 if(free_data
) events_request_free((EventsRequest
*)remove_iter
->data
);
1323 list_in
= g_slist_remove_link(list_in
, remove_iter
);
1324 } else { // not remove
1325 iter
= g_slist_next(iter
);
1332 /* C Unlock Traces */
1334 //lttv_process_traceset_get_sync_data(tsc);
1339 iter_trace
<lttv_traceset_number(tsc
->ts
);
1341 LttvTrace
*trace_v
= lttv_traceset_get(tsc
->ts
, iter_trace
);
1343 lttvwindowtraces_unlock(trace_v
);
1348 //set the cursor back to normal
1349 gdk_window_set_cursor(win
, NULL
);
1352 g_assert(g_slist_length(list_in
) == 0);
1354 if( g_slist_length(list_out
) == 0 ) {
1355 /* Put tab's request pending flag back to normal */
1356 tab
->events_request_pending
= FALSE
;
1357 g_debug("remove the idle fct");
1358 return FALSE
; /* Remove the idle function */
1360 g_debug("leave the idle fct");
1361 return TRUE
; /* Leave the idle function */
1363 /* We do not use simili-round-robin, it may require to read 1 meg buffers
1364 * again and again if many tracesets use the same tracefiles. */
1365 /* Hack for round-robin idle functions */
1366 /* It will put the idle function at the end of the pool */
1367 /*g_idle_add_full((G_PRIORITY_HIGH_IDLE + 21),
1368 (GSourceFunc)execute_events_requests,
1378 /* add_trace_into_traceset_selector, each instance of a viewer has an associated
1379 * selector (filter), when a trace is added into traceset, the selector should
1380 * reflect the change. The function is used to update the selector
1383 void add_trace_into_traceset_selector(GtkWidget
* paned
, LttTrace
* t
)
1385 int j
, k
, m
, nb_tracefile
, nb_control
, nb_per_cpu
, nb_facility
, nb_event
;
1386 LttvTracesetSelector
* s
;
1387 LttvTraceSelector
* trace
;
1388 LttvTracefileSelector
* tracefile
;
1389 LttvEventtypeSelector
* eventtype
;
1395 w
= gtk_multivpaned_get_first_widget(GTK_MULTIVPANED(paned
));
1397 s
= g_object_get_data(G_OBJECT(w
), "Traceset_Selector");
1400 trace
= lttv_trace_selector_new(t
);
1401 lttv_traceset_selector_trace_add(s
, trace
);
1403 nb_facility
= ltt_trace_facility_number(t
);
1404 for(k
=0;k
<nb_facility
;k
++){
1405 fac
= ltt_trace_facility_get(t
,k
);
1406 nb_event
= (int) ltt_facility_eventtype_number(fac
);
1407 for(m
=0;m
<nb_event
;m
++){
1408 et
= ltt_facility_eventtype_get(fac
,m
);
1409 eventtype
= lttv_eventtype_selector_new(et
);
1410 lttv_trace_selector_eventtype_add(trace
, eventtype
);
1414 nb_control
= ltt_trace_control_tracefile_number(t
);
1415 nb_per_cpu
= ltt_trace_per_cpu_tracefile_number(t
);
1416 nb_tracefile
= nb_control
+ nb_per_cpu
;
1418 for(j
= 0 ; j
< nb_tracefile
; j
++) {
1420 tf
= ltt_trace_control_tracefile_get(t
, j
);
1422 tf
= ltt_trace_per_cpu_tracefile_get(t
, j
- nb_control
);
1423 tracefile
= lttv_tracefile_selector_new(tf
);
1424 lttv_trace_selector_tracefile_add(trace
, tracefile
);
1425 lttv_eventtype_selector_copy(trace
, tracefile
);
1427 }else g_warning("Module does not support filtering\n");
1429 w
= gtk_multivpaned_get_next_widget(GTK_MULTIVPANED(paned
));
1434 static void lttvwindow_add_trace(Tab
*tab
, LttvTrace
*trace_v
)
1436 LttvTraceset
*traceset
= tab
->traceset_info
->traceset
;
1438 guint num_traces
= lttv_traceset_number(traceset
);
1440 //Verify if trace is already present.
1441 for(i
=0; i
<num_traces
; i
++)
1443 LttvTrace
* trace
= lttv_traceset_get(traceset
, i
);
1444 if(trace
== trace_v
)
1448 //Keep a reference to the traces so they are not freed.
1449 for(i
=0; i
<lttv_traceset_number(traceset
); i
++)
1451 LttvTrace
* trace
= lttv_traceset_get(traceset
, i
);
1452 lttv_trace_ref(trace
);
1455 //remove state update hooks
1456 lttv_state_remove_event_hooks(
1457 (LttvTracesetState
*)tab
->traceset_info
->traceset_context
);
1459 lttv_context_fini(LTTV_TRACESET_CONTEXT(
1460 tab
->traceset_info
->traceset_context
));
1461 g_object_unref(tab
->traceset_info
->traceset_context
);
1463 lttv_traceset_add(traceset
, trace_v
);
1464 lttv_trace_ref(trace_v
); /* local ref */
1466 /* Create new context */
1467 tab
->traceset_info
->traceset_context
=
1468 g_object_new(LTTV_TRACESET_STATS_TYPE
, NULL
);
1470 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->
1475 //add state update hooks
1476 lttv_state_add_event_hooks(
1477 (LttvTracesetState
*)tab
->traceset_info
->traceset_context
);
1478 //Remove local reference to the traces.
1479 for(i
=0; i
<lttv_traceset_number(traceset
); i
++)
1481 LttvTrace
* trace
= lttv_traceset_get(traceset
, i
);
1482 lttv_trace_unref(trace
);
1486 //add_trace_into_traceset_selector(GTK_MULTIVPANED(tab->multivpaned), lttv_trace(trace_v));
1489 /* add_trace adds a trace into the current traceset. It first displays a
1490 * directory selection dialogue to let user choose a trace, then recreates
1491 * tracset_context, and redraws all the viewer of the current tab
1494 void add_trace(GtkWidget
* widget
, gpointer user_data
)
1497 LttvTrace
* trace_v
;
1498 LttvTraceset
* traceset
;
1500 char abs_path
[PATH_MAX
];
1503 MainWindow
* mw_data
= get_window_data_struct(widget
);
1504 GtkWidget
* notebook
= lookup_widget(widget
, "MNotebook");
1506 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook
),
1507 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
)));
1511 tab
= create_new_tab(widget
, NULL
);
1513 tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
1516 GtkDirSelection
* file_selector
= (GtkDirSelection
*)gtk_dir_selection_new("Select a trace");
1517 gtk_dir_selection_hide_fileop_buttons(file_selector
);
1519 if(remember_trace_dir
[0] != '\0')
1520 gtk_dir_selection_set_filename(file_selector
, remember_trace_dir
);
1522 id
= gtk_dialog_run(GTK_DIALOG(file_selector
));
1524 case GTK_RESPONSE_ACCEPT
:
1525 case GTK_RESPONSE_OK
:
1526 dir
= gtk_dir_selection_get_dir (file_selector
);
1527 strncpy(remember_trace_dir
, dir
, PATH_MAX
);
1528 if(!dir
|| strlen(dir
) == 0){
1529 gtk_widget_destroy((GtkWidget
*)file_selector
);
1532 get_absolute_pathname(dir
, abs_path
);
1533 trace_v
= lttvwindowtraces_get_trace_by_name(abs_path
);
1534 if(trace_v
== NULL
) {
1535 trace
= ltt_trace_open(abs_path
);
1537 g_warning("cannot open trace %s", abs_path
);
1539 trace_v
= lttv_trace_new(trace
);
1540 lttvwindowtraces_add_trace(trace_v
);
1541 lttvwindow_add_trace(tab
, trace_v
);
1544 lttvwindow_add_trace(tab
, trace_v
);
1547 gtk_widget_destroy((GtkWidget
*)file_selector
);
1549 //update current tab
1550 //update_traceset(mw_data);
1552 /* Call the updatetraceset hooks */
1554 traceset
= tab
->traceset_info
->traceset
;
1555 SetTraceset(tab
, traceset
);
1556 // in expose now call_pending_read_hooks(mw_data);
1558 //lttvwindow_report_current_time(mw_data,&(tab->current_time));
1560 case GTK_RESPONSE_REJECT
:
1561 case GTK_RESPONSE_CANCEL
:
1563 gtk_widget_destroy((GtkWidget
*)file_selector
);
1569 /* remove_trace_into_traceset_selector, each instance of a viewer has an associated
1570 * selector (filter), when a trace is remove from traceset, the selector should
1571 * reflect the change. The function is used to update the selector
1574 void remove_trace_from_traceset_selector(GtkWidget
* paned
, unsigned i
)
1576 LttvTracesetSelector
* s
;
1577 LttvTraceSelector
* t
;
1580 w
= gtk_multivpaned_get_first_widget(GTK_MULTIVPANED(paned
));
1582 s
= g_object_get_data(G_OBJECT(w
), "Traceset_Selector");
1584 t
= lttv_traceset_selector_trace_get(s
,i
);
1585 lttv_traceset_selector_trace_remove(s
, i
);
1586 lttv_trace_selector_destroy(t
);
1587 }g_warning("Module dose not support filtering\n");
1588 w
= gtk_multivpaned_get_next_widget(GTK_MULTIVPANED(paned
));
1593 /* remove_trace removes a trace from the current traceset if all viewers in
1594 * the current tab are not interested in the trace. It first displays a
1595 * dialogue, which shows all traces in the current traceset, to let user choose
1596 * a trace, then it checks if all viewers unselect the trace, if it is true,
1597 * it will remove the trace, recreate the traceset_contex,
1598 * and redraws all the viewer of the current tab. If there is on trace in the
1599 * current traceset, it will delete all viewers of the current tab
1602 // MD : no filter version.
1603 void remove_trace(GtkWidget
*widget
, gpointer user_data
)
1606 LttvTrace
* trace_v
;
1607 LttvTraceset
* traceset
;
1608 gint i
, j
, nb_trace
, index
=-1;
1609 char ** name
, *remove_trace_name
;
1610 MainWindow
* mw_data
= get_window_data_struct(widget
);
1611 GtkWidget
* notebook
= lookup_widget(widget
, "MNotebook");
1613 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook
),
1614 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
)));
1620 tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
1623 nb_trace
=lttv_traceset_number(tab
->traceset_info
->traceset
);
1624 name
= g_new(char*,nb_trace
);
1625 for(i
= 0; i
< nb_trace
; i
++){
1626 trace_v
= lttv_traceset_get(tab
->traceset_info
->traceset
, i
);
1627 trace
= lttv_trace(trace_v
);
1628 name
[i
] = ltt_trace_name(trace
);
1631 remove_trace_name
= get_remove_trace(name
, nb_trace
);
1634 if(remove_trace_name
){
1636 /* yuk, cut n paste from old code.. should be better (MD)*/
1637 for(i
= 0; i
<nb_trace
; i
++) {
1638 if(strcmp(remove_trace_name
,name
[i
]) == 0){
1643 traceset
= tab
->traceset_info
->traceset
;
1644 //Keep a reference to the traces so they are not freed.
1645 for(j
=0; j
<lttv_traceset_number(traceset
); j
++)
1647 LttvTrace
* trace
= lttv_traceset_get(traceset
, j
);
1648 lttv_trace_ref(trace
);
1651 //remove state update hooks
1652 lttv_state_remove_event_hooks(
1653 (LttvTracesetState
*)tab
->traceset_info
->traceset_context
);
1654 lttv_context_fini(LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
));
1655 g_object_unref(tab
->traceset_info
->traceset_context
);
1657 trace_v
= lttv_traceset_get(traceset
, index
);
1659 lttv_traceset_remove(traceset
, index
);
1660 lttv_trace_unref(trace_v
); // Remove local reference
1662 if(lttv_trace_get_ref_number(trace_v
) <= 1) {
1663 /* ref 1 : lttvwindowtraces only*/
1664 ltt_trace_close(lttv_trace(trace_v
));
1665 /* lttvwindowtraces_remove_trace takes care of destroying
1666 * the traceset linked with the trace_v and also of destroying
1667 * the trace_v at the same time.
1669 lttvwindowtraces_remove_trace(trace_v
);
1672 tab
->traceset_info
->traceset_context
=
1673 g_object_new(LTTV_TRACESET_STATS_TYPE
, NULL
);
1675 LTTV_TRACESET_CONTEXT(tab
->
1676 traceset_info
->traceset_context
),traceset
);
1677 //add state update hooks
1678 lttv_state_add_event_hooks(
1679 (LttvTracesetState
*)tab
->traceset_info
->traceset_context
);
1681 //Remove local reference to the traces.
1682 for(j
=0; j
<lttv_traceset_number(traceset
); j
++)
1684 LttvTrace
* trace
= lttv_traceset_get(traceset
, j
);
1685 lttv_trace_unref(trace
);
1688 SetTraceset(tab
, (gpointer
)traceset
);
1694 void remove_trace(GtkWidget
* widget
, gpointer user_data
)
1697 LttvTrace
* trace_v
;
1698 LttvTraceset
* traceset
;
1699 gint i
, j
, nb_trace
;
1700 char ** name
, *remove_trace_name
;
1701 MainWindow
* mw_data
= get_window_data_struct(widget
);
1702 LttvTracesetSelector
* s
;
1703 LttvTraceSelector
* t
;
1706 GtkWidget
* notebook
= lookup_widget(widget
, "MNotebook");
1708 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook
),
1709 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
)));
1715 tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
1718 nb_trace
=lttv_traceset_number(tab
->traceset_info
->traceset
);
1719 name
= g_new(char*,nb_trace
);
1720 for(i
= 0; i
< nb_trace
; i
++){
1721 trace_v
= lttv_traceset_get(tab
->traceset_info
->traceset
, i
);
1722 trace
= lttv_trace(trace_v
);
1723 name
[i
] = ltt_trace_name(trace
);
1726 remove_trace_name
= get_remove_trace(name
, nb_trace
);
1728 if(remove_trace_name
){
1729 for(i
=0; i
<nb_trace
; i
++){
1730 if(strcmp(remove_trace_name
,name
[i
]) == 0){
1731 //unselect the trace from the current viewer
1733 w
= gtk_multivpaned_get_widget(GTK_MULTIVPANED(tab
->multivpaned
));
1735 s
= g_object_get_data(G_OBJECT(w
), "Traceset_Selector");
1737 t
= lttv_traceset_selector_trace_get(s
,i
);
1738 lttv_trace_selector_set_selected(t
, FALSE
);
1741 //check if other viewers select the trace
1742 w
= gtk_multivpaned_get_first_widget(GTK_MULTIVPANED(tab
->multivpaned
));
1744 s
= g_object_get_data(G_OBJECT(w
), "Traceset_Selector");
1746 t
= lttv_traceset_selector_trace_get(s
,i
);
1747 selected
= lttv_trace_selector_get_selected(t
);
1750 w
= gtk_multivpaned_get_next_widget(GTK_MULTIVPANED(tab
->multivpaned
));
1752 }else selected
= FALSE
;
1754 //if no viewer selects the trace, remove it
1756 remove_trace_from_traceset_selector(GTK_MULTIVPANED(tab
->multivpaned
), i
);
1758 traceset
= tab
->traceset_info
->traceset
;
1759 //Keep a reference to the traces so they are not freed.
1760 for(j
=0; j
<lttv_traceset_number(traceset
); j
++)
1762 LttvTrace
* trace
= lttv_traceset_get(traceset
, j
);
1763 lttv_trace_ref(trace
);
1766 //remove state update hooks
1767 lttv_state_remove_event_hooks(
1768 (LttvTracesetState
*)tab
->traceset_info
->traceset_context
);
1769 lttv_context_fini(LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
));
1770 g_object_unref(tab
->traceset_info
->traceset_context
);
1773 trace_v
= lttv_traceset_get(traceset
, i
);
1775 if(lttv_trace_get_ref_number(trace_v
) <= 2) {
1776 /* ref 2 : traceset, local */
1777 lttvwindowtraces_remove_trace(trace_v
);
1778 ltt_trace_close(lttv_trace(trace_v
));
1781 lttv_traceset_remove(traceset
, i
);
1782 lttv_trace_unref(trace_v
); // Remove local reference
1784 if(!lttv_trace_get_ref_number(trace_v
))
1785 lttv_trace_destroy(trace_v
);
1787 tab
->traceset_info
->traceset_context
=
1788 g_object_new(LTTV_TRACESET_STATS_TYPE
, NULL
);
1790 LTTV_TRACESET_CONTEXT(tab
->
1791 traceset_info
->traceset_context
),traceset
);
1792 //add state update hooks
1793 lttv_state_add_event_hooks(
1794 (LttvTracesetState
*)tab
->traceset_info
->traceset_context
);
1796 //Remove local reference to the traces.
1797 for(j
=0; j
<lttv_traceset_number(traceset
); j
++)
1799 LttvTrace
* trace
= lttv_traceset_get(traceset
, j
);
1800 lttv_trace_unref(trace
);
1804 //update current tab
1805 //update_traceset(mw_data);
1808 SetTraceset(tab
, (gpointer
)traceset
);
1809 // in expose now call_pending_read_hooks(mw_data);
1811 //lttvwindow_report_current_time(mw_data,&(tab->current_time));
1814 // while(tab->multi_vpaned->num_children){
1815 // gtk_multi_vpaned_widget_delete(tab->multi_vpaned);
1829 /* Redraw all the viewers in the current tab */
1830 void redraw(GtkWidget
*widget
, gpointer user_data
)
1832 GtkWidget
* notebook
= lookup_widget(widget
, "MNotebook");
1833 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook
),
1834 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
)));
1839 tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
1843 LttvAttributeValue value
;
1845 g_assert(lttv_iattribute_find_by_path(tab
->attributes
, "hooks/redraw", LTTV_POINTER
, &value
));
1847 tmp
= (LttvHooks
*)*(value
.v_pointer
);
1849 lttv_hooks_call(tmp
,NULL
);
1853 void continue_processing(GtkWidget
*widget
, gpointer user_data
)
1855 GtkWidget
* notebook
= lookup_widget(widget
, "MNotebook");
1856 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook
),
1857 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
)));
1862 tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
1866 LttvAttributeValue value
;
1868 g_assert(lttv_iattribute_find_by_path(tab
->attributes
,
1869 "hooks/continue", LTTV_POINTER
, &value
));
1871 tmp
= (LttvHooks
*)*(value
.v_pointer
);
1873 lttv_hooks_call(tmp
,NULL
);
1876 /* Stop the processing for the calling main window's current tab.
1877 * It removes every processing requests that are in its list. It does not call
1878 * the end request hooks, because the request is not finished.
1881 void stop_processing(GtkWidget
*widget
, gpointer user_data
)
1883 GtkWidget
* notebook
= lookup_widget(widget
, "MNotebook");
1884 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook
),
1885 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
)));
1890 tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
1892 GSList
*iter
= tab
->events_requests
;
1894 while(iter
!= NULL
) {
1895 GSList
*remove_iter
= iter
;
1896 iter
= g_slist_next(iter
);
1898 g_free(remove_iter
->data
);
1899 tab
->events_requests
=
1900 g_slist_remove_link(tab
->events_requests
, remove_iter
);
1902 tab
->events_request_pending
= FALSE
;
1903 g_idle_remove_by_data(tab
);
1904 g_assert(g_slist_length(tab
->events_requests
) == 0);
1908 /* save will save the traceset to a file
1909 * Not implemented yet FIXME
1912 void save(GtkWidget
* widget
, gpointer user_data
)
1917 void save_as(GtkWidget
* widget
, gpointer user_data
)
1919 g_printf("Save as\n");
1923 /* zoom will change the time_window of all the viewers of the
1924 * current tab, and redisplay them. The main functionality is to
1925 * determine the new time_window of the current tab
1928 void zoom(GtkWidget
* widget
, double size
)
1930 TimeInterval time_span
;
1931 TimeWindow new_time_window
;
1932 LttTime current_time
, time_delta
, time_s
, time_e
, time_tmp
;
1933 MainWindow
* mw_data
= get_window_data_struct(widget
);
1934 LttvTracesetContext
*tsc
;
1935 GtkWidget
* notebook
= lookup_widget(widget
, "MNotebook");
1937 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook
),
1938 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
)));
1944 tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
1947 if(size
== 1) return;
1949 tsc
= LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
);
1950 time_span
= tsc
->time_span
;
1951 new_time_window
= tab
->time_window
;
1952 current_time
= tab
->current_time
;
1954 time_delta
= ltt_time_sub(time_span
.end_time
,time_span
.start_time
);
1956 new_time_window
.start_time
= time_span
.start_time
;
1957 new_time_window
.time_width
= time_delta
;
1959 new_time_window
.time_width
= ltt_time_div(new_time_window
.time_width
, size
);
1960 if(ltt_time_compare(new_time_window
.time_width
,time_delta
) > 0)
1961 { /* Case where zoom out is bigger than trace length */
1962 new_time_window
.start_time
= time_span
.start_time
;
1963 new_time_window
.time_width
= time_delta
;
1967 /* Center the image on the current time */
1968 new_time_window
.start_time
=
1969 ltt_time_sub(current_time
, ltt_time_div(new_time_window
.time_width
, 2.0));
1970 /* If on borders, don't fall off */
1971 if(ltt_time_compare(new_time_window
.start_time
, time_span
.start_time
) <0)
1973 new_time_window
.start_time
= time_span
.start_time
;
1977 if(ltt_time_compare(
1978 ltt_time_add(new_time_window
.start_time
, new_time_window
.time_width
),
1979 time_span
.end_time
) > 0)
1981 new_time_window
.start_time
=
1982 ltt_time_sub(time_span
.end_time
, new_time_window
.time_width
);
1988 //time_tmp = ltt_time_div(new_time_window.time_width, 2);
1989 //if(ltt_time_compare(current_time, time_tmp) < 0){
1990 // time_s = time_span->startTime;
1992 // time_s = ltt_time_sub(current_time,time_tmp);
1994 //time_e = ltt_time_add(current_time,time_tmp);
1995 //if(ltt_time_compare(time_span->startTime, time_s) > 0){
1996 // time_s = time_span->startTime;
1997 //}else if(ltt_time_compare(time_span->endTime, time_e) < 0){
1998 // time_e = time_span->endTime;
1999 // time_s = ltt_time_sub(time_e,new_time_window.time_width);
2001 //new_time_window.start_time = time_s;
2004 //lttvwindow_report_time_window(mw_data, &new_time_window);
2005 //call_pending_read_hooks(mw_data);
2007 //lttvwindow_report_current_time(mw_data,&(tab->current_time));
2008 //set_time_window(tab, &new_time_window);
2009 // in expose now call_pending_read_hooks(mw_data);
2010 //gtk_multi_vpaned_set_adjust(tab->multi_vpaned, &new_time_window, FALSE);
2015 ltt_time_sub(new_time_window
.start_time
, time_span
.start_time
);
2016 if( ltt_time_to_double(new_time_window
.time_width
)
2017 * NANOSECONDS_PER_SECOND
2018 / SCROLL_STEP_PER_PAGE
/* step increment */
2020 ltt_time_to_double(rel_time
) * NANOSECONDS_PER_SECOND
/* page size */
2022 ltt_time_to_double(rel_time
) * NANOSECONDS_PER_SECOND
/* page size */
2024 g_warning("Can not zoom that far due to scrollbar precision");
2027 ltt_time_from_double(
2028 ltt_time_to_double(new_time_window
.time_width
)
2029 /SCROLL_STEP_PER_PAGE
),
2032 g_warning("Can not zoom that far due to time nanosecond precision");
2034 time_change_manager(tab
, new_time_window
);
2037 GtkAdjustment
*adjustment
= gtk_range_get_adjustment(GTK_RANGE(tab
->scrollbar
));
2039 g_object_set(G_OBJECT(adjustment
),
2041 //ltt_time_to_double(new_time_window.start_time)
2042 // * NANOSECONDS_PER_SECOND, /* value */
2047 ltt_time_sub(time_span
.end_time
, time_span
.start_time
))
2048 * NANOSECONDS_PER_SECOND
, /* upper */
2050 ltt_time_to_double(new_time_window
.time_width
)
2051 / SCROLL_STEP_PER_PAGE
2052 * NANOSECONDS_PER_SECOND
, /* step increment */
2054 ltt_time_to_double(new_time_window
.time_width
)
2055 * NANOSECONDS_PER_SECOND
, /* page increment */
2057 ltt_time_to_double(new_time_window
.time_width
)
2058 * NANOSECONDS_PER_SECOND
, /* page size */
2060 gtk_adjustment_changed(adjustment
);
2061 //gtk_range_set_adjustment(GTK_RANGE(tab->scrollbar), adjustment);
2062 //gtk_adjustment_value_changed(adjustment);
2063 g_object_set(G_OBJECT(adjustment
),
2066 ltt_time_sub(new_time_window
.start_time
, time_span
.start_time
))
2067 * NANOSECONDS_PER_SECOND
, /* value */
2069 gtk_adjustment_value_changed(adjustment
);
2072 //g_object_set(G_OBJECT(adjustment),
2074 // ltt_time_to_double(time_window->start_time)
2075 // * NANOSECONDS_PER_SECOND, /* value */
2077 /* Note : the set value will call set_time_window if scrollbar value changed
2079 //gtk_adjustment_set_value(adjustment,
2080 // ltt_time_to_double(new_time_window.start_time)
2081 // * NANOSECONDS_PER_SECOND);
2086 void zoom_in(GtkWidget
* widget
, gpointer user_data
)
2091 void zoom_out(GtkWidget
* widget
, gpointer user_data
)
2096 void zoom_extended(GtkWidget
* widget
, gpointer user_data
)
2101 void go_to_time(GtkWidget
* widget
, gpointer user_data
)
2103 g_printf("Go to time\n");
2106 void show_time_frame(GtkWidget
* widget
, gpointer user_data
)
2108 g_printf("Show time frame\n");
2112 /* callback function */
2115 on_empty_traceset_activate (GtkMenuItem
*menuitem
,
2118 create_new_window((GtkWidget
*)menuitem
, user_data
, FALSE
);
2123 on_clone_traceset_activate (GtkMenuItem
*menuitem
,
2126 create_new_window((GtkWidget
*)menuitem
, user_data
, TRUE
);
2130 /* create_new_tab calls create_tab to construct a new tab in the main window
2133 Tab
*create_new_tab(GtkWidget
* widget
, gpointer user_data
){
2134 gchar label
[PATH_MAX
];
2135 MainWindow
* mw_data
= get_window_data_struct(widget
);
2137 GtkNotebook
* notebook
= (GtkNotebook
*)lookup_widget(widget
, "MNotebook");
2138 if(notebook
== NULL
){
2139 g_printf("Notebook does not exist\n");
2142 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook
),
2143 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
)));
2149 copy_tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
2152 strcpy(label
,"Page");
2153 if(get_label(mw_data
, label
,"Get the name of the tab","Please input tab's name"))
2154 return (create_tab (mw_data
, copy_tab
, notebook
, label
));
2158 on_tab_activate (GtkMenuItem
*menuitem
,
2161 create_new_tab((GtkWidget
*)menuitem
, user_data
);
2166 on_open_activate (GtkMenuItem
*menuitem
,
2169 open_traceset((GtkWidget
*)menuitem
, user_data
);
2174 on_close_activate (GtkMenuItem
*menuitem
,
2177 MainWindow
* mw_data
= get_window_data_struct((GtkWidget
*)menuitem
);
2178 main_window_destructor(mw_data
);
2182 /* remove the current tab from the main window
2186 on_close_tab_activate (GtkWidget
*widget
,
2190 GtkWidget
* notebook
;
2192 MainWindow
* mw_data
= get_window_data_struct(widget
);
2193 notebook
= lookup_widget(widget
, "MNotebook");
2194 if(notebook
== NULL
){
2195 g_printf("Notebook does not exist\n");
2199 page_num
= gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
));
2201 gtk_notebook_remove_page(GTK_NOTEBOOK(notebook
), page_num
);
2206 on_close_tab_X_clicked (GtkWidget
*widget
,
2210 GtkWidget
*notebook
= lookup_widget(widget
, "MNotebook");
2211 if(notebook
== NULL
){
2212 g_printf("Notebook does not exist\n");
2216 if((page_num
= gtk_notebook_page_num(GTK_NOTEBOOK(notebook
), widget
)) != -1)
2217 gtk_notebook_remove_page(GTK_NOTEBOOK(notebook
), page_num
);
2223 on_add_trace_activate (GtkMenuItem
*menuitem
,
2226 add_trace((GtkWidget
*)menuitem
, user_data
);
2231 on_remove_trace_activate (GtkMenuItem
*menuitem
,
2234 remove_trace((GtkWidget
*)menuitem
, user_data
);
2239 on_save_activate (GtkMenuItem
*menuitem
,
2242 save((GtkWidget
*)menuitem
, user_data
);
2247 on_save_as_activate (GtkMenuItem
*menuitem
,
2250 save_as((GtkWidget
*)menuitem
, user_data
);
2255 on_quit_activate (GtkMenuItem
*menuitem
,
2263 on_cut_activate (GtkMenuItem
*menuitem
,
2271 on_copy_activate (GtkMenuItem
*menuitem
,
2274 g_printf("Copye\n");
2279 on_paste_activate (GtkMenuItem
*menuitem
,
2282 g_printf("Paste\n");
2287 on_delete_activate (GtkMenuItem
*menuitem
,
2290 g_printf("Delete\n");
2295 on_zoom_in_activate (GtkMenuItem
*menuitem
,
2298 zoom_in((GtkWidget
*)menuitem
, user_data
);
2303 on_zoom_out_activate (GtkMenuItem
*menuitem
,
2306 zoom_out((GtkWidget
*)menuitem
, user_data
);
2311 on_zoom_extended_activate (GtkMenuItem
*menuitem
,
2314 zoom_extended((GtkWidget
*)menuitem
, user_data
);
2319 on_go_to_time_activate (GtkMenuItem
*menuitem
,
2322 go_to_time((GtkWidget
*)menuitem
, user_data
);
2327 on_show_time_frame_activate (GtkMenuItem
*menuitem
,
2330 show_time_frame((GtkWidget
*)menuitem
, user_data
);
2335 on_move_viewer_up_activate (GtkMenuItem
*menuitem
,
2338 move_up_viewer((GtkWidget
*)menuitem
, user_data
);
2343 on_move_viewer_down_activate (GtkMenuItem
*menuitem
,
2346 move_down_viewer((GtkWidget
*)menuitem
, user_data
);
2351 on_remove_viewer_activate (GtkMenuItem
*menuitem
,
2354 delete_viewer((GtkWidget
*)menuitem
, user_data
);
2359 on_trace_filter_activate (GtkMenuItem
*menuitem
,
2362 MainWindow
* mw_data
= get_window_data_struct((GtkWidget
*)menuitem
);
2363 LttvTracesetSelector
* s
;
2365 GtkWidget
* notebook
= lookup_widget(GTK_WIDGET(menuitem
), "MNotebook");
2367 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(notebook
),
2368 gtk_notebook_get_current_page(GTK_NOTEBOOK(notebook
)));
2374 tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
2377 w
= gtk_multivpaned_get_widget(GTK_MULTIVPANED(tab
->multivpaned
));
2379 s
= g_object_get_data(G_OBJECT(w
), "Traceset_Selector");
2381 g_printf("There is no viewer yet\n");
2384 if(get_filter_selection(s
, "Configure trace and tracefile filter", "Select traces and tracefiles")){
2385 //FIXME report filter change
2386 //update_traceset(mw_data);
2387 //call_pending_read_hooks(mw_data);
2388 //lttvwindow_report_current_time(mw_data,&(tab->current_time));
2394 on_trace_facility_activate (GtkMenuItem
*menuitem
,
2397 g_printf("Trace facility selector: %s\n");
2401 /* Dispaly a file selection dialogue to let user select a library, then call
2402 * lttv_library_load().
2406 on_load_library_activate (GtkMenuItem
*menuitem
,
2409 GError
*error
= NULL
;
2410 MainWindow
* mw_data
= get_window_data_struct((GtkWidget
*)menuitem
);
2412 gchar load_module_path_alter
[PATH_MAX
];
2416 gchar
*load_module_path
;
2417 name
= g_ptr_array_new();
2418 nb
= lttv_library_path_number();
2419 /* ask for the library path */
2423 path
= lttv_library_path_get(i
);
2424 g_ptr_array_add(name
, path
);
2427 load_module_path
= get_selection((char **)(name
->pdata
), name
->len
,
2428 "Select a library path", "Library paths");
2429 if(load_module_path
!= NULL
)
2430 strncpy(load_module_path_alter
, load_module_path
, PATH_MAX
-1); // -1 for /
2432 g_ptr_array_free(name
, TRUE
);
2434 if(load_module_path
== NULL
) return;
2438 /* Make sure the module path ends with a / */
2439 gchar
*ptr
= load_module_path_alter
;
2441 ptr
= strchr(ptr
, '\0');
2443 if(*(ptr
-1) != '/') {
2450 /* Ask for the library to load : list files in the previously selected
2452 gchar str
[PATH_MAX
];
2455 GtkFileSelection
* file_selector
=
2456 (GtkFileSelection
*)gtk_file_selection_new("Select a module");
2457 gtk_file_selection_set_filename(file_selector
, load_module_path_alter
);
2458 gtk_file_selection_hide_fileop_buttons(file_selector
);
2461 id
= gtk_dialog_run(GTK_DIALOG(file_selector
));
2463 case GTK_RESPONSE_ACCEPT
:
2464 case GTK_RESPONSE_OK
:
2465 dir
= gtk_file_selection_get_selections (file_selector
);
2466 strncpy(str
,dir
[0],PATH_MAX
);
2467 strncpy(remember_plugins_dir
,dir
[0],PATH_MAX
);
2468 /* only keep file name */
2470 str1
= strrchr(str
,'/');
2473 str1
= strrchr(str
,'\\');
2478 if(*str1
== 'l' && *(str1
+1)== 'i' && *(str1
+2)=='b')
2480 remove info after
. */
2484 str2
= strrchr(str2
, '.');
2485 if(str2
!= NULL
) *str2
= '\0';
2487 lttv_module_require(str1
, &error
);
2489 lttv_library_load(str1
, &error
);
2490 if(error
!= NULL
) g_warning(error
->message
);
2491 else g_printf("Load library: %s\n", str
);
2493 case GTK_RESPONSE_REJECT
:
2494 case GTK_RESPONSE_CANCEL
:
2496 gtk_widget_destroy((GtkWidget
*)file_selector
);
2507 /* Display all loaded modules, let user to select a module to unload
2508 * by calling lttv_module_unload
2512 on_unload_library_activate (GtkMenuItem
*menuitem
,
2515 MainWindow
* mw_data
= get_window_data_struct((GtkWidget
*)menuitem
);
2517 LttvLibrary
*library
;
2522 name
= g_ptr_array_new();
2523 nb
= lttv_library_number();
2524 LttvLibraryInfo
*lib_info
= g_new(LttvLibraryInfo
,nb
);
2525 /* ask for the library name */
2528 LttvLibrary
*iter_lib
= lttv_library_get(i
);
2529 lttv_library_info(iter_lib
, &lib_info
[i
]);
2531 gchar
*path
= lib_info
[i
].name
;
2532 g_ptr_array_add(name
, lib_info
[i
].name
);
2534 lib_name
= get_selection((char **)(name
->pdata
), name
->len
,
2535 "Select a library", "Libraries");
2536 if(lib_name
!= NULL
) {
2538 if(strcmp(lib_name
, lib_info
[i
].name
) == 0) {
2539 library
= lttv_library_get(i
);
2544 g_ptr_array_free(name
, TRUE
);
2547 if(lib_name
== NULL
) return;
2550 lttv_library_unload(library
);
2554 /* Dispaly a file selection dialogue to let user select a module, then call
2555 * lttv_module_require().
2559 on_load_module_activate (GtkMenuItem
*menuitem
,
2562 GError
*error
= NULL
;
2563 MainWindow
* mw_data
= get_window_data_struct((GtkWidget
*)menuitem
);
2565 LttvLibrary
*library
;
2570 name
= g_ptr_array_new();
2571 nb
= lttv_library_number();
2572 LttvLibraryInfo
*lib_info
= g_new(LttvLibraryInfo
,nb
);
2573 /* ask for the library name */
2576 LttvLibrary
*iter_lib
= lttv_library_get(i
);
2577 lttv_library_info(iter_lib
, &lib_info
[i
]);
2579 gchar
*path
= lib_info
[i
].name
;
2580 g_ptr_array_add(name
, path
);
2582 lib_name
= get_selection((char **)(name
->pdata
), name
->len
,
2583 "Select a library", "Libraries");
2584 if(lib_name
!= NULL
) {
2586 if(strcmp(lib_name
, lib_info
[i
].name
) == 0) {
2587 library
= lttv_library_get(i
);
2592 g_ptr_array_free(name
, TRUE
);
2595 if(lib_name
== NULL
) return;
2598 //LttvModule *module;
2599 gchar module_name_out
[PATH_MAX
];
2601 /* Ask for the module to load : list modules in the selected lib */
2605 LttvModuleInfo
*module_info
= g_new(LttvModuleInfo
,nb
);
2606 name
= g_ptr_array_new();
2607 nb
= lttv_library_module_number(library
);
2608 /* ask for the module name */
2611 LttvModule
*iter_module
= lttv_library_module_get(library
, i
);
2612 lttv_module_info(iter_module
, &module_info
[i
]);
2614 gchar
*path
= module_info
[i
].name
;
2615 g_ptr_array_add(name
, path
);
2617 module_name
= get_selection((char **)(name
->pdata
), name
->len
,
2618 "Select a module", "Modules");
2619 if(module_name
!= NULL
) {
2621 if(strcmp(module_name
, module_info
[i
].name
) == 0) {
2622 strncpy(module_name_out
, module_name
, PATH_MAX
);
2623 //module = lttv_library_module_get(i);
2629 g_ptr_array_free(name
, TRUE
);
2630 g_free(module_info
);
2632 if(module_name
== NULL
) return;
2635 lttv_module_require(module_name_out
, &error
);
2636 if(error
!= NULL
) g_warning(error
->message
);
2637 else g_printf("Load module: %s\n", module_name_out
);
2644 gchar str
[PATH_MAX
];
2647 GtkFileSelection
* file_selector
=
2648 (GtkFileSelection
*)gtk_file_selection_new("Select a module");
2649 gtk_file_selection_set_filename(file_selector
, load_module_path_alter
);
2650 gtk_file_selection_hide_fileop_buttons(file_selector
);
2653 id
= gtk_dialog_run(GTK_DIALOG(file_selector
));
2655 case GTK_RESPONSE_ACCEPT
:
2656 case GTK_RESPONSE_OK
:
2657 dir
= gtk_file_selection_get_selections (file_selector
);
2658 strncpy(str
,dir
[0],PATH_MAX
);
2659 strncpy(remember_plugins_dir
,dir
[0],PATH_MAX
);
2661 /* only keep file name */
2663 str1
= strrchr(str
,'/');
2666 str1
= strrchr(str
,'\\');
2671 if(*str1
== 'l' && *(str1
+1)== 'i' && *(str1
+2)=='b')
2673 remove info after
. */
2677 str2
= strrchr(str2
, '.');
2678 if(str2
!= NULL
) *str2
= '\0';
2680 lttv_module_require(str1
, &error
);
2682 lttv_library_load(str1
, &error
);
2683 if(error
!= NULL
) g_warning(error
->message
);
2684 else g_printf("Load library: %s\n", str
);
2686 case GTK_RESPONSE_REJECT
:
2687 case GTK_RESPONSE_CANCEL
:
2689 gtk_widget_destroy((GtkWidget
*)file_selector
);
2701 /* Display all loaded modules, let user to select a module to unload
2702 * by calling lttv_module_unload
2706 on_unload_module_activate (GtkMenuItem
*menuitem
,
2709 GError
*error
= NULL
;
2710 MainWindow
* mw_data
= get_window_data_struct((GtkWidget
*)menuitem
);
2712 LttvLibrary
*library
;
2717 name
= g_ptr_array_new();
2718 nb
= lttv_library_number();
2719 LttvLibraryInfo
*lib_info
= g_new(LttvLibraryInfo
,nb
);
2720 /* ask for the library name */
2723 LttvLibrary
*iter_lib
= lttv_library_get(i
);
2724 lttv_library_info(iter_lib
, &lib_info
[i
]);
2726 gchar
*path
= lib_info
[i
].name
;
2727 g_ptr_array_add(name
, path
);
2729 lib_name
= get_selection((char **)(name
->pdata
), name
->len
,
2730 "Select a library", "Libraries");
2731 if(lib_name
!= NULL
) {
2733 if(strcmp(lib_name
, lib_info
[i
].name
) == 0) {
2734 library
= lttv_library_get(i
);
2739 g_ptr_array_free(name
, TRUE
);
2742 if(lib_name
== NULL
) return;
2747 /* Ask for the module to load : list modules in the selected lib */
2751 nb
= lttv_library_module_number(library
);
2752 LttvModuleInfo
*module_info
= g_new(LttvModuleInfo
,nb
);
2753 name
= g_ptr_array_new();
2754 /* ask for the module name */
2757 LttvModule
*iter_module
= lttv_library_module_get(library
, i
);
2758 lttv_module_info(iter_module
, &module_info
[i
]);
2760 gchar
*path
= module_info
[i
].name
;
2761 if(module_info
[i
].use_count
> 0) g_ptr_array_add(name
, path
);
2763 module_name
= get_selection((char **)(name
->pdata
), name
->len
,
2764 "Select a module", "Modules");
2765 if(module_name
!= NULL
) {
2767 if(strcmp(module_name
, module_info
[i
].name
) == 0) {
2768 module
= lttv_library_module_get(library
, i
);
2774 g_ptr_array_free(name
, TRUE
);
2775 g_free(module_info
);
2777 if(module_name
== NULL
) return;
2780 LttvModuleInfo module_info
;
2781 lttv_module_info(module
, &module_info
);
2782 g_printf("Release module: %s\n", module_info
.name
);
2784 lttv_module_release(module
);
2788 /* Display a directory dialogue to let user select a path for library searching
2792 on_add_library_search_path_activate (GtkMenuItem
*menuitem
,
2795 GtkDirSelection
* file_selector
= (GtkDirSelection
*)gtk_dir_selection_new("Select library path");
2799 MainWindow
* mw_data
= get_window_data_struct((GtkWidget
*)menuitem
);
2800 if(remember_plugins_dir
[0] != '\0')
2801 gtk_dir_selection_set_filename(file_selector
, remember_plugins_dir
);
2803 id
= gtk_dialog_run(GTK_DIALOG(file_selector
));
2805 case GTK_RESPONSE_ACCEPT
:
2806 case GTK_RESPONSE_OK
:
2807 dir
= gtk_dir_selection_get_dir (file_selector
);
2808 strncpy(remember_plugins_dir
,dir
,PATH_MAX
);
2809 strncat(remember_plugins_dir
,"/",PATH_MAX
);
2810 lttv_library_path_add(dir
);
2811 case GTK_RESPONSE_REJECT
:
2812 case GTK_RESPONSE_CANCEL
:
2814 gtk_widget_destroy((GtkWidget
*)file_selector
);
2820 /* Display a directory dialogue to let user select a path for library searching
2824 on_remove_library_search_path_activate (GtkMenuItem
*menuitem
,
2827 MainWindow
* mw_data
= get_window_data_struct((GtkWidget
*)menuitem
);
2829 const char *lib_path
;
2834 name
= g_ptr_array_new();
2835 nb
= lttv_library_path_number();
2836 /* ask for the library name */
2839 gchar
*path
= lttv_library_path_get(i
);
2840 g_ptr_array_add(name
, path
);
2842 lib_path
= get_selection((char **)(name
->pdata
), name
->len
,
2843 "Select a library path", "Library paths");
2845 g_ptr_array_free(name
, TRUE
);
2847 if(lib_path
== NULL
) return;
2850 lttv_library_path_remove(lib_path
);
2854 on_color_activate (GtkMenuItem
*menuitem
,
2857 g_printf("Color\n");
2862 on_filter_activate (GtkMenuItem
*menuitem
,
2865 g_printf("Filter\n");
2870 on_save_configuration_activate (GtkMenuItem
*menuitem
,
2873 g_printf("Save configuration\n");
2878 on_content_activate (GtkMenuItem
*menuitem
,
2881 g_printf("Content\n");
2886 on_about_close_activate (GtkButton
*button
,
2889 GtkWidget
*about_widget
= GTK_WIDGET(user_data
);
2891 gtk_widget_destroy(about_widget
);
2895 on_about_activate (GtkMenuItem
*menuitem
,
2898 MainWindow
*main_window
= get_window_data_struct(GTK_WIDGET(menuitem
));
2899 GtkWidget
*window_widget
= main_window
->mwindow
;
2900 GtkWidget
*about_widget
= gtk_window_new(GTK_WINDOW_TOPLEVEL
);
2901 GtkWindow
*about_window
= GTK_WINDOW(about_widget
);
2902 gint window_width
, window_height
;
2904 gtk_window_set_title(about_window
, "About Linux Trace Toolkit");
2906 gtk_window_set_resizable(about_window
, FALSE
);
2907 gtk_window_set_transient_for(GTK_WINDOW(window_widget
), about_window
);
2908 gtk_window_set_destroy_with_parent(about_window
, TRUE
);
2909 gtk_window_set_modal(about_window
, FALSE
);
2911 /* Put the about window at the center of the screen */
2912 gtk_window_get_size(about_window
, &window_width
, &window_height
);
2913 gtk_window_move (about_window
,
2914 (gdk_screen_width() - window_width
)/2,
2915 (gdk_screen_height() - window_height
)/2);
2917 GtkWidget
*vbox
= gtk_vbox_new(FALSE
, 1);
2919 gtk_container_add(GTK_CONTAINER(about_widget
), vbox
);
2923 GtkWidget
*label1
= gtk_label_new("");
2924 gtk_misc_set_padding(GTK_MISC(label1
), 10, 20);
2925 gtk_label_set_markup(GTK_LABEL(label1
), "\
2926 <big>Linux Trace Toolkit</big>");
2927 gtk_label_set_justify(GTK_LABEL(label1
), GTK_JUSTIFY_CENTER
);
2929 GtkWidget
*label2
= gtk_label_new("");
2930 gtk_misc_set_padding(GTK_MISC(label2
), 10, 20);
2931 gtk_label_set_markup(GTK_LABEL(label2
), "\
2932 Project author: Karim Yaghmour\n\
2936 Michel Dagenais (New trace format, lttv main)\n\
2937 Mathieu Desnoyers (Directory structure, build with automake/conf,\n\
2938 lttv gui, control flow view, gui green threads\n\
2939 with interruptible foreground and background computation,\n\
2940 detailed event list)\n\
2941 Benoit Des Ligneris (Cluster adaptation)\n\
2942 Xang-Xiu Yang (new trace reading library and converter, lttv gui, \n\
2943 detailed event list and statistics view)\n\
2944 Tom Zanussi (RelayFS)");
2946 GtkWidget
*label3
= gtk_label_new("");
2947 gtk_label_set_markup(GTK_LABEL(label3
), "\
2948 Linux Trace Toolkit, Copyright (C) 2004 Karim Yaghmour\n\
2949 Linux Trace Toolkit comes with ABSOLUTELY NO WARRANTY.\n\
2950 This is free software, and you are welcome to redistribute it\n\
2951 under certain conditions. See COPYING for details.");
2952 gtk_misc_set_padding(GTK_MISC(label3
), 10, 20);
2954 gtk_box_pack_start_defaults(GTK_BOX(vbox
), label1
);
2955 gtk_box_pack_start_defaults(GTK_BOX(vbox
), label2
);
2956 gtk_box_pack_start_defaults(GTK_BOX(vbox
), label3
);
2958 GtkWidget
*hbox
= gtk_hbox_new(TRUE
, 0);
2959 gtk_box_pack_end(GTK_BOX(vbox
), hbox
, FALSE
, FALSE
, 0);
2960 GtkWidget
*close_button
= gtk_button_new_with_mnemonic("_Close");
2961 gtk_box_pack_end(GTK_BOX(hbox
), close_button
, FALSE
, FALSE
, 0);
2962 gtk_container_set_border_width(GTK_CONTAINER(close_button
), 20);
2964 g_signal_connect(G_OBJECT(close_button
), "clicked",
2965 G_CALLBACK(on_about_close_activate
),
2966 (gpointer
)about_widget
);
2968 gtk_widget_show_all(about_widget
);
2973 on_button_new_clicked (GtkButton
*button
,
2976 create_new_window((GtkWidget
*)button
, user_data
, TRUE
);
2980 on_button_new_tab_clicked (GtkButton
*button
,
2983 create_new_tab((GtkWidget
*)button
, user_data
);
2987 on_button_open_clicked (GtkButton
*button
,
2990 open_traceset((GtkWidget
*)button
, user_data
);
2995 on_button_add_trace_clicked (GtkButton
*button
,
2998 add_trace((GtkWidget
*)button
, user_data
);
3003 on_button_remove_trace_clicked (GtkButton
*button
,
3006 remove_trace((GtkWidget
*)button
, user_data
);
3010 on_button_redraw_clicked (GtkButton
*button
,
3013 redraw((GtkWidget
*)button
, user_data
);
3017 on_button_continue_processing_clicked (GtkButton
*button
,
3020 continue_processing((GtkWidget
*)button
, user_data
);
3024 on_button_stop_processing_clicked (GtkButton
*button
,
3027 stop_processing((GtkWidget
*)button
, user_data
);
3033 on_button_save_clicked (GtkButton
*button
,
3036 save((GtkWidget
*)button
, user_data
);
3041 on_button_save_as_clicked (GtkButton
*button
,
3044 save_as((GtkWidget
*)button
, user_data
);
3049 on_button_zoom_in_clicked (GtkButton
*button
,
3052 zoom_in((GtkWidget
*)button
, user_data
);
3057 on_button_zoom_out_clicked (GtkButton
*button
,
3060 zoom_out((GtkWidget
*)button
, user_data
);
3065 on_button_zoom_extended_clicked (GtkButton
*button
,
3068 zoom_extended((GtkWidget
*)button
, user_data
);
3073 on_button_go_to_time_clicked (GtkButton
*button
,
3076 go_to_time((GtkWidget
*)button
, user_data
);
3081 on_button_show_time_frame_clicked (GtkButton
*button
,
3084 show_time_frame((GtkWidget
*)button
, user_data
);
3089 on_button_move_up_clicked (GtkButton
*button
,
3092 move_up_viewer((GtkWidget
*)button
, user_data
);
3097 on_button_move_down_clicked (GtkButton
*button
,
3100 move_down_viewer((GtkWidget
*)button
, user_data
);
3105 on_button_delete_viewer_clicked (GtkButton
*button
,
3108 delete_viewer((GtkWidget
*)button
, user_data
);
3112 on_MWindow_destroy (GtkWidget
*widget
,
3115 MainWindow
*main_window
= get_window_data_struct(widget
);
3116 LttvIAttribute
*attributes
= main_window
->attributes
;
3117 LttvAttributeValue value
;
3119 //This is unnecessary, since widgets will be destroyed
3120 //by the main window widget anyway.
3121 //remove_all_menu_toolbar_constructors(main_window, NULL);
3123 g_assert(lttv_iattribute_find_by_path(attributes
,
3124 "viewers/menu", LTTV_POINTER
, &value
));
3125 lttv_menus_destroy((LttvMenus
*)*(value
.v_pointer
));
3127 g_assert(lttv_iattribute_find_by_path(attributes
,
3128 "viewers/toolbar", LTTV_POINTER
, &value
));
3129 lttv_toolbars_destroy((LttvToolbars
*)*(value
.v_pointer
));
3131 g_object_unref(main_window
->attributes
);
3132 g_main_window_list
= g_slist_remove(g_main_window_list
, main_window
);
3134 g_printf("There are now : %d windows\n",g_slist_length(g_main_window_list
));
3135 if(g_slist_length(g_main_window_list
) == 0)
3140 on_MWindow_configure (GtkWidget
*widget
,
3141 GdkEventConfigure
*event
,
3144 MainWindow
* mw_data
= get_window_data_struct((GtkWidget
*)widget
);
3145 float width
= event
->width
;
3146 TimeWindow time_win
;
3148 TimeInterval
*time_span
;
3151 // MD : removed time width modification upon resizing of the main window.
3152 // The viewers will redraw themselves completely, without time interval
3155 if(mw_data->window_width){
3156 time_span = LTTV_TRACESET_CONTEXT(tab->traceset_info->traceset_context)->Time_Span ;
3157 time_win = tab->time_window;
3158 ratio = width / mw_data->window_width;
3159 tab->time_window.time_width = ltt_time_mul(time_win.time_width,ratio);
3160 time = ltt_time_sub(time_span->endTime, time_win.start_time);
3161 if(ltt_time_compare(time, tab->time_window.time_width) < 0){
3162 tab->time_window.time_width = time;
3168 mw_data->window_width = (int)width;
3177 on_MNotebook_switch_page (GtkNotebook
*notebook
,
3178 GtkNotebookPage
*page
,
3186 void time_change_manager (Tab
*tab
,
3187 TimeWindow new_time_window
)
3189 /* Only one source of time change */
3190 if(tab
->time_manager_lock
== TRUE
) return;
3192 tab
->time_manager_lock
= TRUE
;
3194 LttvTracesetContext
*tsc
= LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
);
3195 TimeInterval time_span
= tsc
->time_span
;
3196 LttTime start_time
= new_time_window
.start_time
;
3197 LttTime end_time
= ltt_time_add(new_time_window
.start_time
,
3198 new_time_window
.time_width
);
3201 GtkAdjustment
*adjustment
= gtk_range_get_adjustment(GTK_RANGE(tab
->scrollbar
));
3202 LttTime upper
= ltt_time_sub(time_span
.end_time
, time_span
.start_time
);
3204 gtk_range_set_increments(GTK_RANGE(tab
->scrollbar
),
3205 ltt_time_to_double(new_time_window
.time_width
)
3206 / SCROLL_STEP_PER_PAGE
3207 * NANOSECONDS_PER_SECOND
, /* step increment */
3208 ltt_time_to_double(new_time_window
.time_width
)
3209 * NANOSECONDS_PER_SECOND
); /* page increment */
3210 gtk_range_set_range(GTK_RANGE(tab
->scrollbar
),
3212 ltt_time_to_double(upper
)
3213 * NANOSECONDS_PER_SECOND
); /* upper */
3215 g_object_set(G_OBJECT(adjustment
),
3219 ltt_time_to_double(upper
)
3220 * NANOSECONDS_PER_SECOND
, /* upper */
3222 ltt_time_to_double(new_time_window
.time_width
)
3223 / SCROLL_STEP_PER_PAGE
3224 * NANOSECONDS_PER_SECOND
, /* step increment */
3226 ltt_time_to_double(new_time_window
.time_width
)
3227 * NANOSECONDS_PER_SECOND
, /* page increment */
3229 ltt_time_to_double(new_time_window
.time_width
)
3230 * NANOSECONDS_PER_SECOND
, /* page size */
3232 gtk_adjustment_changed(adjustment
);
3234 // g_object_set(G_OBJECT(adjustment),
3236 // ltt_time_to_double(
3237 // ltt_time_sub(start_time, time_span.start_time))
3238 // * NANOSECONDS_PER_SECOND, /* value */
3240 //gtk_adjustment_value_changed(adjustment);
3241 gtk_range_set_value(GTK_RANGE(tab
->scrollbar
),
3243 ltt_time_sub(start_time
, time_span
.start_time
))
3244 * NANOSECONDS_PER_SECOND
/* value */);
3246 /* set the time bar. */
3248 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry1
),
3249 (double)time_span
.start_time
.tv_sec
,
3250 (double)time_span
.end_time
.tv_sec
);
3251 gtk_spin_button_set_value(GTK_SPIN_BUTTON(tab
->MEntry1
),
3252 (double)start_time
.tv_sec
);
3254 /* start nanoseconds */
3255 if(start_time
.tv_sec
== time_span
.start_time
.tv_sec
) {
3256 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry2
),
3257 (double)time_span
.start_time
.tv_nsec
,
3258 (double)NANOSECONDS_PER_SECOND
-1);
3260 else if(start_time
.tv_sec
== time_span
.end_time
.tv_sec
) {
3261 /* If we are at the end, max nsec to end.. -1 (not zero length) */
3262 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry2
),
3264 (double)time_span
.end_time
.tv_nsec
-1);
3266 else /* anywhere else */
3267 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry2
),
3269 (double)NANOSECONDS_PER_SECOND
-1);
3270 gtk_spin_button_set_value(GTK_SPIN_BUTTON(tab
->MEntry2
),
3271 (double)start_time
.tv_nsec
);
3274 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry3
),
3275 (double)time_span
.start_time
.tv_sec
,
3276 (double)time_span
.end_time
.tv_sec
);
3277 gtk_spin_button_set_value(GTK_SPIN_BUTTON(tab
->MEntry3
),
3278 (double)end_time
.tv_sec
);
3280 /* end nanoseconds */
3281 if(end_time
.tv_sec
== time_span
.start_time
.tv_sec
) {
3282 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry4
),
3283 (double)time_span
.start_time
.tv_nsec
+1,
3284 (double)NANOSECONDS_PER_SECOND
-1);
3286 else if(end_time
.tv_sec
== time_span
.end_time
.tv_sec
) {
3287 /* If we are at the end, max nsec to end.. */
3288 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry4
),
3290 (double)time_span
.end_time
.tv_nsec
);
3292 else /* anywhere else */
3293 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry4
),
3295 (double)NANOSECONDS_PER_SECOND
-1);
3296 gtk_spin_button_set_value(GTK_SPIN_BUTTON(tab
->MEntry4
),
3297 (double)end_time
.tv_nsec
);
3299 /* call viewer hooks for new time window */
3300 set_time_window(tab
, &new_time_window
);
3302 tab
->time_manager_lock
= FALSE
;
3306 /* value changed for frame start s
3308 * Check time span : if ns is out of range, clip it the nearest good value.
3311 on_MEntry1_value_changed (GtkSpinButton
*spinbutton
,
3314 Tab
*tab
=(Tab
*)user_data
;
3315 LttvTracesetContext
* tsc
=
3316 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
);
3317 TimeInterval time_span
= tsc
->time_span
;
3318 gint value
= gtk_spin_button_get_value_as_int(spinbutton
);
3320 TimeWindow new_time_window
= tab
->time_window
;
3322 LttTime end_time
= ltt_time_add(new_time_window
.start_time
,
3323 new_time_window
.time_width
);
3325 new_time_window
.start_time
.tv_sec
= value
;
3327 /* start nanoseconds */
3328 if(new_time_window
.start_time
.tv_sec
== time_span
.start_time
.tv_sec
) {
3329 if(new_time_window
.start_time
.tv_nsec
< time_span
.start_time
.tv_nsec
)
3330 new_time_window
.start_time
.tv_nsec
= time_span
.start_time
.tv_nsec
;
3332 else if(new_time_window
.start_time
.tv_sec
== time_span
.end_time
.tv_sec
) {
3333 if(new_time_window
.start_time
.tv_nsec
> time_span
.end_time
.tv_nsec
)
3334 new_time_window
.start_time
.tv_nsec
= time_span
.end_time
.tv_nsec
-1;
3337 /* check if end time selected is below or equal */
3338 if(ltt_time_compare(new_time_window
.start_time
, end_time
) >= 0) {
3339 /* Then, we must push back end time : keep the same time width
3340 * if possible, else end traceset time */
3341 end_time
= LTT_TIME_MIN(time_span
.end_time
,
3342 ltt_time_add(new_time_window
.start_time
,
3343 new_time_window
.time_width
)
3347 /* Fix the time width to fit start time and end time */
3348 new_time_window
.time_width
= ltt_time_sub(end_time
,
3349 new_time_window
.start_time
);
3351 time_change_manager(tab
, new_time_window
);
3356 on_MEntry2_value_changed (GtkSpinButton
*spinbutton
,
3359 Tab
*tab
=(Tab
*)user_data
;
3360 LttvTracesetContext
* tsc
=
3361 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
);
3362 TimeInterval time_span
= tsc
->time_span
;
3363 gint value
= gtk_spin_button_get_value_as_int(spinbutton
);
3365 TimeWindow new_time_window
= tab
->time_window
;
3367 LttTime end_time
= ltt_time_add(new_time_window
.start_time
,
3368 new_time_window
.time_width
);
3370 new_time_window
.start_time
.tv_nsec
= value
;
3372 /* check if end time selected is below or equal */
3373 if(ltt_time_compare(new_time_window
.start_time
, end_time
) >= 0) {
3374 /* Then, we must push back end time : keep the same time width
3375 * if possible, else end traceset time */
3376 end_time
= LTT_TIME_MIN(time_span
.end_time
,
3377 ltt_time_add(new_time_window
.start_time
,
3378 new_time_window
.time_width
)
3382 /* Fix the time width to fit start time and end time */
3383 new_time_window
.time_width
= ltt_time_sub(end_time
,
3384 new_time_window
.start_time
);
3386 time_change_manager(tab
, new_time_window
);
3391 on_MEntry3_value_changed (GtkSpinButton
*spinbutton
,
3394 Tab
*tab
=(Tab
*)user_data
;
3395 LttvTracesetContext
* tsc
=
3396 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
);
3397 TimeInterval time_span
= tsc
->time_span
;
3398 gint value
= gtk_spin_button_get_value_as_int(spinbutton
);
3400 TimeWindow new_time_window
= tab
->time_window
;
3402 LttTime end_time
= ltt_time_add(new_time_window
.start_time
,
3403 new_time_window
.time_width
);
3404 end_time
.tv_sec
= value
;
3406 /* end nanoseconds */
3407 if(end_time
.tv_sec
== time_span
.start_time
.tv_sec
) {
3408 if(end_time
.tv_nsec
< time_span
.start_time
.tv_nsec
)
3409 end_time
.tv_nsec
= time_span
.start_time
.tv_nsec
+1;
3411 else if(end_time
.tv_sec
== time_span
.end_time
.tv_sec
) {
3412 if(end_time
.tv_nsec
> time_span
.end_time
.tv_nsec
)
3413 end_time
.tv_nsec
= time_span
.end_time
.tv_nsec
;
3416 /* check if end time selected is below or equal */
3417 if(ltt_time_compare(new_time_window
.start_time
, end_time
) >= 0) {
3418 /* Then, we must push front start time : keep the same time width
3419 * if possible, else end traceset time */
3420 new_time_window
.start_time
= LTT_TIME_MAX(time_span
.start_time
,
3421 ltt_time_sub(end_time
,
3422 new_time_window
.time_width
)
3426 /* Fix the time width to fit start time and end time */
3427 new_time_window
.time_width
= ltt_time_sub(end_time
,
3428 new_time_window
.start_time
);
3430 time_change_manager(tab
, new_time_window
);
3435 on_MEntry4_value_changed (GtkSpinButton
*spinbutton
,
3438 Tab
*tab
=(Tab
*)user_data
;
3439 LttvTracesetContext
* tsc
=
3440 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
);
3441 TimeInterval time_span
= tsc
->time_span
;
3442 gint value
= gtk_spin_button_get_value_as_int(spinbutton
);
3444 TimeWindow new_time_window
= tab
->time_window
;
3446 LttTime end_time
= ltt_time_add(new_time_window
.start_time
,
3447 new_time_window
.time_width
);
3448 end_time
.tv_nsec
= value
;
3450 /* check if end time selected is below or equal */
3451 if(ltt_time_compare(new_time_window
.start_time
, end_time
) >= 0) {
3452 /* Then, we must push front start time : keep the same time width
3453 * if possible, else end traceset time */
3454 new_time_window
.start_time
= LTT_TIME_MAX(time_span
.start_time
,
3455 ltt_time_sub(end_time
,
3456 new_time_window
.time_width
)
3460 /* Fix the time width to fit start time and end time */
3461 new_time_window
.time_width
= ltt_time_sub(end_time
,
3462 new_time_window
.start_time
);
3464 time_change_manager(tab
, new_time_window
);
3469 void current_time_change_manager (Tab
*tab
,
3470 LttTime new_current_time
)
3472 /* Only one source of time change */
3473 if(tab
->current_time_manager_lock
== TRUE
) return;
3475 tab
->current_time_manager_lock
= TRUE
;
3477 LttvTracesetContext
*tsc
= LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
);
3478 TimeInterval time_span
= tsc
->time_span
;
3480 /* current seconds */
3481 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry5
),
3482 (double)time_span
.start_time
.tv_sec
,
3483 (double)time_span
.end_time
.tv_sec
);
3484 gtk_spin_button_set_value(GTK_SPIN_BUTTON(tab
->MEntry5
),
3485 (double)new_current_time
.tv_sec
);
3486 /* start nanoseconds */
3487 if(new_current_time
.tv_sec
== time_span
.start_time
.tv_sec
) {
3488 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry6
),
3489 (double)time_span
.start_time
.tv_nsec
,
3490 (double)NANOSECONDS_PER_SECOND
-1);
3492 else if(new_current_time
.tv_sec
== time_span
.end_time
.tv_sec
) {
3493 /* If we are at the end, max nsec to end.. */
3494 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry6
),
3496 (double)time_span
.end_time
.tv_nsec
);
3498 else /* anywhere else */
3499 gtk_spin_button_set_range(GTK_SPIN_BUTTON(tab
->MEntry6
),
3501 (double)NANOSECONDS_PER_SECOND
-1);
3502 gtk_spin_button_set_value(GTK_SPIN_BUTTON(tab
->MEntry6
),
3503 (double)new_current_time
.tv_nsec
);
3505 set_current_time(tab
, &new_current_time
);
3507 tab
->current_time_manager_lock
= FALSE
;
3511 on_MEntry5_value_changed (GtkSpinButton
*spinbutton
,
3514 Tab
*tab
= (Tab
*)user_data
;
3515 LttvTracesetContext
* tsc
=
3516 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
);
3517 TimeInterval time_span
= tsc
->time_span
;
3518 gint value
= gtk_spin_button_get_value_as_int(spinbutton
);
3519 LttTime new_current_time
= tab
->current_time
;
3520 new_current_time
.tv_sec
= value
;
3522 /* current nanoseconds */
3523 if(new_current_time
.tv_sec
== time_span
.start_time
.tv_sec
) {
3524 if(new_current_time
.tv_nsec
< time_span
.start_time
.tv_nsec
)
3525 new_current_time
.tv_nsec
= time_span
.start_time
.tv_nsec
;
3527 else if(new_current_time
.tv_sec
== time_span
.end_time
.tv_sec
) {
3528 if(new_current_time
.tv_nsec
> time_span
.end_time
.tv_nsec
)
3529 new_current_time
.tv_nsec
= time_span
.end_time
.tv_nsec
;
3532 current_time_change_manager(tab
, new_current_time
);
3536 on_MEntry6_value_changed (GtkSpinButton
*spinbutton
,
3539 Tab
*tab
= (Tab
*)user_data
;
3540 gint value
= gtk_spin_button_get_value_as_int(spinbutton
);
3541 LttTime new_current_time
= tab
->current_time
;
3542 new_current_time
.tv_nsec
= value
;
3544 current_time_change_manager(tab
, new_current_time
);
3548 void scroll_value_changed_cb(GtkWidget
*scrollbar
,
3551 Tab
*tab
= (Tab
*)user_data
;
3552 TimeWindow new_time_window
;
3554 GtkAdjustment
*adjust
= gtk_range_get_adjustment(GTK_RANGE(scrollbar
));
3555 gdouble value
= gtk_adjustment_get_value(adjust
);
3556 // gdouble upper, lower, ratio, page_size;
3558 LttvTracesetContext
* tsc
=
3559 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
);
3560 TimeInterval time_span
= tsc
->time_span
;
3562 time
= ltt_time_add(ltt_time_from_double(value
/NANOSECONDS_PER_SECOND
),
3563 time_span
.start_time
);
3565 new_time_window
.start_time
= time
;
3567 page_size
= adjust
->page_size
;
3569 new_time_window
.time_width
=
3570 ltt_time_from_double(page_size
/NANOSECONDS_PER_SECOND
);
3573 time_change_manager(tab
, new_time_window
);
3575 //time_window = tab->time_window;
3577 lower
= adjust
->lower
;
3578 upper
= adjust
->upper
;
3579 ratio
= (value
- lower
) / (upper
- lower
);
3580 g_info("lower %lu, upper %lu, value %lu, ratio %lu", lower
, upper
, value
, ratio
);
3582 //time = ltt_time_sub(time_span->end_time, time_span->start_time);
3583 //time = ltt_time_mul(time, (float)ratio);
3584 //time = ltt_time_add(time_span->start_time, time);
3585 time
= ltt_time_add(ltt_time_from_double(value
/NANOSECONDS_PER_SECOND
),
3586 time_span
.start_time
);
3588 time_window
.start_time
= time
;
3590 page_size
= adjust
->page_size
;
3592 time_window
.time_width
=
3593 ltt_time_from_double(page_size
/NANOSECONDS_PER_SECOND
);
3594 //time = ltt_time_sub(time_span.end_time, time);
3595 //if(ltt_time_compare(time,time_window.time_width) < 0){
3596 // time_window.time_width = time;
3599 /* call viewer hooks for new time window */
3600 set_time_window(tab
, &time_window
);
3605 /* callback function to check or uncheck the check box (filter)
3608 void checkbox_changed(GtkTreeView
*treeview
,
3610 GtkTreeViewColumn
*arg2
,
3613 GtkTreeStore
* store
= (GtkTreeStore
*)gtk_tree_view_get_model (treeview
);
3617 if (gtk_tree_model_get_iter ((GtkTreeModel
*)store
, &iter
, arg1
)){
3618 gtk_tree_model_get ((GtkTreeModel
*)store
, &iter
, CHECKBOX_COLUMN
, &value
, -1);
3619 value
= value
? FALSE
: TRUE
;
3620 gtk_tree_store_set (GTK_TREE_STORE (store
), &iter
, CHECKBOX_COLUMN
, value
, -1);
3626 /* According to user's selection, update selector(filter)
3629 void update_filter(LttvTracesetSelector
*s
, GtkTreeStore
*store
)
3631 GtkTreeIter iter
, child_iter
, child_iter1
, child_iter2
;
3632 int i
, j
, k
, nb_eventtype
;
3633 LttvTraceSelector
* trace
;
3634 LttvTracefileSelector
* tracefile
;
3635 LttvEventtypeSelector
* eventtype
;
3636 gboolean value
, value1
, value2
;
3638 if(gtk_tree_model_get_iter_first((GtkTreeModel
*)store
, &iter
)){
3641 trace
= lttv_traceset_selector_trace_get(s
, i
);
3642 nb_eventtype
= lttv_trace_selector_eventtype_number(trace
);
3643 gtk_tree_model_get ((GtkTreeModel
*)store
, &iter
, CHECKBOX_COLUMN
, &value
,-1);
3646 if(gtk_tree_model_iter_children ((GtkTreeModel
*)store
, &child_iter
, &iter
)){
3648 if(j
<1){//eventtype selector for trace
3649 gtk_tree_model_get ((GtkTreeModel
*)store
, &child_iter
, CHECKBOX_COLUMN
, &value2
,-1);
3652 if(gtk_tree_model_iter_children ((GtkTreeModel
*)store
, &child_iter1
, &child_iter
)){
3654 eventtype
= lttv_trace_selector_eventtype_get(trace
,k
);
3655 gtk_tree_model_get ((GtkTreeModel
*)store
, &child_iter1
, CHECKBOX_COLUMN
, &value2
,-1);
3656 lttv_eventtype_selector_set_selected(eventtype
,value2
);
3658 }while(gtk_tree_model_iter_next((GtkTreeModel
*)store
, &child_iter1
));
3661 }else{ //tracefile selector
3662 tracefile
= lttv_trace_selector_tracefile_get(trace
, j
- 1);
3663 gtk_tree_model_get ((GtkTreeModel
*)store
, &child_iter
, CHECKBOX_COLUMN
, &value1
,-1);
3664 lttv_tracefile_selector_set_selected(tracefile
,value1
);
3666 gtk_tree_model_iter_children((GtkTreeModel
*)store
, &child_iter1
, &child_iter
); //eventtype selector
3667 gtk_tree_model_get ((GtkTreeModel
*)store
, &child_iter1
, CHECKBOX_COLUMN
, &value2
,-1);
3670 if(gtk_tree_model_iter_children ((GtkTreeModel
*)store
, &child_iter2
, &child_iter1
)){
3671 do{//eventtype selector for tracefile
3672 eventtype
= lttv_tracefile_selector_eventtype_get(tracefile
,k
);
3673 gtk_tree_model_get ((GtkTreeModel
*)store
, &child_iter2
, CHECKBOX_COLUMN
, &value2
,-1);
3674 lttv_eventtype_selector_set_selected(eventtype
,value2
);
3676 }while(gtk_tree_model_iter_next((GtkTreeModel
*)store
, &child_iter2
));
3682 }while(gtk_tree_model_iter_next((GtkTreeModel
*)store
, &child_iter
));
3685 lttv_trace_selector_set_selected(trace
,value
);
3687 }while(gtk_tree_model_iter_next((GtkTreeModel
*)store
, &iter
));
3692 /* Display a dialogue showing all eventtypes and traces, let user to select the interested
3693 * eventtypes, tracefiles and traces (filter)
3696 gboolean
get_filter_selection(LttvTracesetSelector
*s
,char *title
, char * column_title
)
3698 GtkWidget
* dialogue
;
3699 GtkTreeStore
* store
;
3701 GtkWidget
* scroll_win
;
3702 GtkCellRenderer
* renderer
;
3703 GtkTreeViewColumn
* column
;
3704 GtkTreeIter iter
, child_iter
, child_iter1
, child_iter2
;
3705 int i
, j
, k
, id
, nb_trace
, nb_tracefile
, nb_eventtype
;
3706 LttvTraceSelector
* trace
;
3707 LttvTracefileSelector
* tracefile
;
3708 LttvEventtypeSelector
* eventtype
;
3712 dialogue
= gtk_dialog_new_with_buttons(title
,
3715 GTK_STOCK_OK
,GTK_RESPONSE_ACCEPT
,
3716 GTK_STOCK_CANCEL
,GTK_RESPONSE_REJECT
,
3718 gtk_window_set_default_size((GtkWindow
*)dialogue
, 300, 500);
3720 store
= gtk_tree_store_new (TOTAL_COLUMNS
, G_TYPE_BOOLEAN
, G_TYPE_STRING
);
3721 tree
= gtk_tree_view_new_with_model (GTK_TREE_MODEL (store
));
3722 g_object_unref (G_OBJECT (store
));
3723 g_signal_connect (G_OBJECT (tree
), "row-activated",
3724 G_CALLBACK (checkbox_changed
),
3728 renderer
= gtk_cell_renderer_toggle_new ();
3729 gtk_cell_renderer_toggle_set_radio((GtkCellRendererToggle
*)renderer
, FALSE
);
3731 g_object_set (G_OBJECT (renderer
),"activatable", TRUE
, NULL
);
3733 column
= gtk_tree_view_column_new_with_attributes ("Checkbox",
3735 "active", CHECKBOX_COLUMN
,
3737 gtk_tree_view_column_set_alignment (column
, 0.5);
3738 gtk_tree_view_column_set_fixed_width (column
, 20);
3739 gtk_tree_view_append_column (GTK_TREE_VIEW (tree
), column
);
3741 renderer
= gtk_cell_renderer_text_new ();
3742 column
= gtk_tree_view_column_new_with_attributes (column_title
,
3744 "text", NAME_COLUMN
,
3746 gtk_tree_view_column_set_alignment (column
, 0.0);
3747 gtk_tree_view_append_column (GTK_TREE_VIEW (tree
), column
);
3748 gtk_tree_view_set_headers_visible(GTK_TREE_VIEW (tree
), FALSE
);
3750 scroll_win
= gtk_scrolled_window_new (NULL
, NULL
);
3751 gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(scroll_win
),
3752 GTK_POLICY_AUTOMATIC
,GTK_POLICY_AUTOMATIC
);
3753 gtk_container_add (GTK_CONTAINER (scroll_win
), tree
);
3755 gtk_box_pack_start(GTK_BOX(GTK_DIALOG(dialogue
)->vbox
), scroll_win
,TRUE
, TRUE
,0);
3757 gtk_widget_show(scroll_win
);
3758 gtk_widget_show(tree
);
3760 nb_trace
= lttv_traceset_selector_trace_number(s
);
3761 for(i
=0;i
<nb_trace
;i
++){
3762 trace
= lttv_traceset_selector_trace_get(s
, i
);
3763 name
= lttv_trace_selector_get_name(trace
);
3764 gtk_tree_store_append (store
, &iter
, NULL
);
3765 checked
= lttv_trace_selector_get_selected(trace
);
3766 gtk_tree_store_set (store
, &iter
,
3767 CHECKBOX_COLUMN
,checked
,
3771 gtk_tree_store_append (store
, &child_iter
, &iter
);
3772 gtk_tree_store_set (store
, &child_iter
,
3773 CHECKBOX_COLUMN
, checked
,
3774 NAME_COLUMN
,"eventtype",
3777 nb_eventtype
= lttv_trace_selector_eventtype_number(trace
);
3778 for(j
=0;j
<nb_eventtype
;j
++){
3779 eventtype
= lttv_trace_selector_eventtype_get(trace
,j
);
3780 name
= lttv_eventtype_selector_get_name(eventtype
);
3781 checked
= lttv_eventtype_selector_get_selected(eventtype
);
3782 gtk_tree_store_append (store
, &child_iter1
, &child_iter
);
3783 gtk_tree_store_set (store
, &child_iter1
,
3784 CHECKBOX_COLUMN
, checked
,
3789 nb_tracefile
= lttv_trace_selector_tracefile_number(trace
);
3790 for(j
=0;j
<nb_tracefile
;j
++){
3791 tracefile
= lttv_trace_selector_tracefile_get(trace
, j
);
3792 name
= lttv_tracefile_selector_get_name(tracefile
);
3793 gtk_tree_store_append (store
, &child_iter
, &iter
);
3794 checked
= lttv_tracefile_selector_get_selected(tracefile
);
3795 gtk_tree_store_set (store
, &child_iter
,
3796 CHECKBOX_COLUMN
, checked
,
3800 gtk_tree_store_append (store
, &child_iter1
, &child_iter
);
3801 gtk_tree_store_set (store
, &child_iter1
,
3802 CHECKBOX_COLUMN
, checked
,
3803 NAME_COLUMN
,"eventtype",
3806 for(k
=0;k
<nb_eventtype
;k
++){
3807 eventtype
= lttv_tracefile_selector_eventtype_get(tracefile
,k
);
3808 name
= lttv_eventtype_selector_get_name(eventtype
);
3809 checked
= lttv_eventtype_selector_get_selected(eventtype
);
3810 gtk_tree_store_append (store
, &child_iter2
, &child_iter1
);
3811 gtk_tree_store_set (store
, &child_iter2
,
3812 CHECKBOX_COLUMN
, checked
,
3819 id
= gtk_dialog_run(GTK_DIALOG(dialogue
));
3821 case GTK_RESPONSE_ACCEPT
:
3822 case GTK_RESPONSE_OK
:
3823 update_filter(s
, store
);
3824 gtk_widget_destroy(dialogue
);
3826 case GTK_RESPONSE_REJECT
:
3827 case GTK_RESPONSE_CANCEL
:
3829 gtk_widget_destroy(dialogue
);
3836 /* Select a trace which will be removed from traceset
3839 char * get_remove_trace(char ** all_trace_name
, int nb_trace
)
3841 return get_selection(all_trace_name
, nb_trace
,
3842 "Select a trace", "Trace pathname");
3846 /* Select a module which will be loaded
3849 char * get_load_module(char ** load_module_name
, int nb_module
)
3851 return get_selection(load_module_name
, nb_module
,
3852 "Select a module to load", "Module name");
3858 /* Select a module which will be unloaded
3861 char * get_unload_module(char ** loaded_module_name
, int nb_module
)
3863 return get_selection(loaded_module_name
, nb_module
,
3864 "Select a module to unload", "Module name");
3868 /* Display a dialogue which shows all selectable items, let user to
3869 * select one of them
3872 char * get_selection(char ** loaded_module_name
, int nb_module
,
3873 char *title
, char * column_title
)
3875 GtkWidget
* dialogue
;
3876 GtkWidget
* scroll_win
;
3878 GtkListStore
* store
;
3879 GtkTreeViewColumn
* column
;
3880 GtkCellRenderer
* renderer
;
3881 GtkTreeSelection
* select
;
3884 char * unload_module_name
= NULL
;
3886 dialogue
= gtk_dialog_new_with_buttons(title
,
3889 GTK_STOCK_OK
,GTK_RESPONSE_ACCEPT
,
3890 GTK_STOCK_CANCEL
,GTK_RESPONSE_REJECT
,
3892 gtk_window_set_default_size((GtkWindow
*)dialogue
, 500, 200);
3894 scroll_win
= gtk_scrolled_window_new (NULL
, NULL
);
3895 gtk_widget_show ( scroll_win
);
3896 gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(scroll_win
),
3897 GTK_POLICY_AUTOMATIC
, GTK_POLICY_AUTOMATIC
);
3899 store
= gtk_list_store_new (N_COLUMNS
,G_TYPE_STRING
);
3900 tree
= gtk_tree_view_new_with_model(GTK_TREE_MODEL (store
));
3901 gtk_widget_show ( tree
);
3902 g_object_unref (G_OBJECT (store
));
3904 renderer
= gtk_cell_renderer_text_new ();
3905 column
= gtk_tree_view_column_new_with_attributes (column_title
,
3907 "text", MODULE_COLUMN
,
3909 gtk_tree_view_column_set_alignment (column
, 0.5);
3910 gtk_tree_view_column_set_fixed_width (column
, 150);
3911 gtk_tree_view_append_column (GTK_TREE_VIEW (tree
), column
);
3913 select
= gtk_tree_view_get_selection (GTK_TREE_VIEW (tree
));
3914 gtk_tree_selection_set_mode (select
, GTK_SELECTION_SINGLE
);
3916 gtk_container_add (GTK_CONTAINER (scroll_win
), tree
);
3918 gtk_box_pack_start(GTK_BOX(GTK_DIALOG(dialogue
)->vbox
), scroll_win
,TRUE
, TRUE
,0);
3920 for(i
=0;i
<nb_module
;i
++){
3921 gtk_list_store_append (store
, &iter
);
3922 gtk_list_store_set (store
, &iter
, MODULE_COLUMN
,loaded_module_name
[i
],-1);
3925 id
= gtk_dialog_run(GTK_DIALOG(dialogue
));
3927 case GTK_RESPONSE_ACCEPT
:
3928 case GTK_RESPONSE_OK
:
3929 if (gtk_tree_selection_get_selected (select
, (GtkTreeModel
**)&store
, &iter
)){
3930 gtk_tree_model_get ((GtkTreeModel
*)store
, &iter
, MODULE_COLUMN
, &unload_module_name
, -1);
3932 case GTK_RESPONSE_REJECT
:
3933 case GTK_RESPONSE_CANCEL
:
3935 gtk_widget_destroy(dialogue
);
3939 return unload_module_name
;
3943 /* Insert all menu entry and tool buttons into this main window
3948 void add_all_menu_toolbar_constructors(MainWindow
* mw
, gpointer user_data
)
3952 lttvwindow_viewer_constructor constructor
;
3953 LttvMenus
* global_menu
, * instance_menu
;
3954 LttvToolbars
* global_toolbar
, * instance_toolbar
;
3955 LttvMenuClosure
*menu_item
;
3956 LttvToolbarClosure
*toolbar_item
;
3957 LttvAttributeValue value
;
3958 LttvIAttribute
*global_attributes
= LTTV_IATTRIBUTE(lttv_global_attributes());
3959 LttvIAttribute
*attributes
= mw
->attributes
;
3960 GtkWidget
* tool_menu_title_menu
, *new_widget
, *pixmap
;
3962 g_assert(lttv_iattribute_find_by_path(global_attributes
,
3963 "viewers/menu", LTTV_POINTER
, &value
));
3964 if(*(value
.v_pointer
) == NULL
)
3965 *(value
.v_pointer
) = lttv_menus_new();
3966 global_menu
= (LttvMenus
*)*(value
.v_pointer
);
3968 g_assert(lttv_iattribute_find_by_path(attributes
,
3969 "viewers/menu", LTTV_POINTER
, &value
));
3970 if(*(value
.v_pointer
) == NULL
)
3971 *(value
.v_pointer
) = lttv_menus_new();
3972 instance_menu
= (LttvMenus
*)*(value
.v_pointer
);
3976 g_assert(lttv_iattribute_find_by_path(global_attributes
,
3977 "viewers/toolbar", LTTV_POINTER
, &value
));
3978 if(*(value
.v_pointer
) == NULL
)
3979 *(value
.v_pointer
) = lttv_toolbars_new();
3980 global_toolbar
= (LttvToolbars
*)*(value
.v_pointer
);
3982 g_assert(lttv_iattribute_find_by_path(attributes
,
3983 "viewers/toolbar", LTTV_POINTER
, &value
));
3984 if(*(value
.v_pointer
) == NULL
)
3985 *(value
.v_pointer
) = lttv_toolbars_new();
3986 instance_toolbar
= (LttvToolbars
*)*(value
.v_pointer
);
3988 /* Add missing menu entries to window instance */
3989 for(i
=0;i
<global_menu
->len
;i
++) {
3990 menu_item
= &g_array_index(global_menu
, LttvMenuClosure
, i
);
3992 //add menu_item to window instance;
3993 constructor
= menu_item
->con
;
3994 tool_menu_title_menu
= lookup_widget(mw
->mwindow
,"ToolMenuTitle_menu");
3996 gtk_menu_item_new_with_mnemonic (menu_item
->menu_text
);
3997 gtk_container_add (GTK_CONTAINER (tool_menu_title_menu
),
3999 g_signal_connect ((gpointer
) new_widget
, "activate",
4000 G_CALLBACK (insert_viewer_wrap
),
4002 gtk_widget_show (new_widget
);
4003 lttv_menus_add(instance_menu
, menu_item
->con
,
4004 menu_item
->menu_path
,
4005 menu_item
->menu_text
,
4010 /* Add missing toolbar entries to window instance */
4011 for(i
=0;i
<global_toolbar
->len
;i
++) {
4012 toolbar_item
= &g_array_index(global_toolbar
, LttvToolbarClosure
, i
);
4014 //add toolbar_item to window instance;
4015 constructor
= toolbar_item
->con
;
4016 tool_menu_title_menu
= lookup_widget(mw
->mwindow
,"MToolbar1");
4017 pixbuf
= gdk_pixbuf_new_from_xpm_data((const char**)toolbar_item
->pixmap
);
4018 pixmap
= gtk_image_new_from_pixbuf(pixbuf
);
4020 gtk_toolbar_append_element (GTK_TOOLBAR (tool_menu_title_menu
),
4021 GTK_TOOLBAR_CHILD_BUTTON
,
4024 toolbar_item
->tooltip
, NULL
,
4025 pixmap
, NULL
, NULL
);
4026 gtk_label_set_use_underline(
4027 GTK_LABEL (((GtkToolbarChild
*) (
4028 g_list_last (GTK_TOOLBAR
4029 (tool_menu_title_menu
)->children
)->data
))->label
),
4031 gtk_container_set_border_width (GTK_CONTAINER (new_widget
), 1);
4032 g_signal_connect ((gpointer
) new_widget
,
4034 G_CALLBACK (insert_viewer_wrap
),
4036 gtk_widget_show (new_widget
);
4038 lttv_toolbars_add(instance_toolbar
, toolbar_item
->con
,
4039 toolbar_item
->tooltip
,
4040 toolbar_item
->pixmap
,
4048 /* Create a main window
4051 void construct_main_window(MainWindow
* parent
)
4053 g_debug("construct_main_window()");
4054 GtkWidget
* new_window
; /* New generated main window */
4055 MainWindow
* new_m_window
;/* New main window structure */
4056 GtkNotebook
* notebook
;
4057 LttvIAttribute
*attributes
=
4058 LTTV_IATTRIBUTE(g_object_new(LTTV_ATTRIBUTE_TYPE
, NULL
));
4059 LttvAttributeValue value
;
4062 new_m_window
= g_new(MainWindow
, 1);
4064 // Add the object's information to the module's array
4065 g_main_window_list
= g_slist_append(g_main_window_list
, new_m_window
);
4067 new_window
= create_MWindow();
4068 gtk_widget_show (new_window
);
4070 new_m_window
->mwindow
= new_window
;
4071 new_m_window
->attributes
= attributes
;
4073 g_assert(lttv_iattribute_find_by_path(attributes
,
4074 "viewers/menu", LTTV_POINTER
, &value
));
4075 *(value
.v_pointer
) = lttv_menus_new();
4077 g_assert(lttv_iattribute_find_by_path(attributes
,
4078 "viewers/toolbar", LTTV_POINTER
, &value
));
4079 *(value
.v_pointer
) = lttv_toolbars_new();
4081 add_all_menu_toolbar_constructors(new_m_window
, NULL
);
4083 g_object_set_data_full(G_OBJECT(new_window
),
4085 (gpointer
)new_m_window
,
4086 (GDestroyNotify
)g_free
);
4087 //create a default tab
4088 notebook
= (GtkNotebook
*)lookup_widget(new_m_window
->mwindow
, "MNotebook");
4089 if(notebook
== NULL
){
4090 g_printf("Notebook does not exist\n");
4093 //gtk_notebook_popup_enable (GTK_NOTEBOOK(notebook));
4094 //for now there is no name field in LttvTraceset structure
4095 //Use "Traceset" as the label for the default tab
4097 GtkWidget
* parent_notebook
= lookup_widget(parent
->mwindow
, "MNotebook");
4098 GtkWidget
*page
= gtk_notebook_get_nth_page(GTK_NOTEBOOK(parent_notebook
),
4099 gtk_notebook_get_current_page(GTK_NOTEBOOK(parent_notebook
)));
4105 parent_tab
= (Tab
*)g_object_get_data(G_OBJECT(page
), "Tab_Info");
4107 new_tab
= create_tab(new_m_window
, parent_tab
, notebook
, "Traceset");
4109 new_tab
= create_tab(new_m_window
, NULL
, notebook
, "Traceset");
4110 /* First window, use command line trace */
4111 if(g_init_trace
!= NULL
){
4112 lttvwindow_add_trace(new_tab
,
4116 LttvTraceset
*traceset
= new_tab
->traceset_info
->traceset
;
4117 SetTraceset(new_tab
, traceset
);
4120 g_printf("There are now : %d windows\n",g_slist_length(g_main_window_list
));
4124 /* Free the memory occupied by a tab structure
4128 void tab_destructor(Tab
* tab_instance
)
4130 int i
, nb
, ref_count
;
4133 if(tab_instance
->attributes
)
4134 g_object_unref(tab_instance
->attributes
);
4136 if(tab_instance
->interrupted_state
)
4137 g_object_unref(tab_instance
->interrupted_state
);
4140 if(tab_instance
->traceset_info
->traceset_context
!= NULL
){
4141 //remove state update hooks
4142 lttv_state_remove_event_hooks(
4143 (LttvTracesetState
*)tab_instance
->traceset_info
->
4145 lttv_context_fini(LTTV_TRACESET_CONTEXT(tab_instance
->traceset_info
->
4147 g_object_unref(tab_instance
->traceset_info
->traceset_context
);
4149 if(tab_instance
->traceset_info
->traceset
!= NULL
) {
4150 nb
= lttv_traceset_number(tab_instance
->traceset_info
->traceset
);
4151 for(i
= 0 ; i
< nb
; i
++) {
4152 trace
= lttv_traceset_get(tab_instance
->traceset_info
->traceset
, i
);
4153 ref_count
= lttv_trace_get_ref_number(trace
);
4155 ltt_trace_close(lttv_trace(trace
));
4159 lttv_traceset_destroy(tab_instance
->traceset_info
->traceset
);
4160 /* Remove the idle events requests processing function of the tab */
4161 g_idle_remove_by_data(tab_instance
);
4163 g_slist_free(tab_instance
->events_requests
);
4164 g_free(tab_instance
->traceset_info
);
4165 g_free(tab_instance
);
4169 /* Create a tab and insert it into the current main window
4172 Tab
* create_tab(MainWindow
* mw
, Tab
*copy_tab
,
4173 GtkNotebook
* notebook
, char * label
)
4179 //create a new tab data structure
4182 //construct and initialize the traceset_info
4183 tab
->traceset_info
= g_new(TracesetInfo
,1);
4186 tab
->traceset_info
->traceset
=
4187 lttv_traceset_copy(copy_tab
->traceset_info
->traceset
);
4189 tab
->traceset_info
->traceset
= lttv_traceset_new();
4193 lttv_attribute_write_xml(
4194 lttv_traceset_attribute(tab
->traceset_info
->traceset
),
4200 tab
->time_manager_lock
= FALSE
;
4201 tab
->current_time_manager_lock
= FALSE
;
4203 //FIXME copy not implemented in lower level
4204 tab
->traceset_info
->traceset_context
=
4205 g_object_new(LTTV_TRACESET_STATS_TYPE
, NULL
);
4206 g_assert(tab
->traceset_info
->traceset_context
!= NULL
);
4208 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
),
4209 tab
->traceset_info
->traceset
);
4210 //add state update hooks
4211 lttv_state_add_event_hooks(
4212 (LttvTracesetState
*)tab
->traceset_info
->traceset_context
);
4214 //determine the current_time and time_window of the tab
4216 if(copy_tab
!= NULL
){
4217 tab
->time_window
= copy_tab
->time_window
;
4218 tab
->current_time
= copy_tab
->current_time
;
4220 tab
->time_window
.start_time
=
4221 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
)->
4222 time_span
.start_time
;
4223 if(DEFAULT_TIME_WIDTH_S
<
4224 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
)->
4225 time_span
.end_time
.tv_sec
)
4226 tmp_time
.tv_sec
= DEFAULT_TIME_WIDTH_S
;
4229 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
)->
4230 time_span
.end_time
.tv_sec
;
4231 tmp_time
.tv_nsec
= 0;
4232 tab
->time_window
.time_width
= tmp_time
;
4233 tab
->current_time
.tv_sec
=
4234 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
)->
4235 time_span
.start_time
.tv_sec
;
4236 tab
->current_time
.tv_nsec
=
4237 LTTV_TRACESET_CONTEXT(tab
->traceset_info
->traceset_context
)->
4238 time_span
.start_time
.tv_nsec
;
4241 tab
->attributes
= LTTV_IATTRIBUTE(g_object_new(LTTV_ATTRIBUTE_TYPE
, NULL
));
4242 tab
->interrupted_state
= g_object_new(LTTV_ATTRIBUTE_TYPE
, NULL
);
4244 tab
->vbox
= gtk_vbox_new(FALSE
, 2);
4245 tab
->viewer_container
= gtk_vbox_new(TRUE
, 2);
4246 tab
->scrollbar
= gtk_hscrollbar_new(NULL
);
4247 //tab->multivpaned = gtk_multi_vpaned_new();
4249 gtk_box_pack_start(GTK_BOX(tab
->vbox
),
4250 tab
->viewer_container
,
4252 TRUE
, /* Give the extra space to the child */
4253 0); /* No padding */
4255 /* Create the timebar */
4257 tab
->MTimebar
= gtk_hbox_new(FALSE
, 2);
4258 gtk_widget_show(tab
->MTimebar
);
4260 tab
->MText1
= gtk_label_new("Time Frame start: ");
4261 gtk_widget_show(tab
->MText1
);
4262 tab
->MText2
= gtk_label_new("s");
4263 gtk_widget_show(tab
->MText2
);
4264 tab
->MText3a
= gtk_label_new("ns");
4265 gtk_widget_show(tab
->MText3a
);
4266 tab
->MText3b
= gtk_label_new("end:");
4267 gtk_widget_show(tab
->MText3b
);
4268 tab
->MText4
= gtk_label_new("s");
4269 gtk_widget_show(tab
->MText4
);
4270 tab
->MText5a
= gtk_label_new("ns");
4271 gtk_widget_show(tab
->MText5a
);
4272 tab
->MText5b
= gtk_label_new("Current Time:");
4273 gtk_widget_show(tab
->MText5b
);
4274 tab
->MText6
= gtk_label_new("s");
4275 gtk_widget_show(tab
->MText6
);
4276 tab
->MText7
= gtk_label_new("ns");
4277 gtk_widget_show(tab
->MText7
);
4279 tab
->MEntry1
= gtk_spin_button_new_with_range(0.0, 1.0, 1.0);
4280 gtk_spin_button_set_digits(GTK_SPIN_BUTTON(tab
->MEntry1
),0);
4281 gtk_spin_button_set_snap_to_ticks(GTK_SPIN_BUTTON(tab
->MEntry1
),TRUE
);
4282 gtk_widget_show(tab
->MEntry1
);
4283 tab
->MEntry2
= gtk_spin_button_new_with_range(0.0, 1.0, 1.0);
4284 gtk_spin_button_set_digits(GTK_SPIN_BUTTON(tab
->MEntry2
),0);
4285 gtk_spin_button_set_snap_to_ticks(GTK_SPIN_BUTTON(tab
->MEntry2
),TRUE
);
4286 gtk_widget_show(tab
->MEntry2
);
4287 tab
->MEntry3
= gtk_spin_button_new_with_range(0.0, 1.0, 1.0);
4288 gtk_spin_button_set_digits(GTK_SPIN_BUTTON(tab
->MEntry3
),0);
4289 gtk_spin_button_set_snap_to_ticks(GTK_SPIN_BUTTON(tab
->MEntry3
),TRUE
);
4290 gtk_widget_show(tab
->MEntry3
);
4291 tab
->MEntry4
= gtk_spin_button_new_with_range(0.0, 1.0, 1.0);
4292 gtk_spin_button_set_digits(GTK_SPIN_BUTTON(tab
->MEntry4
),0);
4293 gtk_spin_button_set_snap_to_ticks(GTK_SPIN_BUTTON(tab
->MEntry4
),TRUE
);
4294 gtk_widget_show(tab
->MEntry4
);
4295 tab
->MEntry5
= gtk_spin_button_new_with_range(0.0, 1.0, 1.0);
4296 gtk_spin_button_set_digits(GTK_SPIN_BUTTON(tab
->MEntry5
),0);
4297 gtk_spin_button_set_snap_to_ticks(GTK_SPIN_BUTTON(tab
->MEntry5
),TRUE
);
4298 gtk_widget_show(tab
->MEntry5
);
4299 tab
->MEntry6
= gtk_spin_button_new_with_range(0.0, 1.0, 1.0);
4300 gtk_spin_button_set_digits(GTK_SPIN_BUTTON(tab
->MEntry6
),0);
4301 gtk_spin_button_set_snap_to_ticks(GTK_SPIN_BUTTON(tab
->MEntry6
),TRUE
);
4302 gtk_widget_show(tab
->MEntry6
);
4305 GtkWidget
*temp_widget
;
4307 gtk_box_pack_start (GTK_BOX (tab
->MTimebar
), tab
->MText1
, FALSE
, FALSE
, 0);
4308 gtk_box_pack_start (GTK_BOX (tab
->MTimebar
), tab
->MEntry1
, FALSE
, FALSE
, 0);
4309 gtk_box_pack_start (GTK_BOX (tab
->MTimebar
), tab
->MText2
, FALSE
, FALSE
, 0);
4310 gtk_box_pack_start (GTK_BOX (tab
->MTimebar
), tab
->MEntry2
, FALSE
, FALSE
, 0);
4311 gtk_box_pack_start (GTK_BOX (tab
->MTimebar
), tab
->MText3a
, FALSE
, FALSE
, 0);
4312 temp_widget
= gtk_vseparator_new();
4313 gtk_widget_show(temp_widget
);
4314 gtk_box_pack_start (GTK_BOX (tab
->MTimebar
), temp_widget
, FALSE
, FALSE
, 0);
4315 gtk_box_pack_start (GTK_BOX (tab
->MTimebar
), tab
->MText3b
, FALSE
, FALSE
, 0);
4316 gtk_box_pack_start (GTK_BOX (tab
->MTimebar
), tab
->MEntry3
, FALSE
, FALSE
, 0);
4317 gtk_box_pack_start (GTK_BOX (tab
->MTimebar
), tab
->MText4
, FALSE
, FALSE
, 0);
4318 gtk_box_pack_start (GTK_BOX (tab
->MTimebar
), tab
->MEntry4
, FALSE
, FALSE
, 0);
4319 gtk_box_pack_start (GTK_BOX (tab
->MTimebar
), tab
->MText5a
, FALSE
, FALSE
, 0);
4320 temp_widget
= gtk_vseparator_new();
4321 gtk_widget_show(temp_widget
);
4322 gtk_box_pack_end (GTK_BOX (tab
->MTimebar
), tab
->MText7
, FALSE
, FALSE
, 0);
4323 gtk_box_pack_end (GTK_BOX (tab
->MTimebar
), tab
->MEntry6
, FALSE
, FALSE
, 0);
4324 gtk_box_pack_end (GTK_BOX (tab
->MTimebar
), tab
->MText6
, FALSE
, FALSE
, 0);
4325 gtk_box_pack_end (GTK_BOX (tab
->MTimebar
), tab
->MEntry5
, FALSE
, FALSE
, 0);
4326 gtk_box_pack_end (GTK_BOX (tab
->MTimebar
), tab
->MText5b
, FALSE
, FALSE
, 0);
4327 gtk_box_pack_end (GTK_BOX (tab
->MTimebar
), temp_widget
, FALSE
, FALSE
, 0);
4330 gtk_box_pack_end(GTK_BOX(tab
->vbox
),
4332 FALSE
, /* Do not expand */
4333 FALSE
, /* Fill has no effect here (expand false) */
4334 0); /* No padding */
4336 gtk_box_pack_end(GTK_BOX(tab
->vbox
),
4338 FALSE
, /* Do not expand */
4339 FALSE
, /* Fill has no effect here (expand false) */
4340 0); /* No padding */
4342 g_object_set_data(G_OBJECT(tab
->viewer_container
), "focused_viewer", NULL
);
4348 // Display a label with a X
4349 GtkWidget *w_hbox = gtk_hbox_new(FALSE, 4);
4350 GtkWidget *w_label = gtk_label_new (label);
4351 GtkWidget *pixmap = create_pixmap(GTK_WIDGET(notebook), "close.png");
4352 GtkWidget *w_button = gtk_button_new ();
4353 gtk_container_add(GTK_CONTAINER(w_button), pixmap);
4354 //GtkWidget *w_button = gtk_button_new_with_label("x");
4356 gtk_button_set_relief(GTK_BUTTON(w_button), GTK_RELIEF_NONE);
4358 gtk_box_pack_start(GTK_BOX(w_hbox), w_label, TRUE, TRUE, 0);
4359 gtk_box_pack_end(GTK_BOX(w_hbox), w_button, FALSE,
4362 g_signal_connect_swapped (w_button, "clicked",
4363 G_CALLBACK (on_close_tab_X_clicked),
4366 gtk_widget_set_state(w_button, GTK_STATE_ACTIVE);
4368 gtk_widget_show (w_label);
4369 gtk_widget_show (pixmap);
4370 gtk_widget_show (w_button);
4371 gtk_widget_show (w_hbox);
4373 tab->label = w_hbox;
4377 tab
->label
= gtk_label_new (label
);
4379 gtk_widget_show(tab
->label
);
4380 gtk_widget_show(tab
->scrollbar
);
4381 gtk_widget_show(tab
->viewer_container
);
4382 gtk_widget_show(tab
->vbox
);
4383 //gtk_widget_show(tab->multivpaned);
4386 /* Start with empty events requests list */
4387 tab
->events_requests
= NULL
;
4388 tab
->events_request_pending
= FALSE
;
4390 g_object_set_data_full(
4391 G_OBJECT(tab
->vbox
),
4394 (GDestroyNotify
)tab_destructor
);
4396 g_signal_connect(G_OBJECT(tab
->scrollbar
), "value-changed",
4397 G_CALLBACK(scroll_value_changed_cb
), tab
);
4399 g_signal_connect ((gpointer
) tab
->MEntry1
, "value-changed",
4400 G_CALLBACK (on_MEntry1_value_changed
),
4402 g_signal_connect ((gpointer
) tab
->MEntry2
, "value-changed",
4403 G_CALLBACK (on_MEntry2_value_changed
),
4405 g_signal_connect ((gpointer
) tab
->MEntry3
, "value-changed",
4406 G_CALLBACK (on_MEntry3_value_changed
),
4408 g_signal_connect ((gpointer
) tab
->MEntry4
, "value-changed",
4409 G_CALLBACK (on_MEntry4_value_changed
),
4411 g_signal_connect ((gpointer
) tab
->MEntry5
, "value-changed",
4412 G_CALLBACK (on_MEntry5_value_changed
),
4414 g_signal_connect ((gpointer
) tab
->MEntry6
, "value-changed",
4415 G_CALLBACK (on_MEntry6_value_changed
),
4418 //g_signal_connect(G_OBJECT(tab->scrollbar), "changed",
4419 // G_CALLBACK(scroll_value_changed_cb), tab);
4422 //insert tab into notebook
4423 gtk_notebook_append_page(notebook
,
4426 list
= gtk_container_get_children(GTK_CONTAINER(notebook
));
4427 gtk_notebook_set_current_page(notebook
,g_list_length(list
)-1);
4428 // always show : not if(g_list_length(list)>1)
4429 gtk_notebook_set_show_tabs(notebook
, TRUE
);
4435 * execute_events_requests
4437 * Idle function that executes the pending requests for a tab.
4439 * @return return value : TRUE : keep the idle function, FALSE : remove it.
4441 gboolean
execute_events_requests(Tab
*tab
)
4443 return ( lttvwindow_process_pending_requests(tab
) );