2aae7aaca7bdb1deee1ffc06a79aa1a3b9dee744
[lttv.git] / lttv / modules / gui / tracecontrol / tracecontrol.c
1 /* This file is part of the Linux Trace Toolkit viewer
2 * Copyright (C) 2005 Mathieu Desnoyers
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
19 #ifdef HAVE_CONFIG_H
20 #include <config.h>
21 #endif
22
23 #include <glib.h>
24 #include <glib/gprintf.h>
25 #include <string.h>
26 #include <gtk/gtk.h>
27 #include <gdk/gdk.h>
28 #include <gdk/gdkkeysyms.h>
29
30 #include <lttv/lttv.h>
31 #include <lttv/module.h>
32 #include <lttv/hook.h>
33
34 #include <lttvwindow/lttvwindow.h>
35 #include <lttvwindow/lttvwindowtraces.h>
36 #include <lttvwindow/callbacks.h>
37 #include <lttvwindow/lttv_plugin_tab.h>
38
39 #include "hTraceControlInsert.xpm"
40 #include "TraceControlStart.xpm"
41 #include "TraceControlPause.xpm"
42 #include "TraceControlStop.xpm"
43
44 #include <sys/types.h>
45 #include <unistd.h>
46 #include <stdlib.h>
47 #include <pty.h>
48 #include <utmp.h>
49 #include <sys/wait.h>
50 #include <sys/poll.h>
51 #include <errno.h>
52 #include <fcntl.h>
53 #include <sched.h>
54
55 #define MAX_ARGS_LEN PATH_MAX * 10
56
57 GSList *g_control_list = NULL ;
58
59 /*! \file lttv/modules/gui/tracecontrol/tracecontrol.c
60 * \brief Graphic trace start/stop control interface.
61 *
62 * This plugin interacts with lttctl to start/stop tracing. It needs to take the
63 * root password to be able to interact with lttctl.
64 *
65 */
66
67 typedef struct _ControlData ControlData;
68
69 /*
70 * Prototypes
71 */
72 GtkWidget *guicontrol_get_widget(ControlData *tcd);
73 ControlData *gui_control(LttvPluginTab *ptab);
74 void gui_control_destructor(ControlData *tcd);
75 GtkWidget* h_guicontrol(LttvPlugin *plugin);
76 void control_destroy_walk(gpointer data, gpointer user_data);
77
78 /*
79 * Callback functions
80 */
81
82 static void arm_clicked (GtkButton *button, gpointer user_data);
83 static void disarm_clicked (GtkButton *button, gpointer user_data);
84 static void start_clicked (GtkButton *button, gpointer user_data);
85 static void pause_clicked (GtkButton *button, gpointer user_data);
86 static void unpause_clicked (GtkButton *button, gpointer user_data);
87 static void stop_clicked (GtkButton *button, gpointer user_data);
88
89
90 /**
91 * @struct _ControlData
92 *
93 * @brief Main structure of gui control
94 */
95 struct _ControlData {
96 Tab *tab; /**< current tab of module */
97
98 GtkWidget *window; /**< window */
99
100 GtkWidget *main_box; /**< main container */
101 GtkWidget *ltt_armall_button;
102 GtkWidget *ltt_disarmall_button;
103 GtkWidget *start_button;
104 GtkWidget *pause_button;
105 GtkWidget *unpause_button;
106 GtkWidget *stop_button;
107 GtkWidget *username_label;
108 GtkWidget *username_entry;
109 GtkWidget *password_label;
110 GtkWidget *password_entry;
111 GtkWidget *channel_dir_label;
112 GtkWidget *channel_dir_entry;
113 GtkWidget *trace_dir_label;
114 GtkWidget *trace_dir_entry;
115 GtkWidget *trace_name_label;
116 GtkWidget *trace_name_entry;
117 GtkWidget *trace_mode_label;
118 GtkWidget *trace_mode_combo;
119 GtkWidget *start_daemon_label;
120 GtkWidget *start_daemon_check;
121 GtkWidget *append_label;
122 GtkWidget *append_check;
123 GtkWidget *optional_label;
124 GtkWidget *subbuf_size_label;
125 GtkWidget *subbuf_size_entry;
126 GtkWidget *subbuf_num_label;
127 GtkWidget *subbuf_num_entry;
128 GtkWidget *lttd_threads_label;
129 GtkWidget *lttd_threads_entry;
130 GtkWidget *lttctl_path_label;
131 GtkWidget *lttctl_path_entry;
132 GtkWidget *lttd_path_label;
133 GtkWidget *lttd_path_entry;
134 GtkWidget *ltt_armall_path_label;
135 GtkWidget *ltt_armall_path_entry;
136 GtkWidget *ltt_disarmall_path_label;
137 GtkWidget *ltt_disarmall_path_entry;
138 };
139
140 /**
141 * @fn GtkWidget* guicontrol_get_widget(ControlData*)
142 *
143 * This function returns the current main widget
144 * used by this module
145 * @param tcd the module struct
146 * @return The main widget
147 */
148 GtkWidget*
149 guicontrol_get_widget(ControlData *tcd)
150 {
151 return tcd->window;
152 }
153
154 /**
155 * @fn ControlData* gui_control(Tab*)
156 *
157 * Constructor is used to create ControlData data structure.
158 * @param tab The tab structure used by the widget
159 * @return The Filter viewer data created.
160 */
161 ControlData*
162 gui_control(LttvPluginTab *ptab)
163 {
164 Tab *tab = ptab->tab;
165 g_debug("filter::gui_control()");
166
167 ControlData* tcd = g_new(ControlData,1);
168
169 tcd->tab = tab;
170
171 tcd->window = gtk_window_new(GTK_WINDOW_TOPLEVEL);
172 gtk_window_set_title(GTK_WINDOW(tcd->window), "LTTng Trace Control");
173 /*
174 * Initiating GtkTable layout
175 * starts with 2 rows and 5 columns and
176 * expands when expressions added
177 */
178 tcd->main_box = gtk_table_new(14,7,FALSE);
179 gtk_table_set_row_spacings(GTK_TABLE(tcd->main_box),5);
180 gtk_table_set_col_spacings(GTK_TABLE(tcd->main_box),5);
181
182 gtk_container_add(GTK_CONTAINER(tcd->window), GTK_WIDGET(tcd->main_box));
183
184 GList *focus_chain = NULL;
185
186 /*
187 * start/pause/stop buttons
188 */
189
190 GdkPixbuf *pixbuf;
191 GtkWidget *image;
192 pixbuf = gdk_pixbuf_new_from_xpm_data((const char **)TraceControlStart_xpm);
193 image = gtk_image_new_from_pixbuf(pixbuf);
194 tcd->ltt_armall_button = gtk_button_new_with_label("Arm LTTng kernel probes");
195 //2.6 gtk_button_set_image(GTK_BUTTON(tcd->ltt_armall_button), image);
196 g_object_set(G_OBJECT(tcd->ltt_armall_button), "image", image, NULL);
197 gtk_button_set_alignment(GTK_BUTTON(tcd->ltt_armall_button), 0.0, 0.0);
198 gtk_widget_show (tcd->ltt_armall_button);
199 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->ltt_armall_button,6,7,0,1,GTK_FILL,GTK_FILL,2,2);
200
201 pixbuf = gdk_pixbuf_new_from_xpm_data((const char **)TraceControlStop_xpm);
202 image = gtk_image_new_from_pixbuf(pixbuf);
203 tcd->ltt_disarmall_button = gtk_button_new_with_label("Disarm LTTng kernel probes");
204 //2.6 gtk_button_set_image(GTK_BUTTON(tcd->ltt_disarmall_button), image);
205 g_object_set(G_OBJECT(tcd->ltt_disarmall_button), "image", image, NULL);
206 gtk_button_set_alignment(GTK_BUTTON(tcd->ltt_disarmall_button), 0.0, 0.0);
207 gtk_widget_show (tcd->ltt_disarmall_button);
208 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->ltt_disarmall_button,6,7,1,2,GTK_FILL,GTK_FILL,2,2);
209
210 pixbuf = gdk_pixbuf_new_from_xpm_data((const char **)TraceControlStart_xpm);
211 image = gtk_image_new_from_pixbuf(pixbuf);
212 tcd->start_button = gtk_button_new_with_label("start");
213 //2.6 gtk_button_set_image(GTK_BUTTON(tcd->start_button), image);
214 g_object_set(G_OBJECT(tcd->start_button), "image", image, NULL);
215 gtk_button_set_alignment(GTK_BUTTON(tcd->start_button), 0.0, 0.0);
216 gtk_widget_show (tcd->start_button);
217 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->start_button,6,7,2,3,GTK_FILL,GTK_FILL,2,2);
218
219 pixbuf = gdk_pixbuf_new_from_xpm_data((const char **)TraceControlPause_xpm);
220 image = gtk_image_new_from_pixbuf(pixbuf);
221 tcd->pause_button = gtk_button_new_with_label("pause");
222 //2.6 gtk_button_set_image(GTK_BUTTON(tcd->pause_button), image);
223 g_object_set(G_OBJECT(tcd->pause_button), "image", image, NULL);
224 gtk_button_set_alignment(GTK_BUTTON(tcd->pause_button), 0.0, 0.0);
225 gtk_widget_show (tcd->pause_button);
226 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->pause_button,6,7,3,4,GTK_FILL,GTK_FILL,2,2);
227
228 pixbuf = gdk_pixbuf_new_from_xpm_data((const char **)TraceControlPause_xpm);
229 image = gtk_image_new_from_pixbuf(pixbuf);
230 tcd->unpause_button = gtk_button_new_with_label("unpause");
231 //2.6 gtk_button_set_image(GTK_BUTTON(tcd->unpause_button), image);
232 g_object_set(G_OBJECT(tcd->unpause_button), "image", image, NULL);
233 gtk_button_set_alignment(GTK_BUTTON(tcd->unpause_button), 0.0, 0.0);
234 gtk_widget_show (tcd->unpause_button);
235 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->unpause_button,6,7,4,5,GTK_FILL,GTK_FILL,2,2);
236
237 pixbuf = gdk_pixbuf_new_from_xpm_data((const char **)TraceControlStop_xpm);
238 image = gtk_image_new_from_pixbuf(pixbuf);
239 tcd->stop_button = gtk_button_new_with_label("stop");
240 //2.6 gtk_button_set_image(GTK_BUTTON(tcd->stop_button), image);
241 g_object_set(G_OBJECT(tcd->stop_button), "image", image, NULL);
242 gtk_button_set_alignment(GTK_BUTTON(tcd->stop_button), 0.0, 0.0);
243 gtk_widget_show (tcd->stop_button);
244 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->stop_button,6,7,5,6,GTK_FILL,GTK_FILL,2,2);
245
246 /*
247 * First half of the filter window
248 * - textual entry of filter expression
249 * - processing button
250 */
251 tcd->username_label = gtk_label_new("Username:");
252 gtk_widget_show (tcd->username_label);
253 tcd->username_entry = gtk_entry_new();
254 gtk_entry_set_text(GTK_ENTRY(tcd->username_entry),"root");
255 gtk_widget_show (tcd->username_entry);
256 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->username_label,0,2,0,1,GTK_FILL,GTK_FILL,2,2);
257 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->username_entry,2,6,0,1,GTK_FILL|GTK_EXPAND|GTK_SHRINK,GTK_FILL,0,0);
258
259
260
261 tcd->password_label = gtk_label_new("Password:");
262 gtk_widget_show (tcd->password_label);
263 tcd->password_entry = gtk_entry_new();
264 gtk_entry_set_visibility(GTK_ENTRY(tcd->password_entry), FALSE);
265 gtk_widget_show (tcd->password_entry);
266 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->password_label,0,2,1,2,GTK_FILL,GTK_FILL,2,2);
267 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->password_entry,2,6,1,2,GTK_FILL|GTK_EXPAND|GTK_SHRINK,GTK_FILL,0,0);
268
269
270 tcd->channel_dir_label = gtk_label_new("Channel directory:");
271 gtk_widget_show (tcd->channel_dir_label);
272 tcd->channel_dir_entry = gtk_entry_new();
273 gtk_entry_set_text(GTK_ENTRY(tcd->channel_dir_entry),"/mnt/debugfs/ltt");
274 gtk_widget_show (tcd->channel_dir_entry);
275 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->channel_dir_label,0,2,2,3,GTK_FILL,GTK_FILL,2,2);
276 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->channel_dir_entry,2,6,2,3,GTK_FILL|GTK_EXPAND|GTK_SHRINK,GTK_FILL,0,0);
277
278 tcd->trace_dir_label = gtk_label_new("Trace directory:");
279 gtk_widget_show (tcd->trace_dir_label);
280 tcd->trace_dir_entry = gtk_entry_new();
281 gtk_entry_set_text(GTK_ENTRY(tcd->trace_dir_entry),"/tmp/trace1");
282 gtk_widget_show (tcd->trace_dir_entry);
283 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->trace_dir_label,0,2,3,4,GTK_FILL,GTK_FILL,2,2);
284 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->trace_dir_entry,2,6,3,4,GTK_FILL|GTK_EXPAND|GTK_SHRINK,GTK_FILL,0,0);
285
286 tcd->trace_name_label = gtk_label_new("Trace name:");
287 gtk_widget_show (tcd->trace_name_label);
288 tcd->trace_name_entry = gtk_entry_new();
289 gtk_entry_set_text(GTK_ENTRY(tcd->trace_name_entry),"trace");
290 gtk_widget_show (tcd->trace_name_entry);
291 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->trace_name_label,0,2,4,5,GTK_FILL,GTK_FILL,2,2);
292 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->trace_name_entry,2,6,4,5,GTK_FILL|GTK_EXPAND|GTK_SHRINK,GTK_FILL,0,0);
293
294 tcd->trace_mode_label = gtk_label_new("Trace mode ");
295 gtk_widget_show (tcd->trace_mode_label);
296 tcd->trace_mode_combo = gtk_combo_box_new_text();
297 gtk_combo_box_append_text(GTK_COMBO_BOX(tcd->trace_mode_combo),
298 "normal");
299 gtk_combo_box_append_text(GTK_COMBO_BOX(tcd->trace_mode_combo),
300 "flight recorder");
301 gtk_combo_box_set_active(GTK_COMBO_BOX(tcd->trace_mode_combo), 0);
302 gtk_widget_show (tcd->trace_mode_combo);
303 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->trace_mode_label,0,2,5,6,GTK_FILL,GTK_FILL,2,2);
304 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->trace_mode_combo,2,6,5,6,GTK_FILL|GTK_EXPAND|GTK_SHRINK,GTK_FILL,0,0);
305
306 tcd->start_daemon_label = gtk_label_new("Start daemon ");
307 gtk_widget_show (tcd->start_daemon_label);
308 tcd->start_daemon_check = gtk_check_button_new();
309 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(tcd->start_daemon_check), TRUE);
310 gtk_widget_show (tcd->start_daemon_check);
311 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->start_daemon_label,0,2,6,7,GTK_FILL,GTK_FILL,2,2);
312 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->start_daemon_check,2,6,6,7,GTK_FILL,GTK_FILL,0,0);
313
314 tcd->append_label = gtk_label_new("Append to trace ");
315 gtk_widget_show (tcd->append_label);
316 tcd->append_check = gtk_check_button_new();
317 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(tcd->append_check), FALSE);
318 gtk_widget_show (tcd->append_check);
319 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->append_label,0,2,7,8,GTK_FILL,GTK_FILL,2,2);
320 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->append_check,2,6,7,8,GTK_FILL,GTK_FILL,0,0);
321
322
323 tcd->optional_label = gtk_label_new("Optional fields ");
324 gtk_widget_show (tcd->optional_label);
325 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->optional_label,0,6,8,9,GTK_FILL,GTK_FILL,2,2);
326
327 tcd->subbuf_size_label = gtk_label_new("Subbuffer size:");
328 gtk_widget_show (tcd->subbuf_size_label);
329 tcd->subbuf_size_entry = gtk_entry_new();
330 gtk_widget_show (tcd->subbuf_size_entry);
331 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->subbuf_size_label,0,2,9,10,GTK_FILL,GTK_FILL,2,2);
332 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->subbuf_size_entry,2,6,9,10,GTK_FILL|GTK_EXPAND|GTK_SHRINK,GTK_FILL,0,0);
333
334 tcd->subbuf_num_label = gtk_label_new("Number of subbuffers:");
335 gtk_widget_show (tcd->subbuf_num_label);
336 tcd->subbuf_num_entry = gtk_entry_new();
337 gtk_widget_show (tcd->subbuf_num_entry);
338 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->subbuf_num_label,0,2,10,11,GTK_FILL,GTK_FILL,2,2);
339 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->subbuf_num_entry,2,6,10,11,GTK_FILL|GTK_EXPAND|GTK_SHRINK,GTK_FILL,0,0);
340
341 tcd->lttd_threads_label = gtk_label_new("Number of lttd threads:");
342 gtk_widget_show (tcd->lttd_threads_label);
343 tcd->lttd_threads_entry = gtk_entry_new();
344 gtk_entry_set_text(GTK_ENTRY(tcd->lttd_threads_entry), "1");
345 gtk_widget_show (tcd->lttd_threads_entry);
346 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->lttd_threads_label,0,2,11,12,GTK_FILL,GTK_FILL,2,2);
347 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->lttd_threads_entry,2,6,11,12,GTK_FILL|GTK_EXPAND|GTK_SHRINK,GTK_FILL,0,0);
348
349 tcd->lttctl_path_label = gtk_label_new("path to lttctl:");
350 gtk_widget_show (tcd->lttctl_path_label);
351 tcd->lttctl_path_entry = gtk_entry_new();
352 gtk_entry_set_text(GTK_ENTRY(tcd->lttctl_path_entry),PACKAGE_BIN_DIR "/lttctl");
353 gtk_widget_show (tcd->lttctl_path_entry);
354 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->lttctl_path_label,0,2,12,13,GTK_FILL,GTK_FILL,2,2);
355 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->lttctl_path_entry,2,6,12,13,GTK_FILL|GTK_EXPAND|GTK_SHRINK,GTK_FILL,0,0);
356
357
358 tcd->lttd_path_label = gtk_label_new("path to lttd:");
359 gtk_widget_show (tcd->lttd_path_label);
360 tcd->lttd_path_entry = gtk_entry_new();
361 gtk_entry_set_text(GTK_ENTRY(tcd->lttd_path_entry),PACKAGE_BIN_DIR "/lttd");
362 gtk_widget_show (tcd->lttd_path_entry);
363 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->lttd_path_label,0,2,13,14,GTK_FILL,GTK_FILL,2,2);
364 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->lttd_path_entry,2,6,13,14,GTK_FILL|GTK_EXPAND|GTK_SHRINK,GTK_FILL,0,0);
365
366 tcd->ltt_armall_path_label = gtk_label_new("path to ltt_armall:");
367 gtk_widget_show (tcd->ltt_armall_path_label);
368 tcd->ltt_armall_path_entry = gtk_entry_new();
369 gtk_entry_set_text(GTK_ENTRY(tcd->ltt_armall_path_entry),PACKAGE_BIN_DIR "/ltt-armall");
370 gtk_widget_show (tcd->ltt_armall_path_entry);
371 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->ltt_armall_path_label,0,2,14,15,GTK_FILL,GTK_FILL,2,2);
372 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->ltt_armall_path_entry,2,6,14,15,GTK_FILL|GTK_EXPAND|GTK_SHRINK,GTK_FILL,0,0);
373
374 tcd->ltt_disarmall_path_label = gtk_label_new("path to ltt_disarmall:");
375 gtk_widget_show (tcd->ltt_disarmall_path_label);
376 tcd->ltt_disarmall_path_entry = gtk_entry_new();
377 gtk_entry_set_text(GTK_ENTRY(tcd->ltt_disarmall_path_entry),PACKAGE_BIN_DIR "/ltt-disarmall");
378 gtk_widget_show (tcd->ltt_disarmall_path_entry);
379 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->ltt_disarmall_path_label,0,2,15,16,GTK_FILL,GTK_FILL,2,2);
380 gtk_table_attach( GTK_TABLE(tcd->main_box),tcd->ltt_disarmall_path_entry,2,6,15,16,GTK_FILL|GTK_EXPAND|GTK_SHRINK,GTK_FILL,0,0);
381
382 focus_chain = g_list_append (focus_chain, tcd->username_entry);
383 focus_chain = g_list_append (focus_chain, tcd->password_entry);
384 focus_chain = g_list_append (focus_chain, tcd->ltt_armall_path_entry);
385 focus_chain = g_list_append (focus_chain, tcd->ltt_disarmall_path_entry);
386 focus_chain = g_list_append (focus_chain, tcd->start_button);
387 focus_chain = g_list_append (focus_chain, tcd->pause_button);
388 focus_chain = g_list_append (focus_chain, tcd->unpause_button);
389 focus_chain = g_list_append (focus_chain, tcd->stop_button);
390 focus_chain = g_list_append (focus_chain, tcd->channel_dir_entry);
391 focus_chain = g_list_append (focus_chain, tcd->trace_dir_entry);
392 focus_chain = g_list_append (focus_chain, tcd->trace_name_entry);
393 focus_chain = g_list_append (focus_chain, tcd->trace_mode_combo);
394 focus_chain = g_list_append (focus_chain, tcd->start_daemon_check);
395 focus_chain = g_list_append (focus_chain, tcd->append_check);
396 focus_chain = g_list_append (focus_chain, tcd->subbuf_size_entry);
397 focus_chain = g_list_append (focus_chain, tcd->subbuf_num_entry);
398 focus_chain = g_list_append (focus_chain, tcd->lttd_threads_entry);
399 focus_chain = g_list_append (focus_chain, tcd->lttctl_path_entry);
400 focus_chain = g_list_append (focus_chain, tcd->lttd_path_entry);
401
402 gtk_container_set_focus_chain(GTK_CONTAINER(tcd->main_box), focus_chain);
403
404 g_list_free(focus_chain);
405
406 g_signal_connect(G_OBJECT(tcd->start_button), "clicked",
407 (GCallback)start_clicked, tcd);
408 g_signal_connect(G_OBJECT(tcd->pause_button), "clicked",
409 (GCallback)pause_clicked, tcd);
410 g_signal_connect(G_OBJECT(tcd->unpause_button), "clicked",
411 (GCallback)unpause_clicked, tcd);
412 g_signal_connect(G_OBJECT(tcd->stop_button), "clicked",
413 (GCallback)stop_clicked, tcd);
414 g_signal_connect(G_OBJECT(tcd->ltt_armall_button), "clicked",
415 (GCallback)arm_clicked, tcd);
416 g_signal_connect(G_OBJECT(tcd->ltt_disarmall_button), "clicked",
417 (GCallback)disarm_clicked, tcd);
418
419 /*
420 * show main container
421 */
422 gtk_widget_show(tcd->main_box);
423 gtk_widget_show(tcd->window);
424
425
426 g_object_set_data_full(
427 G_OBJECT(guicontrol_get_widget(tcd)),
428 "control_viewer_data",
429 tcd,
430 (GDestroyNotify)gui_control_destructor);
431
432 g_control_list = g_slist_append(
433 g_control_list,
434 tcd);
435
436 return tcd;
437 }
438
439
440 /**
441 * @fn void gui_control_destructor(ControlData*)
442 *
443 * Destructor for the filter gui module
444 * @param tcd The module structure
445 */
446 void
447 gui_control_destructor(ControlData *tcd)
448 {
449 /* May already been done by GTK window closing */
450 if(GTK_IS_WIDGET(guicontrol_get_widget(tcd))){
451 g_info("widget still exists");
452 }
453 // if(tab != NULL) {
454 // lttvwindow_unregister_traceset_notify(tcd->tab,
455 // filter_traceset_changed,
456 // filter_viewer_data);
457 // }
458 lttvwindowtraces_background_notify_remove(tcd);
459
460 g_control_list = g_slist_remove(g_control_list, tcd);
461
462 g_free(tcd);
463 }
464
465 static int execute_command(const gchar *command, const gchar *username,
466 const gchar *password, const gchar *lttd_path)
467 {
468 pid_t pid;
469 int fdpty;
470 pid = forkpty(&fdpty, NULL, NULL, NULL);
471 int retval = 0;
472
473 if(pid > 0) {
474 /* parent */
475 gchar buf[256];
476 int status;
477 ssize_t count;
478 /* discuss with su */
479 struct timeval timeout;
480 timeout.tv_sec = 1;
481 timeout.tv_usec = 0;
482
483 struct pollfd pollfd;
484 int num_rdy;
485 int num_hup = 0;
486 enum read_state { GET_LINE, GET_SEMI, GET_SPACE } read_state = GET_LINE;
487
488 retval = fcntl(fdpty, F_SETFL, O_WRONLY);
489 if(retval == -1) {
490 perror("Error in fcntl");
491 goto wait_child;
492 }
493
494 /* Read the output from the child terminal before the prompt. If no data in
495 * 200 ms, we stop reading to give the password */
496 g_info("Reading from child console...");
497 while(1) {
498 pollfd.fd = fdpty;
499 pollfd.events = POLLIN|POLLPRI|POLLERR|POLLHUP|POLLNVAL;
500
501 num_rdy = poll(&pollfd, 1, -1);
502 if(num_rdy == -1) {
503 perror("Poll error");
504 goto wait_child;
505 }
506
507 /* Timeout : Stop waiting for chars */
508 if(num_rdy == 0) goto wait_child;
509
510 /* Check for fatal errors */
511 if(pollfd.revents & POLLERR) {
512 g_warning("Error returned in polling fd\n");
513 num_hup++;
514 }
515 if(pollfd.revents & POLLNVAL) {
516 g_warning("Polling fd tells it is not open");
517 num_hup++;
518 }
519
520 if(pollfd.revents & POLLHUP) {
521
522 g_info("Polling FD : hung up.");
523 num_hup++;
524
525 }
526
527 if(pollfd.revents & (POLLIN | POLLPRI)) {
528 int count;
529 count = read (fdpty, buf, 256);
530 if(count > 0) {
531 unsigned int i;
532 buf[count] = '\0';
533 g_printf("%s", buf);
534 for(i=0; i<count; i++) {
535 switch(read_state) {
536 case GET_LINE:
537 if(buf[i] == '\n') {
538 read_state = GET_SEMI;
539 g_debug("Tracecontrol input line skip\n");
540 }
541 break;
542 case GET_SEMI:
543 if(buf[i] == ':') {
544 g_debug("Tracecontrol input : marker found\n");
545 read_state = GET_SPACE;
546 }
547 break;
548 case GET_SPACE:
549 if(buf[i] == ' ') {
550 g_debug("Tracecontrol input space marker found\n");
551 goto write_password;
552 }
553 break;
554 }
555 }
556 } else if(count == -1) {
557 perror("Error in read");
558 goto wait_child;
559 }
560
561 }
562
563 if(num_hup > 0) {
564 g_warning("Child hung up without returning a full reply");
565 goto wait_child;
566 }
567 }
568 write_password:
569 fsync(fdpty);
570 pollfd.fd = fdpty;
571 pollfd.events = POLLOUT|POLLERR|POLLHUP|POLLNVAL;
572
573 num_rdy = poll(&pollfd, 1, -1);
574 if(num_rdy == -1) {
575 perror("Poll error");
576 goto wait_child;
577 }
578
579 /* Write the password */
580 g_info("Got su prompt, now writing password...");
581 int ret;
582 sleep(1);
583 ret = write(fdpty, password, strlen(password));
584 if(ret < 0) perror("Error in write");
585 ret = write(fdpty, "\n", 1);
586 if(ret < 0) perror("Error in write");
587 fsync(fdpty);
588 /* Take the output from the terminal and show it on the real console */
589 g_info("Getting data from child terminal...");
590 while(1) {
591 int num_hup = 0;
592 pollfd.fd = fdpty;
593 pollfd.events = POLLIN|POLLPRI|POLLERR|POLLHUP|POLLNVAL;
594
595 num_rdy = poll(&pollfd, 1, -1);
596 if(num_rdy == -1) {
597 perror("Poll error");
598 goto wait_child;
599 }
600 if(num_rdy == 0) break;
601
602 if(pollfd.revents & (POLLERR|POLLNVAL)) {
603 g_warning("Error returned in polling fd\n");
604 num_hup++;
605 }
606
607 if(pollfd.revents & (POLLIN|POLLPRI) ) {
608 count = read (fdpty, buf, 256);
609 if(count > 0) {
610 buf[count] = '\0';
611 printf("%s", buf);
612 } else if(count == -1) {
613 perror("Error in read");
614 goto wait_child;
615 }
616 }
617
618 if(pollfd.revents & POLLHUP) {
619 g_info("Polling FD : hung up.");
620 num_hup++;
621 }
622
623 if(num_hup > 0) goto wait_child;
624 }
625 wait_child:
626 g_info("Waiting for child exit...");
627
628 ret = waitpid(pid, &status, 0);
629
630 if(ret == -1) {
631 g_warning("An error occured in wait : %s",
632 strerror(errno));
633 } else {
634 if(WIFEXITED(status))
635 if(WEXITSTATUS(status) != 0) {
636 retval = WEXITSTATUS(status);
637 g_warning("An error occured in the su command : %s",
638 strerror(retval));
639 }
640 }
641
642 g_info("Child exited.");
643
644 } else if(pid == 0) {
645 /* Setup environment variables */
646 if(strcmp(lttd_path, "") != 0)
647 setenv("LTT_DAEMON", lttd_path, 1);
648
649 /* One comment line (must be only one) */
650 g_printf("Executing (as %s) : %s\n", username, command);
651
652 execlp("su", "su", "-p", "-c", command, username, NULL);
653 exit(-1); /* not supposed to happen! */
654
655 //gint ret = execvp();
656
657 } else {
658 /* error */
659 g_warning("Error happened when forking for su");
660 }
661
662 return retval;
663 }
664
665
666 /* Callbacks */
667
668 void start_clicked (GtkButton *button, gpointer user_data)
669 {
670 ControlData *tcd = (ControlData*)user_data;
671
672 const gchar *username = gtk_entry_get_text(GTK_ENTRY(tcd->username_entry));
673 const gchar *password = gtk_entry_get_text(GTK_ENTRY(tcd->password_entry));
674 const gchar *channel_dir =
675 gtk_entry_get_text(GTK_ENTRY(tcd->channel_dir_entry));
676 const gchar *trace_dir = gtk_entry_get_text(GTK_ENTRY(tcd->trace_dir_entry));
677 const gchar *trace_name =
678 gtk_entry_get_text(GTK_ENTRY(tcd->trace_name_entry));
679
680 const gchar *trace_mode_sel;
681 GtkTreeIter iter;
682
683 gtk_combo_box_get_active_iter(GTK_COMBO_BOX(tcd->trace_mode_combo), &iter);
684 gtk_tree_model_get(
685 gtk_combo_box_get_model(GTK_COMBO_BOX(tcd->trace_mode_combo)),
686 &iter, 0, &trace_mode_sel, -1);
687 //const gchar *trace_mode_sel =
688 //2.6+ gtk_combo_box_get_active_text(GTK_COMBO_BOX(tcd->trace_mode_combo));
689 const gchar *trace_mode;
690 if(strcmp(trace_mode_sel, "normal") == 0)
691 trace_mode = "normal";
692 else
693 trace_mode = "flight";
694
695 gboolean start_daemon =
696 gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(tcd->start_daemon_check));
697
698 gboolean append =
699 gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(tcd->append_check));
700
701 const gchar *subbuf_size =
702 gtk_entry_get_text(GTK_ENTRY(tcd->subbuf_size_entry));
703 const gchar *subbuf_num =
704 gtk_entry_get_text(GTK_ENTRY(tcd->subbuf_num_entry));
705 const gchar *threads_num =
706 gtk_entry_get_text(GTK_ENTRY(tcd->lttd_threads_entry));
707 const gchar *lttctl_path =
708 gtk_entry_get_text(GTK_ENTRY(tcd->lttctl_path_entry));
709 const gchar *lttd_path = gtk_entry_get_text(GTK_ENTRY(tcd->lttd_path_entry));
710
711 /* Setup arguments to su */
712 /* child */
713 gchar args[MAX_ARGS_LEN];
714 gint args_left = MAX_ARGS_LEN - 1; /* for \0 */
715
716 args[0] = '\0';
717
718 /* Command */
719 strncat(args, "exec", args_left);
720 args_left = MAX_ARGS_LEN - strlen(args) - 1;
721
722 /* space */
723 strncat(args, " ", args_left);
724 args_left = MAX_ARGS_LEN - strlen(args) - 1;
725
726 if(strcmp(lttctl_path, "") == 0)
727 strncat(args, "lttctl", args_left);
728 else
729 strncat(args, lttctl_path, args_left);
730 args_left = MAX_ARGS_LEN - strlen(args) - 1;
731
732 /* space */
733 strncat(args, " ", args_left);
734 args_left = MAX_ARGS_LEN - strlen(args) - 1;
735
736 /* Start daemon ? */
737 if(start_daemon) {
738 strncat(args, "-C", args_left);
739 args_left = MAX_ARGS_LEN - strlen(args) - 1;
740 } else {
741 /* Simply create the channel and then start tracing */
742 //strncat(args, "-b", args_left);
743 //args_left = MAX_ARGS_LEN - strlen(args) - 1;
744 }
745
746 /* space */
747 strncat(args, " ", args_left);
748 args_left = MAX_ARGS_LEN - strlen(args) - 1;
749
750 /* channel dir */
751 strncat(args, "--channel_root ", args_left);
752 args_left = MAX_ARGS_LEN - strlen(args) - 1;
753 strncat(args, channel_dir, args_left);
754 args_left = MAX_ARGS_LEN - strlen(args) - 1;
755
756 /* space */
757 strncat(args, " ", args_left);
758 args_left = MAX_ARGS_LEN - strlen(args) - 1;
759
760 /* trace dir */
761 strncat(args, "-w ", args_left);
762 args_left = MAX_ARGS_LEN - strlen(args) - 1;
763 strncat(args, trace_dir, args_left);
764 args_left = MAX_ARGS_LEN - strlen(args) - 1;
765
766 /* space */
767 strncat(args, " ", args_left);
768 args_left = MAX_ARGS_LEN - strlen(args) - 1;
769
770 if(strcmp(trace_mode, "flight") == 0) {
771 strncat(args, "-o channel.all.overwrite=1", args_left);
772 args_left = MAX_ARGS_LEN - strlen(args) - 1;
773 } else {
774 strncat(args, "-o channel.all.overwrite=0", args_left);
775 args_left = MAX_ARGS_LEN - strlen(args) - 1;
776 }
777
778 /* Append to trace ? */
779 if(append) {
780 /* space */
781 strncat(args, " ", args_left);
782 args_left = MAX_ARGS_LEN - strlen(args) - 1;
783 strncat(args, "-a", args_left);
784 args_left = MAX_ARGS_LEN - strlen(args) - 1;
785 }
786
787 /* optional arguments */
788 /* subbuffer size */
789 if(strcmp(subbuf_size, "") != 0) {
790 /* space */
791 strncat(args, " ", args_left);
792 args_left = MAX_ARGS_LEN - strlen(args) - 1;
793
794 strncat(args, "-o channel.all.bufsize=", args_left);
795 args_left = MAX_ARGS_LEN - strlen(args) - 1;
796 strncat(args, subbuf_size, args_left);
797 args_left = MAX_ARGS_LEN - strlen(args) - 1;
798 }
799
800 /* number of subbuffers */
801 if(strcmp(subbuf_num, "") != 0) {
802 /* space */
803 strncat(args, " ", args_left);
804 args_left = MAX_ARGS_LEN - strlen(args) - 1;
805
806 strncat(args, "-o channel.all.bufnum=", args_left);
807 args_left = MAX_ARGS_LEN - strlen(args) - 1;
808 strncat(args, subbuf_num, args_left);
809 args_left = MAX_ARGS_LEN - strlen(args) - 1;
810 }
811
812 /* number of lttd threads */
813 if(strcmp(threads_num, "") != 0) {
814 /* space */
815 strncat(args, " ", args_left);
816 args_left = MAX_ARGS_LEN - strlen(args) - 1;
817
818 strncat(args, "-n ", args_left);
819 args_left = MAX_ARGS_LEN - strlen(args) - 1;
820 strncat(args, threads_num, args_left);
821 args_left = MAX_ARGS_LEN - strlen(args) - 1;
822 }
823
824 /* space */
825 strncat(args, " ", args_left);
826 args_left = MAX_ARGS_LEN - strlen(args) - 1;
827
828 /* name */
829 strncat(args, trace_name, args_left);
830 args_left = MAX_ARGS_LEN - strlen(args) - 1;
831
832 int retval = execute_command(args, username, password, lttd_path);
833
834 if(retval) {
835 gchar msg[256];
836 guint msg_left = 256;
837
838 strcpy(msg, "A problem occured when executing the su command : ");
839 msg_left = 256 - strlen(msg) - 1;
840 strncat(msg, strerror(retval), msg_left);
841 GtkWidget *dialogue =
842 gtk_message_dialog_new(
843 GTK_WINDOW(gtk_widget_get_toplevel(GTK_WIDGET(button))),
844 GTK_DIALOG_MODAL|GTK_DIALOG_DESTROY_WITH_PARENT,
845 GTK_MESSAGE_ERROR,
846 GTK_BUTTONS_OK,
847 "%s", msg);
848 gtk_dialog_run(GTK_DIALOG(dialogue));
849 gtk_widget_destroy(dialogue);
850 }
851
852 }
853
854
855 void pause_clicked (GtkButton *button, gpointer user_data)
856 {
857 ControlData *tcd = (ControlData*)user_data;
858
859 const gchar *username = gtk_entry_get_text(GTK_ENTRY(tcd->username_entry));
860 const gchar *password = gtk_entry_get_text(GTK_ENTRY(tcd->password_entry));
861 const gchar *trace_name =
862 gtk_entry_get_text(GTK_ENTRY(tcd->trace_name_entry));
863 const gchar *lttd_path = "";
864
865 const gchar *lttctl_path =
866 gtk_entry_get_text(GTK_ENTRY(tcd->lttctl_path_entry));
867
868 /* Setup arguments to su */
869 /* child */
870 gchar args[MAX_ARGS_LEN];
871 gint args_left = MAX_ARGS_LEN - 1; /* for \0 */
872
873 args[0] = '\0';
874
875 /* Command */
876 strncat(args, "exec", args_left);
877 args_left = MAX_ARGS_LEN - strlen(args) - 1;
878
879 /* space */
880 strncat(args, " ", args_left);
881 args_left = MAX_ARGS_LEN - strlen(args) - 1;
882
883 if(strcmp(lttctl_path, "") == 0)
884 strncat(args, "lttctl", args_left);
885 else
886 strncat(args, lttctl_path, args_left);
887 args_left = MAX_ARGS_LEN - strlen(args) - 1;
888
889 /* space */
890 strncat(args, " ", args_left);
891 args_left = MAX_ARGS_LEN - strlen(args) - 1;
892
893 /* Simply pause tracing */
894 strncat(args, "-p", args_left);
895 args_left = MAX_ARGS_LEN - strlen(args) - 1;
896
897 /* space */
898 strncat(args, " ", args_left);
899 args_left = MAX_ARGS_LEN - strlen(args) - 1;
900
901 /* name */
902 strncat(args, trace_name, args_left);
903 args_left = MAX_ARGS_LEN - strlen(args) - 1;
904
905 int retval = execute_command(args, username, password, lttd_path);
906 if(retval) {
907 gchar msg[256];
908 guint msg_left = 256;
909
910 strcpy(msg, "A problem occured when executing the su command : ");
911 msg_left = 256 - strlen(msg) - 1;
912 strncat(msg, strerror(retval), msg_left);
913 GtkWidget *dialogue =
914 gtk_message_dialog_new(
915 GTK_WINDOW(gtk_widget_get_toplevel(GTK_WIDGET(button))),
916 GTK_DIALOG_MODAL|GTK_DIALOG_DESTROY_WITH_PARENT,
917 GTK_MESSAGE_ERROR,
918 GTK_BUTTONS_OK,
919 "%s", msg);
920 gtk_dialog_run(GTK_DIALOG(dialogue));
921 gtk_widget_destroy(dialogue);
922 }
923
924 }
925
926 void unpause_clicked (GtkButton *button, gpointer user_data)
927 {
928 ControlData *tcd = (ControlData*)user_data;
929
930 const gchar *username = gtk_entry_get_text(GTK_ENTRY(tcd->username_entry));
931 const gchar *password = gtk_entry_get_text(GTK_ENTRY(tcd->password_entry));
932 const gchar *trace_name =
933 gtk_entry_get_text(GTK_ENTRY(tcd->trace_name_entry));
934 const gchar *lttd_path = "";
935
936 const gchar *lttctl_path =
937 gtk_entry_get_text(GTK_ENTRY(tcd->lttctl_path_entry));
938
939 /* Setup arguments to su */
940 /* child */
941 gchar args[MAX_ARGS_LEN];
942 gint args_left = MAX_ARGS_LEN - 1; /* for \0 */
943
944 args[0] = '\0';
945
946 /* Command */
947 strncat(args, "exec", args_left);
948 args_left = MAX_ARGS_LEN - strlen(args) - 1;
949
950 /* space */
951 strncat(args, " ", args_left);
952 args_left = MAX_ARGS_LEN - strlen(args) - 1;
953
954 if(strcmp(lttctl_path, "") == 0)
955 strncat(args, "lttctl", args_left);
956 else
957 strncat(args, lttctl_path, args_left);
958 args_left = MAX_ARGS_LEN - strlen(args) - 1;
959
960 /* space */
961 strncat(args, " ", args_left);
962 args_left = MAX_ARGS_LEN - strlen(args) - 1;
963
964 /* Simply unpause tracing */
965 strncat(args, "-s", args_left);
966 args_left = MAX_ARGS_LEN - strlen(args) - 1;
967
968 /* space */
969 strncat(args, " ", args_left);
970 args_left = MAX_ARGS_LEN - strlen(args) - 1;
971
972 /* name */
973 strncat(args, trace_name, args_left);
974 args_left = MAX_ARGS_LEN - strlen(args) - 1;
975
976 int retval = execute_command(args, username, password, lttd_path);
977 if(retval) {
978 gchar msg[256];
979 guint msg_left = 256;
980
981 strcpy(msg, "A problem occured when executing the su command : ");
982 msg_left = 256 - strlen(msg) - 1;
983 strncat(msg, strerror(retval), msg_left);
984 GtkWidget *dialogue =
985 gtk_message_dialog_new(
986 GTK_WINDOW(gtk_widget_get_toplevel(GTK_WIDGET(button))),
987 GTK_DIALOG_MODAL|GTK_DIALOG_DESTROY_WITH_PARENT,
988 GTK_MESSAGE_ERROR,
989 GTK_BUTTONS_OK,
990 "%s", msg);
991 gtk_dialog_run(GTK_DIALOG(dialogue));
992 gtk_widget_destroy(dialogue);
993 }
994
995 }
996
997 void stop_clicked (GtkButton *button, gpointer user_data)
998 {
999 ControlData *tcd = (ControlData*)user_data;
1000
1001 const gchar *username = gtk_entry_get_text(GTK_ENTRY(tcd->username_entry));
1002 const gchar *password = gtk_entry_get_text(GTK_ENTRY(tcd->password_entry));
1003 const gchar *trace_name =
1004 gtk_entry_get_text(GTK_ENTRY(tcd->trace_name_entry));
1005 const gchar *lttd_path = "";
1006 const gchar *trace_mode;
1007 const gchar *trace_mode_sel;
1008 GtkTreeIter iter;
1009
1010 gtk_combo_box_get_active_iter(GTK_COMBO_BOX(tcd->trace_mode_combo), &iter);
1011 gtk_tree_model_get(
1012 gtk_combo_box_get_model(GTK_COMBO_BOX(tcd->trace_mode_combo)),
1013 &iter, 0, &trace_mode_sel, -1);
1014 if(strcmp(trace_mode_sel, "normal") == 0)
1015 trace_mode = "normal";
1016 else
1017 trace_mode = "flight";
1018
1019 const gchar *lttctl_path =
1020 gtk_entry_get_text(GTK_ENTRY(tcd->lttctl_path_entry));
1021 const gchar *trace_dir = gtk_entry_get_text(GTK_ENTRY(tcd->trace_dir_entry));
1022 GSList * trace_list = NULL;
1023
1024 trace_list = g_slist_append(trace_list, (gpointer) trace_dir);
1025
1026 /* Setup arguments to su */
1027 /* child */
1028 gchar args[MAX_ARGS_LEN];
1029 gint args_left = MAX_ARGS_LEN - 1; /* for \0 */
1030
1031 args[0] = '\0';
1032
1033 /* Command */
1034 strncat(args, "exec", args_left);
1035 args_left = MAX_ARGS_LEN - strlen(args) - 1;
1036
1037 /* space */
1038 strncat(args, " ", args_left);
1039 args_left = MAX_ARGS_LEN - strlen(args) - 1;
1040
1041 if(strcmp(lttctl_path, "") == 0)
1042 strncat(args, "lttctl", args_left);
1043 else
1044 strncat(args, lttctl_path, args_left);
1045 args_left = MAX_ARGS_LEN - strlen(args) - 1;
1046
1047 /* space */
1048 strncat(args, " ", args_left);
1049 args_left = MAX_ARGS_LEN - strlen(args) - 1;
1050
1051 /* Simply stop tracing and destroy channel */
1052 strncat(args, "-D", args_left);
1053 args_left = MAX_ARGS_LEN - strlen(args) - 1;
1054
1055 if(strcmp(trace_mode, "flight") == 0) {
1056 /* space */
1057 strncat(args, " ", args_left);
1058 args_left = MAX_ARGS_LEN - strlen(args) - 1;
1059
1060 /* trace dir */
1061 strncat(args, "-w ", args_left);
1062 args_left = MAX_ARGS_LEN - strlen(args) - 1;
1063 strncat(args, trace_dir, args_left);
1064 args_left = MAX_ARGS_LEN - strlen(args) - 1;
1065 }
1066
1067 /* space */
1068 strncat(args, " ", args_left);
1069 args_left = MAX_ARGS_LEN - strlen(args) - 1;
1070
1071 /* name */
1072 strncat(args, trace_name, args_left);
1073 args_left = MAX_ARGS_LEN - strlen(args) - 1;
1074
1075 int retval = execute_command(args, username, password, lttd_path);
1076 if(retval) {
1077 gchar msg[256];
1078 guint msg_left = 256;
1079
1080 strcpy(msg, "A problem occured when executing the su command : ");
1081 msg_left = 256 - strlen(msg) - 1;
1082 strncat(msg, strerror(retval), msg_left);
1083 GtkWidget *dialogue =
1084 gtk_message_dialog_new(
1085 GTK_WINDOW(gtk_widget_get_toplevel(GTK_WIDGET(button))),
1086 GTK_DIALOG_MODAL|GTK_DIALOG_DESTROY_WITH_PARENT,
1087 GTK_MESSAGE_ERROR,
1088 GTK_BUTTONS_OK,
1089 "%s", msg);
1090 gtk_dialog_run(GTK_DIALOG(dialogue));
1091 gtk_widget_destroy(dialogue);
1092 return;
1093 }
1094
1095
1096 /* Ask to the user if he wants to open the trace in a new window */
1097 GtkWidget *dialogue;
1098 GtkWidget *label;
1099 gint id;
1100
1101 dialogue = gtk_dialog_new_with_buttons("Open trace ?",
1102 GTK_WINDOW(gtk_widget_get_toplevel(GTK_WIDGET(button))),
1103 GTK_DIALOG_MODAL | GTK_DIALOG_DESTROY_WITH_PARENT,
1104 GTK_STOCK_YES,GTK_RESPONSE_ACCEPT,
1105 GTK_STOCK_NO,GTK_RESPONSE_REJECT,
1106 NULL);
1107 label = gtk_label_new("Do you want to open the trace in LTTV ?");
1108 gtk_widget_show(label);
1109
1110 gtk_container_add(GTK_CONTAINER(GTK_DIALOG(dialogue)->vbox),
1111 label);
1112
1113 id = gtk_dialog_run(GTK_DIALOG(dialogue));
1114
1115 switch(id){
1116 case GTK_RESPONSE_ACCEPT:
1117 {
1118 /* TODO ybrosseau: 2011-04-20: Add support for live trace */
1119 create_main_window_with_trace_list(trace_list, FALSE);
1120 }
1121 break;
1122 case GTK_RESPONSE_REJECT:
1123 default:
1124 break;
1125 }
1126 gtk_widget_destroy(dialogue);
1127 g_slist_free(trace_list);
1128 }
1129
1130 void arm_clicked (GtkButton *button, gpointer user_data)
1131 {
1132 ControlData *tcd = (ControlData*)user_data;
1133
1134 const gchar *username = gtk_entry_get_text(GTK_ENTRY(tcd->username_entry));
1135 const gchar *password = gtk_entry_get_text(GTK_ENTRY(tcd->password_entry));
1136 const gchar *ltt_armall_path =
1137 gtk_entry_get_text(GTK_ENTRY(tcd->ltt_armall_path_entry));
1138
1139 /* Setup arguments to su */
1140 /* child */
1141 gchar args[MAX_ARGS_LEN];
1142 gint args_left = MAX_ARGS_LEN - 1; /* for \0 */
1143
1144 args[0] = '\0';
1145
1146 /* Command */
1147 strncat(args, "exec", args_left);
1148 args_left = MAX_ARGS_LEN - strlen(args) - 1;
1149
1150 /* space */
1151 strncat(args, " ", args_left);
1152 args_left = MAX_ARGS_LEN - strlen(args) - 1;
1153
1154 if(strcmp(ltt_armall_path, "") == 0)
1155 strncat(args, "ltt-armall", args_left);
1156 else
1157 strncat(args, ltt_armall_path, args_left);
1158 args_left = MAX_ARGS_LEN - strlen(args) - 1;
1159
1160 int retval = execute_command(args, username, password, "");
1161 if(retval) {
1162 gchar msg[256];
1163 guint msg_left = 256;
1164
1165 strcpy(msg, "A problem occured when executing the su command : ");
1166 msg_left = 256 - strlen(msg) - 1;
1167 strncat(msg, strerror(retval), msg_left);
1168 GtkWidget *dialogue =
1169 gtk_message_dialog_new(
1170 GTK_WINDOW(gtk_widget_get_toplevel(GTK_WIDGET(button))),
1171 GTK_DIALOG_MODAL|GTK_DIALOG_DESTROY_WITH_PARENT,
1172 GTK_MESSAGE_ERROR,
1173 GTK_BUTTONS_OK,
1174 "%s", msg);
1175 gtk_dialog_run(GTK_DIALOG(dialogue));
1176 gtk_widget_destroy(dialogue);
1177 }
1178
1179 }
1180
1181 void disarm_clicked (GtkButton *button, gpointer user_data)
1182 {
1183 ControlData *tcd = (ControlData*)user_data;
1184
1185 const gchar *username = gtk_entry_get_text(GTK_ENTRY(tcd->username_entry));
1186 const gchar *password = gtk_entry_get_text(GTK_ENTRY(tcd->password_entry));
1187 const gchar *ltt_disarmall_path =
1188 gtk_entry_get_text(GTK_ENTRY(tcd->ltt_disarmall_path_entry));
1189
1190 /* Setup arguments to su */
1191 /* child */
1192 gchar args[MAX_ARGS_LEN];
1193 gint args_left = MAX_ARGS_LEN - 1; /* for \0 */
1194
1195 args[0] = '\0';
1196
1197 /* Command */
1198 strncat(args, "exec", args_left);
1199 args_left = MAX_ARGS_LEN - strlen(args) - 1;
1200
1201 /* space */
1202 strncat(args, " ", args_left);
1203 args_left = MAX_ARGS_LEN - strlen(args) - 1;
1204
1205 if(strcmp(ltt_disarmall_path, "") == 0)
1206 strncat(args, "ltt-disarmall", args_left);
1207 else
1208 strncat(args, ltt_disarmall_path, args_left);
1209 args_left = MAX_ARGS_LEN - strlen(args) - 1;
1210
1211 int retval = execute_command(args, username, password, "");
1212 if(retval) {
1213 gchar msg[256];
1214 guint msg_left = 256;
1215
1216 strcpy(msg, "A problem occured when executing the su command : ");
1217 msg_left = 256 - strlen(msg) - 1;
1218 strncat(msg, strerror(retval), msg_left);
1219 GtkWidget *dialogue =
1220 gtk_message_dialog_new(
1221 GTK_WINDOW(gtk_widget_get_toplevel(GTK_WIDGET(button))),
1222 GTK_DIALOG_MODAL|GTK_DIALOG_DESTROY_WITH_PARENT,
1223 GTK_MESSAGE_ERROR,
1224 GTK_BUTTONS_OK,
1225 "%s", msg);
1226 gtk_dialog_run(GTK_DIALOG(dialogue));
1227 gtk_widget_destroy(dialogue);
1228 }
1229
1230 }
1231
1232
1233 /**
1234 * @fn GtkWidget* h_guicontrol(Tab*)
1235 *
1236 * Control Module's constructor hook
1237 *
1238 * This constructor is given as a parameter to the menuitem and toolbar button
1239 * registration. It creates the list.
1240 * @param tab A pointer to the parent window.
1241 * @return The widget created.
1242 */
1243 GtkWidget *
1244 h_guicontrol(LttvPlugin *plugin)
1245 {
1246 LttvPluginTab *ptab = LTTV_PLUGIN_TAB(plugin);
1247 gui_control(ptab) ;
1248
1249 /* TODO ybrosseau 2011-02-04: We should probably return a widget here */
1250 return NULL;
1251 }
1252
1253 /**
1254 * @fn static void init()
1255 *
1256 * This function initializes the Filter Viewer functionnality through the
1257 * gtkTraceSet API.
1258 */
1259 static void init() {
1260
1261 lttvwindow_register_constructor("guicontrol",
1262 "/",
1263 "Insert Tracing Control Module",
1264 hTraceControlInsert_xpm,
1265 "Insert Tracing Control Module",
1266 h_guicontrol);
1267 }
1268
1269 /**
1270 * @fn void control_destroy_walk(gpointer,gpointer)
1271 *
1272 * Initiate the destruction of the current gui module
1273 * on the GTK Interface
1274 */
1275 void
1276 control_destroy_walk(gpointer data, gpointer user_data)
1277 {
1278 ControlData *tcd = (ControlData*)data;
1279
1280 g_debug("traceontrol.c : control_destroy_walk, %p", tcd);
1281
1282 /* May already have been done by GTK window closing */
1283 if(GTK_IS_WIDGET(guicontrol_get_widget(tcd)))
1284 gtk_widget_destroy(guicontrol_get_widget(tcd));
1285 }
1286
1287 /**
1288 * @fn static void destroy()
1289 * @brief plugin's destroy function
1290 *
1291 * This function releases the memory reserved by the module and unregisters
1292 * everything that has been registered in the gtkTraceSet API.
1293 */
1294 static void destroy() {
1295
1296 g_slist_foreach(g_control_list, control_destroy_walk, NULL );
1297
1298 lttvwindow_unregister_constructor(h_guicontrol);
1299
1300 }
1301
1302
1303 LTTV_MODULE("guitracecontrol", "Trace Control Window", \
1304 "Graphical module that let user control kernel tracing", \
1305 init, destroy, "lttvwindow")
1306
This page took 0.065149 seconds and 3 git commands to generate.