2 * smb_stat 2003 Ronnie Sahlberg
6 * Ethereal - Network traffic analyzer
7 * By Gerald Combs <gerald@ethereal.com>
8 * Copyright 1998 Gerald Combs
10 * This program is free software; you can redistribute it and/or
11 * modify it under the terms of the GNU General Public License
12 * as published by the Free Software Foundation; either version 2
13 * of the License, or (at your option) any later version.
15 * This program is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 * GNU General Public License for more details.
20 * You should have received a copy of the GNU General Public License
21 * along with this program; if not, write to the Free Software
22 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
29 #ifdef HAVE_SYS_TYPES_H
30 # include <sys/types.h>
37 #include <epan/packet_info.h>
38 #include <epan/epan.h>
39 #include <epan/value_string.h>
44 #include "../register.h"
45 #include "../timestats.h"
46 #include "compat_macros.h"
47 #include "../simple_dialog.h"
49 #include "dlg_utils.h"
51 #include "../globals.h"
52 #include "filter_dlg.h"
53 #include "service_response_time_table.h"
54 #include "gtkglobals.h"
57 /* used to keep track of the statistics for an entire program interface */
58 typedef struct _smbstat_t {
60 srt_stat_table smb_srt_table;
61 srt_stat_table trans2_srt_table;
62 srt_stat_table nt_trans_srt_table;
66 smbstat_set_title(smbstat_t *ss)
70 title = g_strdup_printf("SMB Service Response Time statistics: %s",
71 cf_get_display_name(&cfile));
72 gtk_window_set_title(GTK_WINDOW(ss->win), title);
77 smbstat_reset(void *pss)
79 smbstat_t *ss=(smbstat_t *)pss;
81 reset_srt_table_data(&ss->smb_srt_table);
82 reset_srt_table_data(&ss->trans2_srt_table);
83 reset_srt_table_data(&ss->nt_trans_srt_table);
84 smbstat_set_title(ss);
88 smbstat_packet(void *pss, packet_info *pinfo, epan_dissect_t *edt _U_, const void *psi)
90 smbstat_t *ss=(smbstat_t *)pss;
91 const smb_info_t *si=psi;
93 /* we are only interested in reply packets */
97 /* if we havnt seen the request, just ignore it */
102 add_srt_table_data(&ss->smb_srt_table, si->cmd, &si->sip->req_time, pinfo);
104 if(si->cmd==0xA0 && si->sip->extra_info_type == SMB_EI_NTI){
105 smb_nt_transact_info_t *sti=(smb_nt_transact_info_t *)si->sip->extra_info;
108 add_srt_table_data(&ss->nt_trans_srt_table, sti->subcmd, &si->sip->req_time, pinfo);
110 } else if(si->cmd==0x32 && si->sip->extra_info_type == SMB_EI_T2I){
111 smb_transact2_info_t *st2i=(smb_transact2_info_t *)si->sip->extra_info;
114 add_srt_table_data(&ss->trans2_srt_table, st2i->subcmd, &si->sip->req_time, pinfo);
124 smbstat_draw(void *pss)
126 smbstat_t *ss=(smbstat_t *)pss;
128 draw_srt_table_data(&ss->smb_srt_table);
129 draw_srt_table_data(&ss->trans2_srt_table);
130 draw_srt_table_data(&ss->nt_trans_srt_table);
134 void protect_thread_critical_region(void);
135 void unprotect_thread_critical_region(void);
137 win_destroy_cb(GtkWindow *win _U_, gpointer data)
139 smbstat_t *ss=(smbstat_t *)data;
141 protect_thread_critical_region();
142 remove_tap_listener(ss);
143 unprotect_thread_critical_region();
145 free_srt_table_data(&ss->smb_srt_table);
146 free_srt_table_data(&ss->trans2_srt_table);
147 free_srt_table_data(&ss->nt_trans_srt_table);
153 gtk_smbstat_init(const char *optarg)
156 const char *filter=NULL;
158 char filter_string[256];
159 GString *error_string;
165 if(!strncmp(optarg,"smb,srt,",8)){
171 ss=g_malloc(sizeof(smbstat_t));
173 ss->win=window_new(GTK_WINDOW_TOPLEVEL, "smb-stat");
174 gtk_window_set_default_size(GTK_WINDOW(ss->win), 550, 600);
175 smbstat_set_title(ss);
177 vbox=gtk_vbox_new(FALSE, 3);
178 gtk_container_add(GTK_CONTAINER(ss->win), vbox);
179 gtk_container_set_border_width(GTK_CONTAINER(vbox), 12);
181 label=gtk_label_new("SMB Service Response Time statistics");
182 gtk_box_pack_start(GTK_BOX(vbox), label, FALSE, FALSE, 0);
184 g_snprintf(filter_string,255,"Filter:%s",filter?filter:"");
185 label=gtk_label_new(filter_string);
186 gtk_box_pack_start(GTK_BOX(vbox), label, FALSE, FALSE, 0);
188 label=gtk_label_new("SMB Commands");
189 gtk_box_pack_start(GTK_BOX(vbox), label, FALSE, FALSE, 0);
191 /* We must display TOP LEVEL Widget before calling init_srt_table() */
192 gtk_widget_show_all(ss->win);
194 init_srt_table(&ss->smb_srt_table, 256, vbox, "smb.cmd");
196 init_srt_table_row(&ss->smb_srt_table, i, val_to_str(i, smb_cmd_vals, "Unknown(0x%02x)"));
200 label=gtk_label_new("Transaction2 Sub-Commands");
201 gtk_box_pack_start(GTK_BOX(vbox), label, FALSE, FALSE, 0);
202 init_srt_table(&ss->trans2_srt_table, 256, vbox, "smb.trans2.cmd");
204 init_srt_table_row(&ss->trans2_srt_table, i, val_to_str(i, trans2_cmd_vals, "Unknown(0x%02x)"));
208 label=gtk_label_new("NT Transaction Sub-Commands");
209 gtk_box_pack_start(GTK_BOX(vbox), label, FALSE, FALSE, 0);
210 init_srt_table(&ss->nt_trans_srt_table, 256, vbox, "smb.nt.function");
212 init_srt_table_row(&ss->nt_trans_srt_table, i, val_to_str(i, nt_cmd_vals, "Unknown(0x%02x)"));
216 error_string=register_tap_listener("smb", ss, filter, smbstat_reset, smbstat_packet, smbstat_draw);
218 simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK, error_string->str);
219 g_string_free(error_string, TRUE);
225 bbox = dlg_button_row_new(GTK_STOCK_CLOSE, NULL);
226 gtk_box_pack_end(GTK_BOX(vbox), bbox, FALSE, FALSE, 0);
228 close_bt = OBJECT_GET_DATA(bbox, GTK_STOCK_CLOSE);
229 window_set_cancel_button(ss->win, close_bt, window_cancel_button_cb);
231 SIGNAL_CONNECT(ss->win, "delete_event", window_delete_event_cb, NULL);
232 SIGNAL_CONNECT(ss->win, "destroy", win_destroy_cb, ss);
234 gtk_widget_show_all(ss->win);
235 window_present(ss->win);
237 cf_retap_packets(&cfile);
242 static GtkWidget *dlg=NULL;
243 static GtkWidget *filter_entry;
252 smbstat_start_button_clicked(GtkWidget *item _U_, gpointer data _U_)
257 str = g_string_new("smb,srt");
258 filter=gtk_entry_get_text(GTK_ENTRY(filter_entry));
260 g_string_sprintfa(str,",%s", filter);
262 gtk_smbstat_init(str->str);
263 g_string_free(str, TRUE);
267 gtk_smbstat_cb(GtkWidget *w _U_, gpointer d _U_)
270 GtkWidget *filter_box, *filter_bt;
271 GtkWidget *bbox, *start_button, *cancel_button;
273 static construct_args_t args = {
274 "Service Response Time Statistics Filter",
279 /* if the window is already open, bring it to front */
281 gdk_window_raise(dlg->window);
285 dlg=dlg_window_new("Ethereal: Compute SMB SRT statistics");
286 gtk_window_set_default_size(GTK_WINDOW(dlg), 300, -1);
288 dlg_box=gtk_vbox_new(FALSE, 10);
289 gtk_container_border_width(GTK_CONTAINER(dlg_box), 10);
290 gtk_container_add(GTK_CONTAINER(dlg), dlg_box);
291 gtk_widget_show(dlg_box);
294 filter_box=gtk_hbox_new(FALSE, 3);
297 filter_bt=BUTTON_NEW_FROM_STOCK(ETHEREAL_STOCK_DISPLAY_FILTER_ENTRY);
298 SIGNAL_CONNECT(filter_bt, "clicked", display_filter_construct_cb, &args);
299 gtk_box_pack_start(GTK_BOX(filter_box), filter_bt, FALSE, TRUE, 0);
300 gtk_widget_show(filter_bt);
303 filter_entry=gtk_entry_new();
304 SIGNAL_CONNECT(filter_entry, "changed", filter_te_syntax_check_cb, NULL);
306 /* filter prefs dialog */
307 OBJECT_SET_DATA(filter_bt, E_FILT_TE_PTR_KEY, filter_entry);
308 /* filter prefs dialog */
310 gtk_box_pack_start(GTK_BOX(filter_box), filter_entry, TRUE, TRUE, 0);
311 filter=gtk_entry_get_text(GTK_ENTRY(main_display_filter_widget));
313 gtk_entry_set_text(GTK_ENTRY(filter_entry), filter);
315 gtk_widget_show(filter_entry);
317 gtk_box_pack_start(GTK_BOX(dlg_box), filter_box, TRUE, TRUE, 0);
318 gtk_widget_show(filter_box);
321 bbox = dlg_button_row_new(ETHEREAL_STOCK_CREATE_STAT, GTK_STOCK_CANCEL, NULL);
322 gtk_box_pack_start(GTK_BOX(dlg_box), bbox, FALSE, FALSE, 0);
323 gtk_widget_show(bbox);
325 start_button = OBJECT_GET_DATA(bbox, ETHEREAL_STOCK_CREATE_STAT);
326 SIGNAL_CONNECT_OBJECT(start_button, "clicked",
327 smbstat_start_button_clicked, NULL);
329 cancel_button = OBJECT_GET_DATA(bbox, GTK_STOCK_CANCEL);
330 window_set_cancel_button(dlg, cancel_button, window_cancel_button_cb);
332 /* Catch the "activate" signal on the filter text entry, so that
333 if the user types Return there, we act as if the "Create Stat"
334 button had been selected, as happens if Return is typed if some
335 widget that *doesn't* handle the Return key has the input
337 dlg_set_activate(filter_entry, start_button);
339 gtk_widget_grab_default(start_button );
341 /* Give the initial focus to the "Filter" entry box. */
342 gtk_widget_grab_focus(filter_entry);
344 SIGNAL_CONNECT(dlg, "delete_event", window_delete_event_cb, NULL);
345 SIGNAL_CONNECT(dlg, "destroy", dlg_destroy_cb, NULL);
347 gtk_widget_show_all(dlg);
352 register_tap_listener_gtksmbstat(void)
354 register_tap_listener_cmd_arg("smb,srt", gtk_smbstat_init);
356 register_tap_menu_item("SMB...", REGISTER_TAP_GROUP_RESPONSE_TIME,
357 gtk_smbstat_cb, NULL, NULL, NULL);