diff options
author | Guy Harris <guy@alum.mit.edu> | 2003-09-10 05:35:26 +0000 |
---|---|---|
committer | Guy Harris <guy@alum.mit.edu> | 2003-09-10 05:35:26 +0000 |
commit | 27ea7816ee9c4613a4272ee6ddadb65a02a8233b (patch) | |
tree | f4f2db48edccdb7e402fef88f3c4672bf5991283 | |
parent | df25d4167371367c9e8e19ccde6135250a174846 (diff) | |
download | wireshark-27ea7816ee9c4613a4272ee6ddadb65a02a8233b.tar.gz wireshark-27ea7816ee9c4613a4272ee6ddadb65a02a8233b.tar.bz2 wireshark-27ea7816ee9c4613a4272ee6ddadb65a02a8233b.zip |
Have "get_interface_list()" return a list of "if_info_t" structures
containing a pointer to an interface name and possibly a pointer to an
interface description (although that pointer might be null if no
description is available), rather than having the Windows version glue
together the name and description into a single string.
Supply for the Linux "any" device the same description that libpcap's
"pcap_findalldevs()" returns.
svn path=/trunk/; revision=8440
-rw-r--r-- | gtk/Makefile.am | 6 | ||||
-rw-r--r-- | gtk/Makefile.nmake | 14 | ||||
-rw-r--r-- | gtk/capture_combo_utils.c | 161 | ||||
-rw-r--r-- | gtk/capture_combo_utils.h | 31 | ||||
-rw-r--r-- | gtk/capture_dlg.c | 178 | ||||
-rw-r--r-- | gtk/capture_prefs.c | 53 | ||||
-rw-r--r-- | gtk/main.c | 6 | ||||
-rw-r--r-- | pcap-util.c | 151 | ||||
-rw-r--r-- | pcap-util.h | 12 | ||||
-rw-r--r-- | tethereal.c | 30 |
10 files changed, 376 insertions, 266 deletions
diff --git a/gtk/Makefile.am b/gtk/Makefile.am index bffaccc82f..2d85306bfd 100644 --- a/gtk/Makefile.am +++ b/gtk/Makefile.am @@ -1,7 +1,7 @@ # Makefile.am # Automake file for the GTK interface routines for Ethereal # -# $Id: Makefile.am,v 1.66 2003/09/02 22:47:58 guy Exp $ +# $Id: Makefile.am,v 1.67 2003/09/10 05:35:25 guy Exp $ # # Ethereal - Network traffic analyzer # By Gerald Combs <gerald@ethereal.com> @@ -54,6 +54,8 @@ ethereal-tap-register.c: $(ETHEREAL_TAP_SRC) $(top_srcdir)/make-tapreg-dotc if USE_GTK2 libui_a_SOURCES = \ + capture_combo_utils.c \ + capture_combo_utils.h \ capture_dlg.c \ capture_dlg.h \ capture_prefs.c \ @@ -134,6 +136,8 @@ libui_a_SOURCES = \ $(ETHEREAL_TAP_SRC) else libui_a_SOURCES = \ + capture_combo_utils.c \ + capture_combo_utils.h \ capture_dlg.c \ capture_dlg.h \ capture_prefs.c \ diff --git a/gtk/Makefile.nmake b/gtk/Makefile.nmake index 766b0e502b..28787f8081 100644 --- a/gtk/Makefile.nmake +++ b/gtk/Makefile.nmake @@ -1,7 +1,7 @@ ## Makefile for building ethereal.exe with Microsoft C and nmake ## Use: $(MAKE) /$(MAKEFLAGS) -f makefile.nmake # -# $Id: Makefile.nmake,v 1.51 2003/09/02 22:47:58 guy Exp $ +# $Id: Makefile.nmake,v 1.52 2003/09/10 05:35:25 guy Exp $ include ..\config.nmake @@ -44,9 +44,15 @@ ETHEREAL_TAP_OBJECTS = $(ETHEREAL_TAP_SRC:.c=.obj) # gtkclist.obj is not in here because it is gtk+-1.2 code, # while the DLL for GTK+ on windows is gtk+-1.3, and there's -# some functions that have disappeared in gtk+-1.3. I might -# get around to #ifdef'ing them out in our gtkclist.c. -OBJECTS=capture_dlg.obj \ +# some functions that have disappeared in gtk+-1.3 - and +# the only purpose our gtkclist.c serves is to be faster +# than versions of the CList code in some older GTK+ 1.2[.x] +# releases, but as of 1.2.8 the standard GTK+ should have +# the performance fix that's in our gtkclist.c, so there's no +# reason to use our gtkclist.c. +OBJECTS = \ + capture_combo_utils.obj \ + capture_dlg.obj \ capture_prefs.obj \ color_dlg.obj \ color_filters.obj \ diff --git a/gtk/capture_combo_utils.c b/gtk/capture_combo_utils.c new file mode 100644 index 0000000000..e0806aac24 --- /dev/null +++ b/gtk/capture_combo_utils.c @@ -0,0 +1,161 @@ +/* capture_combo_utils.c + * Utilities for combo box of interface names + * + * $Id: capture_combo_utils.c,v 1.1 2003/09/10 05:35:25 guy Exp $ + * + * Ethereal - Network traffic analyzer + * By Gerald Combs <gerald@ethereal.com> + * Copyright 1998 Gerald Combs + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + */ + +#ifdef HAVE_CONFIG_H +# include "config.h" +#endif + +#ifdef HAVE_LIBPCAP + +#include <string.h> +#include <gtk/gtk.h> + +#include <pcap.h> + +#include "prefs.h" +#include "pcap-util.h" +#include "capture_combo_utils.h" + +/* + * Find capture device description that matches interface name. + */ +static char * +capture_dev_descr_find(const gchar *if_name) +{ + char *p; + char *p2 = NULL; + char *descr = NULL; + int lp = 0; + int ct = 0; + + if (prefs.capture_devices_descr == NULL) { + /* There are no descriptions. */ + return NULL; + } + + if ((p = strstr(prefs.capture_devices_descr, if_name)) == NULL) { + /* There are, but there isn't one for this interface. */ + return NULL; + } + + while (*p != '\0') { + /* error: ran into next interface description */ + if (*p == ',') + return NULL; + /* found left parenthesis, start of description */ + else if (*p == '(') { + lp++; + /* skip over left parenthesis */ + p++; + /* save pointer to beginning of description */ + p2 = p; + continue; + } + else if (*p == ')') { + /* end of description */ + break; + } + else { + p++; + ct++; + } + } + + if ((lp == 1) && (ct > 0) && (p2 != NULL)) { + /* Allocate enough space to return the string, + which runs from p2 to p, plus a terminating + '\0'. */ + descr = g_malloc(p - p2 + 1); + memcpy(descr, p2, p - p2); + descr[p - p2] = '\0'; + return descr; + } + else + return NULL; +} + +GList * +build_capture_combo_list(GList *if_list, gboolean do_hide) +{ + GList *combo_list; + GList *if_entry; + if_info_t *if_info; + char *if_string; + gchar *descr; + + combo_list = NULL; + if (if_list != NULL) { + /* Scan through the list and build a list of strings to display. */ + for (if_entry = g_list_first(if_list); if_entry != NULL; + if_entry = g_list_next(if_entry)) { + if_info = if_entry->data; + + /* Is this interface hidden and, if so, should we include it + anyway? */ + if (prefs.capture_devices_hide == NULL || + strstr(prefs.capture_devices_hide, if_info->name) == NULL || + !do_hide) { + /* It's not hidden, or it is but we should include it in the list. */ + + /* Do we have a user-supplied description? */ + descr = capture_dev_descr_find(if_info->name); + if (descr != NULL) { + /* Yes, we have a user-supplied description; use it. */ + if_string = g_strdup_printf("%s: %s", descr, if_info->name); + g_free(descr); + } else { + /* No, we don't have a user-supplied description; did we get + one from the OS or libpcap? */ + if (if_info->description != NULL) { + /* Yes - use it. */ + if_string = g_strdup_printf("%s: %s", if_info->description, + if_info->name); + } else { + /* No. */ + if_string = g_strdup(if_info->name); + } + } + combo_list = g_list_append(combo_list, if_string); + } + } + } + return combo_list; +} + +static void +free_if_string(gpointer data, gpointer user_data _U_) +{ + g_free(data); +} + +void +free_capture_combo_list(GList *combo_list) +{ + if (combo_list != NULL) { + g_list_foreach(combo_list, free_if_string, NULL); + g_list_free(combo_list); + } +} + +#endif /* HAVE_LIBPCAP */ diff --git a/gtk/capture_combo_utils.h b/gtk/capture_combo_utils.h new file mode 100644 index 0000000000..87c4ba4fbb --- /dev/null +++ b/gtk/capture_combo_utils.h @@ -0,0 +1,31 @@ +/* capture_combo_utils.c + * Declarations of tilities for combo box of interface names + * + * $Id: capture_combo_utils.h,v 1.1 2003/09/10 05:35:25 guy Exp $ + * + * Ethereal - Network traffic analyzer + * By Gerald Combs <gerald@ethereal.com> + * Copyright 1998 Gerald Combs + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + */ + +#ifndef __CAPTURE_COMBO_UTILS_H__ +#define __CAPTURE_COMBO_UTILS_H__ + +GList *build_capture_combo_list(GList *if_list, gboolean do_hide); +void free_capture_combo_list(GList *combo_list); + +#endif diff --git a/gtk/capture_dlg.c b/gtk/capture_dlg.c index 1331b69b14..98d835c54c 100644 --- a/gtk/capture_dlg.c +++ b/gtk/capture_dlg.c @@ -1,7 +1,7 @@ /* capture_dlg.c * Routines for packet capture windows * - * $Id: capture_dlg.c,v 1.80 2003/09/08 21:44:42 guy Exp $ + * $Id: capture_dlg.c,v 1.81 2003/09/10 05:35:25 guy Exp $ * * Ethereal - Network traffic analyzer * By Gerald Combs <gerald@ethereal.com> @@ -43,6 +43,7 @@ #include "simple_dialog.h" #include "dlg_utils.h" #include "pcap-util.h" +#include "capture_combo_utils.h" #include "prefs.h" #include "ringbuffer.h" #include <epan/filesystem.h> @@ -104,15 +105,6 @@ capture_prep_close_cb(GtkWidget *close_bt, gpointer parent_w); static void capture_prep_destroy_cb(GtkWidget *win, gpointer user_data); -static GList * -capture_dev_descr_add(GList *if_list); - -static char * -capture_dev_descr_find(gchar *devs_descr, gchar *if_name); - -static GList * -capture_dev_hide(GList *if_list); - void capture_stop_cb(GtkWidget *w _U_, gpointer d _U_) { @@ -155,7 +147,7 @@ capture_prep_cb(GtkWidget *w _U_, gpointer d _U_) #endif GtkAdjustment *snap_adj, *ringbuffer_nbf_adj, *count_adj, *filesize_adj, *duration_adj, *ring_duration_adj; - GList *if_list; + GList *if_list, *combo_list; int err; char err_str[PCAP_ERRBUF_SIZE]; @@ -230,15 +222,9 @@ capture_prep_cb(GtkWidget *w _U_, gpointer d _U_) gtk_widget_show(if_lb); if_cb = gtk_combo_new(); - if (if_list != NULL) { - /* remove interface(s) from list if "hidden" */ - if (prefs.capture_devices_hide != NULL) - if_list = capture_dev_hide(if_list); - /* prepend interface descriptions to device name */ - if (prefs.capture_devices_descr != NULL) - if_list = capture_dev_descr_add(if_list); - gtk_combo_set_popdown_strings(GTK_COMBO(if_cb), if_list); - } + combo_list = build_capture_combo_list(if_list, TRUE); + gtk_combo_set_popdown_strings(GTK_COMBO(if_cb), combo_list); + free_capture_combo_list(combo_list); if (cfile.iface == NULL && prefs.capture_device != NULL) { /* No interface was specified on the command line or in a previous capture, but there is one specified in the preferences file; @@ -247,13 +233,14 @@ capture_prep_cb(GtkWidget *w _U_, gpointer d _U_) } if (cfile.iface != NULL) gtk_entry_set_text(GTK_ENTRY(GTK_COMBO(if_cb)->entry), cfile.iface); - else if (if_list != NULL) - gtk_entry_set_text(GTK_ENTRY(GTK_COMBO(if_cb)->entry), if_list->data); + else if (if_list != NULL) { + gtk_entry_set_text(GTK_ENTRY(GTK_COMBO(if_cb)->entry), + ((if_info_t *)(if_list->data))->name); + } + free_interface_list(if_list); gtk_box_pack_start(GTK_BOX(if_hb), if_cb, TRUE, TRUE, 6); gtk_widget_show(if_cb); - free_interface_list(if_list); - /* Capture length row */ snap_hb = gtk_hbox_new(FALSE, 3); gtk_container_add(GTK_CONTAINER(capture_vb), snap_hb); @@ -807,7 +794,7 @@ capture_prep_ok_cb(GtkWidget *ok_bt _U_, gpointer parent_w) { g_strdup(gtk_entry_get_text(GTK_ENTRY(GTK_COMBO(if_cb)->entry))); /* Remove interface description. Also, Windows combo entries have a description followed by the interface name. These two cases are - OK as long as they're in front (see capture_dev_descr_add()). */ + OK as long as they're in front. */ if_name = strrchr(if_text, ' '); if (if_name == NULL) { if_name = if_text; @@ -1075,145 +1062,4 @@ capture_prep_adjust_sensitivity(GtkWidget *tb _U_, gpointer parent_w) } -/* - * Prepend capture devices description to interface list. Remove OS (pcap) - * supplied description if present. - */ -static GList * -capture_dev_descr_add(GList *if_list) -{ - - GList *if_new_list = NULL; - char *osd; - char *tmp_descr; - gchar *tmp_devs_descr; - gchar *tmp_dev_name; - guint i; - guint nitems; - - /* Seems we need to be at list head for g_list_length()? */ - if_list = g_list_first(if_list); - nitems = g_list_length(if_list); - - /* Create new interface list with "(descr) if_name". */ - for (i=0; i < nitems; i++) { - tmp_dev_name = g_list_nth_data(if_list, i); - /* should never happen, but just in case */ - if (tmp_dev_name == NULL) { - if (if_new_list != NULL) - free_interface_list(if_new_list); - return if_list; - } - /* create copy since capture_dev_descr_find() inserts terminator */ - tmp_devs_descr = g_strdup(prefs.capture_devices_descr); - /* find matching description */ - tmp_descr = capture_dev_descr_find(tmp_devs_descr, tmp_dev_name); - /* prepend description */ - if (tmp_descr != NULL) { - /* remove OS (pcap) description */ - if ((osd = strrchr(tmp_dev_name, ' ')) != NULL) { - osd++; - if (osd != NULL) - tmp_dev_name = osd; - } - if_new_list = g_list_append(if_new_list, - g_strdup_printf("%s %s", tmp_descr, tmp_dev_name)); - } - /* no description for this interface, just copy name */ - else { - if_new_list = g_list_append(if_new_list, g_strdup(tmp_dev_name)); - } - g_free(tmp_devs_descr); - } - - free_interface_list(if_list); - /* return pointer to new interface list with descriptions */ - return if_new_list; -} - -/* - * Find capture device description that matches interface name. - */ -static char * -capture_dev_descr_find(gchar *devs_descr, gchar *if_name) -{ - char *p; - char *p2 = NULL; - char *descr = NULL; - int lp = 0; - int ct = 0; - - if (if_name == NULL) - return NULL; - - if ((p = strstr(devs_descr, if_name)) == NULL) - return NULL; - - while (p != NULL) { - /* error: ran into next interface description */ - if (*p == ',') - return NULL; - /* found left parenthesis, start of description */ - else if (*p == '(') { - lp++; - /* save pointer to beginning of description */ - p2 = p; - p++; - continue; - } - else if (*p == ')') { - /* end of description */ - break; - } - else { - p++; - ct++; - } - } - - if ((lp == 1) && (ct > 0) && (p2 != NULL)) { - /* set returned pointer to beginning of description */ - descr = p2; - /* insert terminator */ - *(p+1) = '\0'; - return descr; - } - else - return NULL; -} - -/* - * Remove "hidden" interface(s) from list. - */ -static GList * -capture_dev_hide(GList *if_list) -{ - GList *if_new_list = NULL; - gchar *tmp_dev_name; - guint i; - guint nitems; - - /* Seems we need to be at list head for g_list_length()? */ - if_list = g_list_first(if_list); - nitems = g_list_length(if_list); - - /* Create new list without "hidden" interfaces. */ - for (i=0; i < nitems; i++) { - tmp_dev_name = g_list_nth_data(if_list, i); - /* should never happen, but just in case */ - if (tmp_dev_name == NULL) { - if (if_new_list != NULL) - free_interface_list(if_new_list); - return if_list; - } - /* check if interface name is in "hidden" preferences string */ - if (strstr(prefs.capture_devices_hide, tmp_dev_name) == NULL) - if_new_list = g_list_append(if_new_list, g_strdup(tmp_dev_name)); - } - - free_interface_list(if_list); - /* return pointer to new interface list */ - return if_new_list; -} - #endif /* HAVE_LIBPCAP */ diff --git a/gtk/capture_prefs.c b/gtk/capture_prefs.c index 5c3c15f9f2..ac1730bf9c 100644 --- a/gtk/capture_prefs.c +++ b/gtk/capture_prefs.c @@ -1,7 +1,7 @@ /* capture_prefs.c * Dialog box for capture preferences * - * $Id: capture_prefs.c,v 1.20 2003/09/09 18:27:49 guy Exp $ + * $Id: capture_prefs.c,v 1.21 2003/09/10 05:35:26 guy Exp $ * * Ethereal - Network traffic analyzer * By Gerald Combs <gerald@ethereal.com> @@ -42,6 +42,7 @@ #include "dlg_utils.h" #include "simple_dialog.h" #include "pcap-util.h" +#include "capture_combo_utils.h" #include "main.h" #include "compat_macros.h" @@ -72,7 +73,7 @@ static void ifopts_edit_ifunsel_cb(GtkWidget *clist, gint row, gint column, GdkEventButton *event, gpointer data); static void ifopts_old_options_add(GtkCList *clist); static gboolean ifopts_old_options_chk(GtkCList *clist, gchar *ifname); -static void ifopts_new_options_add(GtkCList *clist, gchar *ifname); +static void ifopts_new_options_add(GtkCList *clist, if_info_t *if_info); static void ifopts_options_free(gchar *text[]); static void ifopts_if_clist_add(GtkCList *clist); static void ifopts_write_new_descr(void); @@ -84,7 +85,7 @@ capture_prefs_show(void) GtkWidget *main_tb, *main_vb; GtkWidget *if_cb, *if_lb, *promisc_cb, *sync_cb, *auto_scroll_cb; GtkWidget *ifopts_lb, *ifopts_bt; - GList *if_list; + GList *if_list, *combo_list; int err; char err_str[PCAP_ERRBUF_SIZE]; @@ -110,8 +111,10 @@ capture_prefs_show(void) * XXX - what if we can't get the list? */ if_list = get_interface_list(&err, err_str); - if (if_list != NULL) - gtk_combo_set_popdown_strings(GTK_COMBO(if_cb), if_list); + combo_list = build_capture_combo_list(if_list, FALSE); + free_interface_list(if_list); + gtk_combo_set_popdown_strings(GTK_COMBO(if_cb), combo_list); + free_capture_combo_list(combo_list); if (prefs.capture_device) gtk_entry_set_text(GTK_ENTRY(GTK_COMBO(if_cb)->entry), prefs.capture_device); @@ -119,8 +122,6 @@ capture_prefs_show(void) gtk_widget_show(if_cb); OBJECT_SET_DATA(main_vb, DEVICE_KEY, if_cb); - free_interface_list(if_list); - /* Interface options */ ifopts_lb = gtk_label_new("Interface options:"); gtk_table_attach_defaults(GTK_TABLE(main_tb), ifopts_lb, 0, 1, 1, 2); @@ -678,13 +679,13 @@ ifopts_old_options_chk(GtkCList *clist, gchar *ifname) * machine or disabled and no longer apply. */ static void -ifopts_new_options_add(GtkCList *clist, gchar *ifname) +ifopts_new_options_add(GtkCList *clist, if_info_t *if_info) { gchar *p; gchar *ifnm; gchar *desc; gchar *pr_descr; - gchar *text[3] = { '\0' }; + gchar *text[3] = { NULL, NULL, NULL }; /* add interface descriptions and "hidden" flag */ if (prefs.capture_devices_descr != NULL) { @@ -692,16 +693,16 @@ ifopts_new_options_add(GtkCList *clist, gchar *ifname) pr_descr = g_strdup(prefs.capture_devices_descr); /* if we find a description for this interface */ - if ((ifnm = strstr(pr_descr, ifname)) != NULL) { + if ((ifnm = strstr(pr_descr, if_info->name)) != NULL) { p = ifnm; while (*p != '\0') { /* found left parenthesis, start of description */ if (*p == '(') { /* set interface name text */ - text[0] = g_strdup(ifname); + text[0] = g_strdup(if_info->name); /* check if interface is "hidden" */ if (prefs.capture_devices_hide != NULL) { - if (strstr(prefs.capture_devices_hide, ifname) != NULL) + if (strstr(prefs.capture_devices_hide, if_info->name) != NULL) text[2] = g_strdup("1"); else text[2] = g_strdup("0"); @@ -746,12 +747,12 @@ ifopts_new_options_add(GtkCList *clist, gchar *ifname) /* if there's no description for this interface */ else { /* set interface name */ - text[0] = g_strdup(ifname); + text[0] = g_strdup(if_info->name); /* set empty description */ text[1] = g_strdup(""); /* check if interface is "hidden" */ if (prefs.capture_devices_hide != NULL) { - if (strstr(prefs.capture_devices_hide, ifname) != NULL) + if (strstr(prefs.capture_devices_hide, if_info->name) != NULL) text[2] = g_strdup("1"); else text[2] = g_strdup("0"); @@ -771,11 +772,11 @@ ifopts_new_options_add(GtkCList *clist, gchar *ifname) */ else if (prefs.capture_devices_hide != NULL) { /* set interface name */ - text[0] = g_strdup(ifname); + text[0] = g_strdup(if_info->name); /* set empty description */ text[1] = g_strdup(""); /* check if interface is "hidden" */ - if (strstr(prefs.capture_devices_hide, ifname) != NULL) + if (strstr(prefs.capture_devices_hide, if_info->name) != NULL) text[2] = g_strdup("1"); else text[2] = g_strdup("0"); @@ -789,7 +790,7 @@ ifopts_new_options_add(GtkCList *clist, gchar *ifname) */ else { /* set interface name */ - text[0] = g_strdup(ifname); + text[0] = g_strdup(if_info->name); /* set empty description */ text[1] = g_strdup(""); /* interface is not "hidden" */ @@ -820,12 +821,13 @@ ifopts_options_free(gchar *text[]) static void ifopts_if_clist_add(GtkCList *clist) { - GList *if_list; + GList *if_list; int err; - char err_str[PCAP_ERRBUF_SIZE]; - gchar *text[1]; - guint i; - guint nitems; + char err_str[PCAP_ERRBUF_SIZE]; + if_info_t *if_info; + gchar *text[1]; + guint i; + guint nitems; if_list = get_interface_list(&err, err_str); if (if_list == NULL && err == CANT_GET_INTERFACE_LIST) { @@ -840,13 +842,14 @@ ifopts_if_clist_add(GtkCList *clist) /* add interface name text to CList */ for (i=0; i < nitems; i++) { - text[0] = g_list_nth_data(if_list, i); + if_info = g_list_nth_data(if_list, i); /* should never happen, but just in case */ - if (text[0] == NULL) + if (if_info == NULL) continue; + text[0] = if_info->name; gtk_clist_append(GTK_CLIST(clist), text); /* fill "new" options CList with previously saved values */ - ifopts_new_options_add(GTK_CLIST(new_clist), text[0]); + ifopts_new_options_add(GTK_CLIST(new_clist), if_info); } free_interface_list(if_list); diff --git a/gtk/main.c b/gtk/main.c index 9bfa5f1079..c7344c8ec4 100644 --- a/gtk/main.c +++ b/gtk/main.c @@ -1,6 +1,6 @@ /* main.c * - * $Id: main.c,v 1.309 2003/09/03 23:32:40 guy Exp $ + * $Id: main.c,v 1.310 2003/09/10 05:35:26 guy Exp $ * * Ethereal - Network traffic analyzer * By Gerald Combs <gerald@ethereal.com> @@ -1511,6 +1511,7 @@ main(int argc, char *argv[]) gboolean start_capture = FALSE; gchar *save_file = NULL; GList *if_list; + if_info_t *if_info; gchar err_str[PCAP_ERRBUF_SIZE]; gboolean stats_known; struct pcap_stat stats; @@ -2074,7 +2075,8 @@ main(int argc, char *argv[]) } exit(2); } - cfile.iface = g_strdup(if_list->data); /* first interface */ + if_info = if_list->data; /* first interface */ + cfile.iface = g_strdup(if_info->name); free_interface_list(if_list); } } diff --git a/pcap-util.c b/pcap-util.c index 318dfb3976..f059086efc 100644 --- a/pcap-util.c +++ b/pcap-util.c @@ -1,7 +1,7 @@ /* pcap-util.c * Utility routines for packet capture * - * $Id: pcap-util.c,v 1.15 2003/09/08 21:44:41 guy Exp $ + * $Id: pcap-util.c,v 1.16 2003/09/10 05:35:23 guy Exp $ * * Ethereal - Network traffic analyzer * By Gerald Combs <gerald@ethereal.com> @@ -213,6 +213,20 @@ search_for_if_cb(gpointer data, gpointer user_data); static void free_if_cb(gpointer data, gpointer user_data); +static if_info_t * +if_info_new(char *name, char *description) +{ + if_info_t *if_info; + + if_info = g_malloc(sizeof (if_info_t)); + if_info->name = g_strdup(name); + if (description == NULL) + if_info->description = NULL; + else + if_info->description = g_strdup(description); + return if_info; +} + #ifndef WIN32 GList * get_interface_list(int *err, char *err_str) @@ -227,6 +241,7 @@ get_interface_list(int *err, char *err_str) pcap_t *pch; int len, lastlen; char *buf; + if_info_t *if_info; if (sock < 0) { sprintf(err_str, "Error opening socket: %s", @@ -328,12 +343,12 @@ get_interface_list(int *err, char *err_str) * don't want a loopback interface to be the default capture * device unless there are no non-loopback devices. */ + if_info = if_info_new(ifr->ifr_name, NULL); if ((ifrflags.ifr_flags & IFF_LOOPBACK) || strncmp(ifr->ifr_name, "lo", 2) == 0) - il = g_list_insert(il, g_strdup(ifr->ifr_name), -1); + il = g_list_insert(il, if_info, -1); else { - il = g_list_insert(il, g_strdup(ifr->ifr_name), - nonloopback_pos); + il = g_list_insert(il, if_info, nonloopback_pos); /* * Insert the next non-loopback interface after this * one. @@ -364,7 +379,9 @@ get_interface_list(int *err, char *err_str) /* * It worked; we can use the "any" device. */ - il = g_list_insert(il, g_strdup("any"), -1); + if_info = if_info_new("any", + "Pseudo-device that captures on all interfaces"); + il = g_list_insert(il, if_info, -1); pcap_close(pch); } #endif @@ -393,8 +410,9 @@ static void search_for_if_cb(gpointer data, gpointer user_data) { struct search_user_data *search_user_data = user_data; + if_info_t *if_info = data; - if (strcmp((char *)data, search_user_data->name) == 0) + if (strcmp(if_info->name, search_user_data->name) == 0) search_user_data->found = TRUE; } #else /* Windows */ @@ -403,7 +421,8 @@ get_interface_list(int *err, char *err_str) { GList *il = NULL; wchar_t *names; char *win95names; - char newname[MAX_WIN_IF_NAME_LEN + 1]; + char ascii_name[MAX_WIN_IF_NAME_LEN + 1]; + char ascii_desc[MAX_WIN_IF_NAME_LEN + 1]; int i, j; /* On Windows pcap_lookupdev is implemented by calling @@ -411,22 +430,36 @@ get_interface_list(int *err, char *err_str) { * (http://winpcap.polito.it/docs/dll.htm#PacketGetAdapterNames) * this means that: * - * On Windows 95x, pcap_lookupdev returns an ASCII string with the - * names of the adapters separated by a single ASCII "\0", a double - * "\0", followed by the descriptions of the adapters separated by a - * single ASCII "\0" . The string is terminated by a double "\0". + * On Windows OT (95, 98, Me), pcap_lookupdev returns a sequence of bytes + * consisting of: + * + * a sequence of null-terminated ASCII strings (i.e., each one is + * terminated by a single 0 byte), giving the names of the interfaces; + * + * an empty ASCII string (i.e., a single 0 byte); + * + * a sequence of null-terminated ASCII strings, giving the + * descriptions of the interfaces; + * + * an empty ASCII string. + * + * On Windows NT (NT 4.0, W2K, WXP, W2K3, etc.), pcap_lookupdev returns + * a sequence of bytes consisting of: + * + * a sequence of null-terminated double-byte Unicode strings (i.e., + * each one consits of a sequence of double-byte characters, + * terminated by a double-byte 0), giving the names of the interfaces; * - * On Windows NTx, pcap_lookupdev returns the names of the adapters, - * in UNICODE format, separated by a single UNICODE "\0" (i.e. 2 - * ASCII "\0"), a double UNICODE "\0", followed by the descriptions - * of the adapters, in ASCII format, separated by a single ASCII - * "\0" . The string is terminated by a double ASCII "\0". + * an empty Unicode string (i.e., a double 0 byte); * - * We prepend the device name with a description to make it easier - * for users to choose the interface they want. This requires that - * we split out the device name later on in tethereal.c and gtk/main.c. - * It might be useful to have separate structures for raw names and - * descriptions at some point. + * a sequence of null-terminated ASCII strings, giving the + * descriptions of the interfaces; + * + * an empty ASCII string. + * + * The Nth string in the first sequence is the name of the Nth adapter; + * the Nth string in the second sequence is the descriptio of the Nth + * adapter. */ names = (wchar_t *)pcap_lookupdev(err_str); @@ -446,53 +479,65 @@ get_interface_list(int *err, char *err_str) { while (names[i] != 0) { + /* + * Copy the Unicode description to an ASCII + * string. + */ j = 0; - while (*desc) { + while (*desc != 0) { if (j < MAX_WIN_IF_NAME_LEN) - newname[j++] = *desc++; - } - *desc++; - if (j < MAX_WIN_IF_NAME_LEN - 1) { - newname[j++] = ':'; - newname[j++] = ' '; + ascii_desc[j++] = *desc; + desc++; } + ascii_desc[j] = '\0'; + desc++; + + /* + * Copy the Unicode name to an ASCII string. + */ + j = 0; while (names[i] != 0) { if (j < MAX_WIN_IF_NAME_LEN) - newname[j++] = names[i++]; + ascii_name[j++] = names[i++]; } + ascii_name[j] = '\0'; i++; - newname[j] = 0; - il = g_list_append(il, g_strdup(newname)); + il = g_list_append(il, + if_info_new(ascii_name, ascii_description)); } } else { - /* Otherwise we are in Windows 95/98 and using ascii(8 bit) - characters */ + /* Otherwise we are in Windows 95/98 and using ASCII + (8 bit) characters */ win95names=(char *)names; while(*(win95names+desc_pos) || *(win95names+desc_pos-1)) desc_pos++; desc_pos++; /* Step over the extra '\0' */ desc = win95names + desc_pos; - while (win95names[i] != 0) + while (win95names[i] != '\0') { - j = 0; - while (*desc) { - if (j < MAX_WIN_IF_NAME_LEN) - newname[j++] = *desc++; - } - *desc++; - if (j < MAX_WIN_IF_NAME_LEN - 1) { - newname[j++] = ':'; - newname[j++] = ' '; - } - while (win95names[i] != 0) { - if (j < MAX_WIN_IF_NAME_LEN) - newname[j++] = win95names[i++]; - } + /* + * "&win95names[i]" points to the current interface + * name, and "desc" points to that interface's + * description. + */ + il = g_list_append(il, + if_info_new(&win95names[i], desc)); + + /* + * Skip to the next description. + */ + while (*desc != 0) + desc++; + desc++; + + /* + * Skip to the next name. + */ + while (win95names[i] != 0) + i++; i++; - newname[j] = 0; - il = g_list_append(il, g_strdup(newname)); } } } @@ -510,7 +555,11 @@ get_interface_list(int *err, char *err_str) { static void free_if_cb(gpointer data, gpointer user_data _U_) { - g_free(data); + if_info_t *if_info = data; + + g_free(if_info->name); + if (if_info->description != NULL) + g_free(if_info->description); } void diff --git a/pcap-util.h b/pcap-util.h index 38a6495646..fe9c71bbd3 100644 --- a/pcap-util.h +++ b/pcap-util.h @@ -1,7 +1,7 @@ /* pcap-util.h * Utility definitions for packet capture * - * $Id: pcap-util.h,v 1.3 2003/09/08 21:44:41 guy Exp $ + * $Id: pcap-util.h,v 1.4 2003/09/10 05:35:24 guy Exp $ * * Ethereal - Network traffic analyzer * By Gerald Combs <gerald@ethereal.com> @@ -34,6 +34,16 @@ extern "C" { int get_pcap_linktype(pcap_t *pch, char *devname); #define MAX_WIN_IF_NAME_LEN 511 + +/* + * The list of interfaces returned by "get_interface_list()" is + * a list of these structures. + */ +typedef struct { + char *name; + char *description; +} if_info_t; + GList *get_interface_list(int *err, char *err_str); /* Error values from "get_interface_list()". */ diff --git a/tethereal.c b/tethereal.c index 2a601c15f7..3e14a584bc 100644 --- a/tethereal.c +++ b/tethereal.c @@ -1,6 +1,6 @@ /* tethereal.c * - * $Id: tethereal.c,v 1.194 2003/09/07 00:47:55 guy Exp $ + * $Id: tethereal.c,v 1.195 2003/09/10 05:35:24 guy Exp $ * * Ethereal - Network traffic analyzer * By Gerald Combs <gerald@ethereal.com> @@ -782,6 +782,7 @@ main(int argc, char *argv[]) #ifdef HAVE_LIBPCAP gboolean capture_filter_specified = FALSE; GList *if_list, *if_entry; + if_info_t *if_info; long adapter_index; char *p; gchar err_str[PCAP_ERRBUF_SIZE]; @@ -956,8 +957,13 @@ main(int argc, char *argv[]) } i = 1; /* Interface id number */ for (if_entry = g_list_first(if_list); if_entry != NULL; - if_entry = g_list_next(if_entry)) - printf("%d. %s\n", i++, (char *)if_entry->data); + if_entry = g_list_next(if_entry)) { + if_info = if_entry->data; + printf("%d. %s", i++, if_info->name); + if (if_info->description != NULL) + printf(" (%s)", if_info->description); + printf("\n"); + } free_interface_list(if_list); exit(0); #else @@ -1030,16 +1036,12 @@ main(int argc, char *argv[]) } exit(2); } - if_text = (char *)g_list_nth_data(if_list, adapter_index - 1); - if (if_text == NULL) { + if_info = g_list_nth_data(if_list, adapter_index - 1); + if (if_info == NULL) { fprintf(stderr, "tethereal: there is no interface with that adapter index\n"); exit(1); } -#ifdef _WIN32 - /* XXX - why is this done? */ - if_text = strchr(if_text, '\\'); -#endif - cfile.iface = g_strdup(if_text); + cfile.iface = g_strdup(if_info->name); free_interface_list(if_list); } else cfile.iface = g_strdup(optarg); @@ -1393,12 +1395,8 @@ main(int argc, char *argv[]) } exit(2); } - if_text = strrchr(if_list->data, ' '); /* first interface */ - if (if_text == NULL) { - cfile.iface = g_strdup(if_list->data); - } else { - cfile.iface = g_strdup(if_text + 1); /* Skip over space */ - } + if_info = if_list->data; /* first interface */ + cfile.iface = g_strdup(if_info->name); free_interface_list(if_list); } } |