Move the declaration of global variables involved with packet capture
[obnox/wireshark/wip.git] / gtk / file_dlg.c
1 /* file_dlg.c
2  * Dialog boxes for handling files
3  *
4  * $Id: file_dlg.c,v 1.5 1999/10/02 19:24:27 guy Exp $
5  *
6  * Ethereal - Network traffic analyzer
7  * By Gerald Combs <gerald@zing.org>
8  * Copyright 1998 Gerald Combs
9  *
10  * 
11  * This program is free software; you can redistribute it and/or
12  * modify it under the terms of the GNU General Public License
13  * as published by the Free Software Foundation; either version 2
14  * of the License, or (at your option) any later version.
15  * 
16  * This program is distributed in the hope that it will be useful,
17  * but WITHOUT ANY WARRANTY; without even the implied warranty of
18  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
19  * GNU General Public License for more details.
20  * 
21  * You should have received a copy of the GNU General Public License
22  * along with this program; if not, write to the Free Software
23  * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
24  */
25
26 #ifdef HAVE_CONFIG_H
27 #include "config.h"
28 #endif
29
30 #ifdef HAVE_UNISTD_H
31 #include <unistd.h>
32 #endif
33
34 #ifdef HAVE_DIRECT_H
35 #include <direct.h>
36 #endif
37
38 #include <string.h>
39
40 #ifndef __GLOBALS_H__
41 #include "globals.h"
42 #endif
43
44 #ifndef __KEYS_H__
45 #include "keys.h"
46 #endif
47
48 #ifndef __PREFS_DLG_H__
49 #include "prefs_dlg.h"
50 #endif
51
52 #ifndef __UTIL_H__
53 #include "util.h"
54 #endif
55
56 #ifndef __MENU_H__
57 #include "menu.h"
58 #endif
59
60 #ifdef HAVE_LIBPCAP
61 #include "capture.h"
62 #endif
63
64 static void file_open_ok_cb(GtkWidget *w, GtkFileSelection *fs);
65 static void file_save_ok_cb(GtkWidget *w, GtkFileSelection *fs);
66 static void file_save_as_ok_cb(GtkWidget *w, GtkFileSelection *fs);
67
68 /* Open a file */
69 void
70 file_open_cmd_cb(GtkWidget *w, gpointer data) {
71   GtkWidget *filter_hbox, *filter_bt, *filter_te;
72
73   if (last_open_dir)
74           chdir(last_open_dir);
75
76   file_sel = gtk_file_selection_new ("Ethereal: Open Capture File");
77   
78   /* Connect the ok_button to file_open_ok_cb function and pass along a
79      pointer to the file selection box widget */
80   gtk_signal_connect (GTK_OBJECT (GTK_FILE_SELECTION (file_sel)->ok_button),
81     "clicked", (GtkSignalFunc) file_open_ok_cb, file_sel );
82
83   gtk_object_set_data(GTK_OBJECT(GTK_FILE_SELECTION(file_sel)->ok_button),
84       E_DFILTER_TE_KEY, gtk_object_get_data(GTK_OBJECT(w), E_DFILTER_TE_KEY));
85
86   filter_hbox = gtk_hbox_new(FALSE, 1);
87   gtk_container_border_width(GTK_CONTAINER(filter_hbox), 0);
88   gtk_box_pack_start(GTK_BOX(GTK_FILE_SELECTION(file_sel)->action_area),
89     filter_hbox, FALSE, FALSE, 0);
90   gtk_widget_show(filter_hbox);
91
92   filter_bt = gtk_button_new_with_label("Filter:");
93   gtk_signal_connect(GTK_OBJECT(filter_bt), "clicked",
94     GTK_SIGNAL_FUNC(prefs_cb), (gpointer) E_PR_PG_FILTER);
95   gtk_box_pack_start(GTK_BOX(filter_hbox), filter_bt, FALSE, TRUE, 0);
96   gtk_widget_show(filter_bt);
97   
98   filter_te = gtk_entry_new();
99   gtk_object_set_data(GTK_OBJECT(filter_bt), E_FILT_TE_PTR_KEY, filter_te);
100   gtk_box_pack_start(GTK_BOX(filter_hbox), filter_te, TRUE, TRUE, 3);
101   gtk_widget_show(filter_te);
102
103   gtk_object_set_data(GTK_OBJECT(GTK_FILE_SELECTION(file_sel)->ok_button),
104     E_RFILTER_TE_KEY, filter_te);
105
106   /* Connect the cancel_button to destroy the widget */
107   gtk_signal_connect_object(GTK_OBJECT (GTK_FILE_SELECTION
108     (file_sel)->cancel_button), "clicked", (GtkSignalFunc)
109     gtk_widget_destroy, GTK_OBJECT (file_sel));
110
111 #ifdef HAVE_LIBPCAP
112   if ((sync_mode || fork_mode) && (cf.save_file != NULL))
113 #else
114   if (cf.save_file != NULL)
115 #endif
116     gtk_file_selection_set_filename(GTK_FILE_SELECTION(file_sel), cf.save_file);
117   else
118     gtk_file_selection_set_filename(GTK_FILE_SELECTION(file_sel), "");
119
120   gtk_widget_show(file_sel);
121 }
122
123 static void
124 file_open_ok_cb(GtkWidget *w, GtkFileSelection *fs) {
125   gchar     *cf_name, *rfilter, *s;
126   GtkWidget *filter_te;
127   dfilter   *rfcode = NULL;
128   int        err;
129
130   cf_name = g_strdup(gtk_file_selection_get_filename(GTK_FILE_SELECTION (fs)));
131   filter_te = gtk_object_get_data(GTK_OBJECT(w), E_RFILTER_TE_KEY);
132   rfilter = gtk_entry_get_text(GTK_ENTRY(filter_te));
133   if (rfilter[0] != '\0') {
134         rfcode = dfilter_new();
135         if (dfilter_compile(rfcode, rfilter) != 0) {
136                 simple_dialog(ESD_TYPE_WARN, NULL, dfilter_error_msg);
137                 dfilter_destroy(rfcode);
138                 return;
139         }
140   }
141
142   /* Try to open the capture file. */
143   if ((err = open_cap_file(cf_name, &cf)) != 0) {
144     /* We couldn't open it; don't dismiss the open dialog box,
145        just leave it around so that the user can, after they
146        dismiss the alert box popped up for the open error,
147        try again. */
148     if (rfcode != NULL)
149       dfilter_destroy(rfcode);
150     return;
151   }
152
153   /* Attach the new read filter to "cf" ("open_cap_file()" succeeded, so
154      it closed the previous capture file, and thus destroyed any
155      previous read filter attached to "cf"). */
156   cf.rfcode = rfcode;
157
158   /* We've crossed the Rubicon; get rid of the file selection box. */
159   gtk_widget_hide(GTK_WIDGET (fs));
160   gtk_widget_destroy(GTK_WIDGET (fs));
161
162   err = read_cap_file(&cf);
163   /* Save the directory name; we can write over cf_name. */
164   s = strrchr(cf_name, '/');
165   if (s && last_open_dir) {
166           *s = '\0';
167           if (strcmp(last_open_dir, cf_name) != 0) {
168                   g_free(last_open_dir);
169                   last_open_dir = g_strdup(cf_name);
170           }
171   }
172   else if (s) { /* ! last_open_dir */
173           *s = '\0';
174           last_open_dir = g_strdup(cf_name);
175   }
176   else {
177           last_open_dir = NULL;
178   }
179   set_menu_sensitivity("/File/Save", FALSE);
180   set_menu_sensitivity("/File/Save As...", TRUE);
181   g_free(cf_name);
182 }
183
184 /* Close a file */
185 void
186 file_close_cmd_cb(GtkWidget *widget, gpointer data) {
187   close_cap_file(&cf, info_bar, file_ctx);
188 }
189
190 void
191 file_save_cmd_cb(GtkWidget *w, gpointer data) {
192   file_sel = gtk_file_selection_new ("Ethereal: Save Capture File");
193  
194   /* Connect the ok_button to file_save_ok_cb function and pass along a
195      pointer to the file selection box widget */
196   gtk_signal_connect (GTK_OBJECT (GTK_FILE_SELECTION (file_sel)->ok_button),
197     "clicked", (GtkSignalFunc) file_save_ok_cb, file_sel );
198
199   /* Connect the cancel_button to destroy the widget */
200   gtk_signal_connect_object(GTK_OBJECT (GTK_FILE_SELECTION
201     (file_sel)->cancel_button), "clicked", (GtkSignalFunc)
202     gtk_widget_destroy, GTK_OBJECT (file_sel));
203
204   gtk_file_selection_set_filename(GTK_FILE_SELECTION(file_sel), "");
205
206   gtk_widget_show(file_sel);
207 }
208
209 void
210 file_save_as_cmd_cb(GtkWidget *w, gpointer data) {
211   file_sel = gtk_file_selection_new ("Ethereal: Save Capture File As");
212
213   /* Connect the ok_button to file_save_as_ok_cb function and pass along a
214      pointer to the file selection box widget */
215   gtk_signal_connect (GTK_OBJECT (GTK_FILE_SELECTION (file_sel)->ok_button),
216     "clicked", (GtkSignalFunc) file_save_as_ok_cb, file_sel );
217
218   /* Connect the cancel_button to destroy the widget */
219   gtk_signal_connect_object(GTK_OBJECT (GTK_FILE_SELECTION
220     (file_sel)->cancel_button), "clicked", (GtkSignalFunc)
221     gtk_widget_destroy, GTK_OBJECT (file_sel));
222
223   gtk_file_selection_set_filename(GTK_FILE_SELECTION(file_sel), "");
224   gtk_widget_show(file_sel);
225 }
226
227 static void
228 file_save_ok_cb(GtkWidget *w, GtkFileSelection *fs) {
229         gchar   *cf_name;
230         int     err;
231
232         cf_name = g_strdup(gtk_file_selection_get_filename(GTK_FILE_SELECTION(fs)));
233         gtk_widget_hide(GTK_WIDGET (fs));
234         gtk_widget_destroy(GTK_WIDGET (fs));
235
236         if (!file_mv(cf.save_file, cf_name))
237                 return;
238
239         g_free(cf.save_file);
240         cf.save_file = g_strdup(cf_name);
241         cf.user_saved = 1;
242         if ((err = open_cap_file(cf_name, &cf)) == 0) {
243                 err = read_cap_file(&cf);
244                 set_menu_sensitivity("/File/Save", FALSE);
245                 set_menu_sensitivity("/File/Save As...", TRUE);
246         }
247 }
248
249 static void
250 file_save_as_ok_cb(GtkWidget *w, GtkFileSelection *fs) {
251         gchar   *cf_name;
252         int     err;
253
254         cf_name = g_strdup(gtk_file_selection_get_filename(GTK_FILE_SELECTION(fs)));
255         gtk_widget_hide(GTK_WIDGET (fs));
256         gtk_widget_destroy(GTK_WIDGET (fs));
257         if (!file_cp(cf.filename, cf_name))
258                 return;
259         g_free(cf.filename);
260         cf.filename = g_strdup(cf_name);
261         cf.user_saved = 1;
262         if ((err = open_cap_file(cf.filename, &cf)) == 0) {
263                 err = read_cap_file(&cf);
264                 set_menu_sensitivity("/File/Save", FALSE);
265                 set_menu_sensitivity("/File/Save As...", TRUE);
266         }
267 }
268
269 /* Reload a file using the current read and display filters */
270 void
271 file_reload_cmd_cb(GtkWidget *w, gpointer data) {
272   /*GtkWidget *filter_te = gtk_object_get_data(GTK_OBJECT(w), E_DFILTER_TE_KEY);*/
273   GtkWidget *filter_te;
274
275   filter_te = gtk_object_get_data(GTK_OBJECT(w), E_DFILTER_TE_KEY);
276
277   if (cf.dfilter) g_free(cf.dfilter);
278   cf.dfilter = g_strdup(gtk_entry_get_text(GTK_ENTRY(filter_te)));
279   if (open_cap_file(cf.filename, &cf) == 0)
280     read_cap_file(&cf);
281   /* XXX - change the menu if the open fails? */
282 }
283