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