Ethereal-dev: [Ethereal-dev] [patch] Packet Fence (1.1)
Note: This archive is from the project's previous web site, ethereal.com. This list is no longer active.
From: Paul Schulz <pschulz@xxxxxxxxxxxxxxxxx>
Date: Sat, 19 May 2001 18:02:26 +0930
Greetings, The following adds packet fence 1.1 functionality to the current CVS version of ethereal (2001-05-19) ---------------------------------------------------------------------- diff -urN ethereal-0.8.18/globals.h ethereal-0.8.18-pf-1.1/globals.h --- ethereal-0.8.18/globals.h Sat May 19 11:02:39 2001 +++ ethereal-0.8.18-pf-1.1/globals.h Sat May 19 14:19:05 2001 @@ -36,6 +36,7 @@ extern guint main_ctx, file_ctx; extern gchar *ethereal_path; extern gchar *last_open_dir; +extern gboolean packet_fence_active; /* do we update the packet fence */ extern field_info *finfo_selected; extern ts_type timestamp_type; diff -urN ethereal-0.8.18/gtk/Makefile.am ethereal-0.8.18-pf-1.1/gtk/Makefile.am --- ethereal-0.8.18/gtk/Makefile.am Sat Mar 24 12:53:08 2001 +++ ethereal-0.8.18-pf-1.1/gtk/Makefile.am Sat May 19 14:20:52 2001 @@ -90,7 +90,9 @@ summary_dlg.c \ summary_dlg.h \ ui_util.c \ - ui_util.h + ui_util.h \ + packet_fence.c \ + packet_fence.h EXTRA_DIST = \ Makefile.nmake diff -urN ethereal-0.8.18/gtk/Makefile.nmake ethereal-0.8.18-pf-1.1/gtk/Makefile.nmake --- ethereal-0.8.18/gtk/Makefile.nmake Thu Apr 5 15:28:05 2001 +++ ethereal-0.8.18-pf-1.1/gtk/Makefile.nmake Sat May 19 14:16:06 2001 @@ -46,7 +46,8 @@ simple_dialog.obj \ stream_prefs.obj \ summary_dlg.obj \ - ui_util.obj + ui_util.obj \ + packet_fence.obj libui.lib : ..\config.h $(OBJECTS) diff -urN ethereal-0.8.18/gtk/display_opts.c ethereal-0.8.18-pf-1.1/gtk/display_opts.c --- ethereal-0.8.18/gtk/display_opts.c Sat May 19 11:03:31 2001 +++ ethereal-0.8.18-pf-1.1/gtk/display_opts.c Sat May 19 14:24:08 2001 @@ -72,6 +72,7 @@ #define E_DISPLAY_TIME_DELTA_KEY "display_time_delta" #define E_DISPLAY_AUTO_SCROLL_KEY "display_auto_scroll" #define E_DISPLAY_NAME_RESOLUTION_KEY "display_name_resolution" +#define E_DISPLAY_PACKET_FENCE "display_packet_fence" static void display_opt_ok_cb(GtkWidget *, gpointer); static void display_opt_apply_cb(GtkWidget *, gpointer); @@ -185,6 +186,13 @@ gtk_box_pack_start(GTK_BOX(main_vb), button, TRUE, TRUE, 0); gtk_widget_show(button); + button = dlg_check_button_new_with_label_with_mnemonic( + "Packet _fence graph", accel_group); + gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(button), packet_fence_active); + gtk_object_set_data(GTK_OBJECT(display_opt_w), E_DISPLAY_PACKET_FENCE, + button); + gtk_box_pack_start(GTK_BOX(main_vb), button, TRUE, TRUE, 0); + gtk_widget_show(button); /* Button row: OK, Apply, and Cancel buttons */ bbox = gtk_hbutton_box_new(); gtk_button_box_set_layout (GTK_BUTTON_BOX (bbox), GTK_BUTTONBOX_END); @@ -270,6 +278,10 @@ button = (GtkWidget *) gtk_object_get_data(GTK_OBJECT(parent_w), E_DISPLAY_NAME_RESOLUTION_KEY); prefs.name_resolve = (GTK_TOGGLE_BUTTON (button)->active); + + button = (GtkWidget *) gtk_object_get_data(GTK_OBJECT(parent_w), + E_DISPLAY_PACKET_FENCE); + packet_fence_active = (GTK_TOGGLE_BUTTON (button)->active); } diff -urN ethereal-0.8.18/gtk/gtkclist.c ethereal-0.8.18-pf-1.1/gtk/gtkclist.c --- ethereal-0.8.18/gtk/gtkclist.c Sat May 19 11:03:31 2001 +++ ethereal-0.8.18-pf-1.1/gtk/gtkclist.c Sat May 19 14:16:06 2001 @@ -3143,6 +3143,23 @@ return GTK_VISIBILITY_FULL; } +/* needed by packet_fence.c to be able determine colors for packet display */ +GtkCListRow * +gtk_clist_get_clistrow (GtkCList *clist, + gint row) +{ + GtkCListRow *clist_row; + + g_return_if_fail (clist != NULL); + g_return_if_fail (GTK_IS_CLIST (clist)); + + if (row < 0 || row >= clist->rows) + return NULL; + + clist_row = ROW_ELEMENT (clist, row)->data; + return clist_row; +} + void gtk_clist_set_foreground (GtkCList *clist, gint row, diff -urN ethereal-0.8.18/gtk/gtkclist.h ethereal-0.8.18-pf-1.1/gtk/gtkclist.h --- ethereal-0.8.18/gtk/gtkclist.h Fri May 26 17:17:47 2000 +++ ethereal-0.8.18-pf-1.1/gtk/gtkclist.h Sat May 19 14:16:06 2001 @@ -626,6 +626,10 @@ GdkPixmap **pixmap, GdkBitmap **mask); +/* return row info*/ + +GtkCListRow * gtk_clist_get_clistrow (GtkCList *clist, + gint row); /* sets the foreground color of a row, the color must already * be allocated */ diff -urN ethereal-0.8.18/gtk/main.c ethereal-0.8.18-pf-1.1/gtk/main.c --- ethereal-0.8.18/gtk/main.c Sat May 19 11:03:32 2001 +++ ethereal-0.8.18-pf-1.1/gtk/main.c Sat May 19 14:16:06 2001 @@ -11,6 +11,8 @@ * Jeff Foster, 2001/03/12, added support tabbed hex display windowss * * + * Martin Visser, 15-Nov-2000, added support to allow packet fence + * * 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 @@ -133,6 +135,7 @@ #include "packet_win.h" #include "gtkglobals.h" #include "plugins.h" +#include "packet_fence.h" #include "colors.h" #include "strutil.h" #include "register.h" @@ -325,7 +328,6 @@ return strcmp(text1, text2); } } - /* What to do when a column is clicked */ static void packet_list_click_column_cb(GtkCList *clist, gint column, gpointer data) @@ -430,6 +432,7 @@ gtk_notebook_remove_page( GTK_NOTEBOOK(byte_nb_ptr), 0); select_packet(&cfile, row); + packet_fence_row_select(row); } @@ -1578,6 +1581,7 @@ { GtkWidget *main_vbox, *menubar, *u_pane, *l_pane, *stat_hbox, + *packet_pane, *filter_bt, *filter_cm, *filter_te, *filter_reset; GList *filter_list = NULL; @@ -1623,6 +1627,14 @@ gtk_paned_add2(GTK_PANED(u_pane), l_pane); gtk_widget_show(u_pane); + packet_pane = gtk_hpaned_new(); /* create a horizontal pane to hold packet list and packet fence */ + gtk_paned_gutter_size(GTK_PANED(packet_pane), (GTK_PANED(packet_pane))->handle_size); +/* gtk_container_border_width(GTK_CONTAINER(packet_pane), 0);*/ + gtk_paned_add1(GTK_PANED(u_pane), packet_pane); + gtk_widget_show(packet_pane); + pf = packet_fence_new(); /* create a packet fence */ + gtk_widget_show(pf->box);/* show it */ + /* Packet list */ pkt_scrollw = gtk_scrolled_window_new(NULL, NULL); gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW(pkt_scrollw), @@ -1630,7 +1642,8 @@ set_scrollbar_placement_scrollw(pkt_scrollw, prefs->gui_scrollbar_on_right); remember_scrolled_window(pkt_scrollw); gtk_widget_show(pkt_scrollw); - gtk_paned_add1(GTK_PANED(u_pane), pkt_scrollw); + gtk_paned_add1(GTK_PANED(packet_pane), pf->box); /* add the packet fence */ + gtk_paned_add2(GTK_PANED(packet_pane), pkt_scrollw); /* add the packet list */ packet_list = gtk_clist_new_with_titles(cfile.cinfo.num_cols, cfile.cinfo.col_title); gtk_container_add(GTK_CONTAINER(pkt_scrollw), packet_list); @@ -1644,6 +1657,10 @@ GTK_SIGNAL_FUNC(packet_list_select_cb), NULL); gtk_signal_connect(GTK_OBJECT(packet_list), "unselect_row", GTK_SIGNAL_FUNC(packet_list_unselect_cb), NULL); + gtk_signal_connect(GTK_OBJECT(GTK_CLIST(packet_list)->vadjustment), "value_changed", + GTK_SIGNAL_FUNC(packet_list_value_changed), (gpointer) pf); /* packet fence wants to know somethings changed */ + gtk_signal_connect(GTK_OBJECT(GTK_CLIST(packet_list)->vadjustment), "changed", + GTK_SIGNAL_FUNC(packet_list_changed), (gpointer) pf); for (i = 0; i < cfile.cinfo.num_cols; i++) { if (get_column_resize_type(cfile.cinfo.col_fmt[i]) != RESIZE_MANUAL) gtk_clist_set_column_auto_resize(GTK_CLIST(packet_list), i, TRUE); diff -urN ethereal-0.8.18/gtk/packet_fence.c ethereal-0.8.18-pf-1.1/gtk/packet_fence.c --- ethereal-0.8.18/gtk/packet_fence.c Thu Jan 1 09:30:00 1970 +++ ethereal-0.8.18-pf-1.1/gtk/packet_fence.c Sat May 19 14:31:03 2001 @@ -0,0 +1,597 @@ +/* packet_fence.c + * Routines for displaying Packet Fence + * + * $Id: packet_fence.c,v 1.1 $ + * + * Copyright (c) 2000 by Martin Visser <martin.visser@xxxxxxxxxx> + * + * Ethereal - Network traffic analyzer + * By Gerald Combs + * Copyright 1999 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 + +#include <gtk/gtk.h> + +#include <stdlib.h> +#include <stdio.h> +#include <string.h> + +#ifdef HAVE_UNISTD_H +#include <unistd.h> +#endif + +#include <errno.h> + +#ifdef HAVE_SYS_TYPES_H +#include <sys/types.h> +#endif + +#ifdef HAVE_SYS_STAT_H +#include <sys/stat.h> +#endif + +#ifdef HAVE_IO_H +#include <io.h> /* open/close on win32 */ +#endif + +#ifdef HAVE_DIRECT_H +#include <direct.h> +#endif + +#ifdef HAVE_NETINET_IN_H +#include <netinet/in.h> +#endif + +#include <signal.h> + +#ifdef NEED_SNPRINTF_H +# include "snprintf.h" +#endif + +#if defined(HAVE_UCD_SNMP_SNMP_H) +#ifdef HAVE_UCD_SNMP_VERSION_H +#include <ucd-snmp/version.h> +#endif /* HAVE_UCD_SNMP_VERSION_H */ +#elif defined(HAVE_SNMP_SNMP_H) +#ifdef HAVE_SNMP_VERSION_H +#include <snmp/version.h> +#endif /* HAVE_SNMP_VERSION_H */ +#endif /* SNMP */ + +#ifdef NEED_STRERROR_H +#include "strerror.h" +#endif + +#ifdef NEED_GETOPT_H +#include "getopt.h" +#endif + +#include "main.h" +#include "timestamp.h" +#include "packet.h" +#include "capture.h" +#include "summary.h" +#include "file.h" +#include "menu.h" +#include "../menu.h" +#include "filter_prefs.h" +#include "prefs_dlg.h" +#include "column.h" +#include "print.h" +#include "resolv.h" +#include "util.h" +#include "simple_dialog.h" +#include "proto_draw.h" +#include "epan/dfilter/dfilter.h" +#include "keys.h" +#include "packet_win.h" +#include "gtkglobals.h" +#include "plugins.h" +#include "packet_fence.h" + + +enum zoomed_func { + ZOOMEDOUT, + ZOOMEDIN +}; +enum pf_returns { + PF_COOL, + PF_REDRAW, + PF_END, + PF_BOTTOM, + PF_TOP +}; +enum pf_updates { + PF_POSCHANGED, + PF_DRAWAGAIN +}; + + +static void packet_fence_update(packet_fence *); + +/* ON/OFF SWITCH */ +gboolean packet_fence_active = TRUE; +packet_fence *pf = NULL; + +/* Zoom in and out callback */ +static void +packet_fence_zoomed(GtkWidget *w, gpointer data){ + static int zoom[] = { 1,2,5,10,20,50,100,200,500,1000,2000,5000,10000,20000,50000,100000,200000,500000,1000000};/* simpler than an algorithm!*/ + static int idx = 12; /* where we start off */ + int zoomnum = sizeof(zoom)/sizeof(int);/* number of levels*/ + char str[30]; + + switch ((int)data ) { + case ZOOMEDOUT: + idx++; + if (idx >= zoomnum ) idx = zoomnum - 1; + break; + case ZOOMEDIN: + idx--; + if (idx <= 0 ) idx = 0; + break; + } + pf->usecpix = zoom[idx]; + sprintf(str, "%d usec/pixel",pf->usecpix); + gtk_label_set_text( GTK_LABEL(pf->zoomlevel), str); + pf->update = PF_DRAWAGAIN; + packet_fence_update(pf); +} + +static void +calc_bytepix(packet_fence *pf) +{ + int availpix; + availpix = pf->pixwidth - pf->lmargin - pf->rmargin; + if (availpix <=0) availpix = 10; + pf->bytepix = (float)pf->maxpacketlength/(float)availpix; /*bytes per pixel */ +} + + +/* callback for config event*/ +static gint +packet_fence_config( GtkWidget *widget, + gpointer user_data ) +{ +GdkColor zoomwinfg = {0,0xc000,0xc000,0xc000};/*grey*/ +GdkColor selectfg = {0,0x0000,0x0000,0xffff};/*blue*/ + if (!widget->window) return TRUE;/* too soo yet */ + if (pf->pixmap) + gdk_pixmap_unref(pf->pixmap);/* destroy the old one*/ + + + pf->pixmap = gdk_pixmap_new(widget->window, + widget->allocation.width, + widget->allocation.height, + -1);/* create a pixmap the size of drawing area*/ + gdk_draw_rectangle (pf->pixmap, + widget->style->white_gc, + TRUE, + 0, 0, + widget->allocation.width, + widget->allocation.height); /* white out*/ + pf->pixwidth = widget->allocation.width; /* save width of pf drawing area */ + pf->pixheight = widget->allocation.height; /* save height */ + calc_bytepix(pf); + /* + * I need a better way of scaling this. Maybe I should size to maximum size + * that I've seen?? + */ + pf->pixtimeorigin = pf->pixheight/2; /* centre the time to middle of widget */ + pf->gc = gdk_gc_new(widget->window);/* generic gc*/ + pf->selectgc = gdk_gc_new(widget->window);/* gc for drawing selected packet*/ + pf->zoomwingc = gdk_gc_new(widget->window);/*gc for drawing the zoom window */ + gdk_colormap_alloc_color(gtk_widget_get_colormap(widget),&zoomwinfg,FALSE,TRUE); + gdk_gc_set_foreground(pf->zoomwingc,&zoomwinfg); + gdk_colormap_alloc_color(gtk_widget_get_colormap(widget),&selectfg,FALSE,TRUE); + gdk_gc_set_foreground(pf->selectgc,&selectfg); + + if (pf->framearray) { + pf->framearray = (frame_data**)g_realloc(pf->framearray,pf->pixheight * sizeof (frame_data *)); + /* allocate room to store a widget-ful of frame pointers*/ + } + else { + pf->framearray = (frame_data**)g_malloc(pf->pixheight * sizeof (frame_data *)); + } + pf->update = PF_DRAWAGAIN; + packet_fence_update(pf); + return TRUE; +} + +/* Redraw the screen from the backing pixmap */ +static gint packet_fence_expose( GtkWidget *widget, + GdkEventExpose *event ) +{ + gdk_draw_pixmap(widget->window, + widget->style->fg_gc[GTK_WIDGET_STATE (widget)], + pf->pixmap, + event->area.x, event->area.y, + event->area.x, event->area.y, + event->area.width, event->area.height); + + return FALSE; +} +/* callback for a row being selected in the packet list*/ +void +packet_fence_row_select(gint row) +{ + if (pf->selectedrow != row ) {/* only bother updating if different*/ + pf->selectedrow = row;/* save the new row*/ + pf->update = PF_DRAWAGAIN; + packet_fence_update(pf);/* update */ + } +} + +/* callback for clicking on the packet fence */ +gint +packet_fence_pressed_cb(GtkWidget *widget, GdkEvent *event, gpointer data) +{ + GdkEventButton * event_button; + frame_data * fdata; + int i,pos,sign = 1; + if(widget == NULL || event == NULL ) { + return FALSE; + } + if(event->type == GDK_BUTTON_PRESS) { + event_button = (GdkEventButton *) event; + + if(event_button->button == 1) { + for (i=0;i< 8; i++) {/*look for nearest frame +/- 8 pixels */ + for (sign = -1; sign<=1;sign+=2) { + pos = (sign * i ) + (int)event_button->y;/*alternate 0,-1,1,-2,2.... */ + if (pos<0 || pos >=pf->pixheight) return TRUE; /* gone over the edge */ + if ((fdata = (frame_data*)pf->framearray[pos])) + { + goto_frame(&cfile,fdata->num); /* goto this frame in clist */ + return TRUE; + } + } + } + return TRUE; + } + } + return FALSE;/*not one of ours */ +} + + +/* +static void +packet_fence_size_request_cb (GtkWidget *widget, + GtkRequisition *requisition, + gpointer user_data) +{ + printf("got size\n"); +} +*/ + +static void +packet_fence_config_event_cb (GtkWidget *widget, + GdkEventConfigure *event, + gpointer user_data) +{ + packet_fence_config(widget,user_data); +} + + +/* create the packet fence */ +packet_fence * +packet_fence_new() +{ + GtkWidget *zoomin; + GtkWidget *zoomout; + GtkWidget *bbox; + pf = (packet_fence*) g_malloc(sizeof(packet_fence)); + pf->pixwidth = 50; + pf->pixheight = 10; + pf->lmargin = 10 ; + pf->rmargin = 20 ; + pf->hmargin = 20 ; + pf->maxpacketlength = 1518;/* till we know better */ + calc_bytepix(pf); + pf->usecpix = 10000 ; /* usecs per pixel */ + pf->timeorigin = 0; + pf->pixtimeorigin = 0; + pf->adj_seq = 0; + pf->started = FALSE; + pf->update = FALSE; + pf->box = gtk_table_new (2,2, FALSE); /* create 2 x 2 table */ + gtk_widget_set_usize(pf->box, 100 ,100); + gtk_widget_show (pf->box); + pf->ruler = gtk_vruler_new(); + gtk_ruler_set_metric(GTK_RULER(pf->ruler),GTK_PIXELS); + gtk_widget_set_usize(pf->ruler, 16 ,0); + gtk_table_attach (GTK_TABLE (pf->box), pf->ruler, 0,1,0,1,GTK_FILL,GTK_FILL|GTK_EXPAND,0,0); /* put a 20 pixel wide ruler down left */ + gtk_widget_show (pf->ruler); + pf->drawing_area = gtk_drawing_area_new (); + gtk_drawing_area_size (GTK_DRAWING_AREA (pf->drawing_area), pf->pixwidth, pf->pixheight); + gtk_table_attach (GTK_TABLE (pf->box), pf->drawing_area, 1,2,0,1,GTK_FILL|GTK_EXPAND|GTK_SHRINK,GTK_FILL|GTK_EXPAND,0,0); /* put a drawing area up on the right */ + gtk_widget_show (pf->drawing_area); + bbox = gtk_hbox_new(FALSE,1); + zoomout = gtk_button_new_with_label("<"); + gtk_signal_connect(GTK_OBJECT(zoomout), "clicked", + GTK_SIGNAL_FUNC(packet_fence_zoomed), (gpointer) ZOOMEDOUT); + zoomin = gtk_button_new_with_label(">"); + gtk_signal_connect(GTK_OBJECT(zoomin), "clicked", + GTK_SIGNAL_FUNC(packet_fence_zoomed), (gpointer) ZOOMEDIN); + pf->zoomlevel = gtk_label_new("10000 usec/pixel"); + gtk_widget_set_usize(zoomin, 14 ,14); + gtk_widget_set_usize(zoomout, 14 ,14); + gtk_widget_set_usize(pf->zoomlevel, 0 ,14); + gtk_label_set_justify(GTK_LABEL(pf->zoomlevel),GTK_JUSTIFY_LEFT); + + gtk_box_pack_start(GTK_BOX(bbox), zoomout, FALSE, FALSE, 0); + gtk_box_pack_start(GTK_BOX(bbox), zoomin, FALSE, FALSE, 0); + gtk_box_pack_start(GTK_BOX(bbox), pf->zoomlevel, FALSE, FALSE, 0); + gtk_table_attach (GTK_TABLE (pf->box), bbox, 1,2,1,2,GTK_FILL|GTK_EXPAND|GTK_SHRINK,GTK_FILL,0,0); /* add the zoom box with two buttons and label to bottom right */ + gtk_widget_show(zoomin); + gtk_widget_show(zoomout); + gtk_widget_show(pf->zoomlevel); + gtk_widget_show(bbox); + gtk_signal_connect (GTK_OBJECT (pf->drawing_area), "expose_event", + (GtkSignalFunc) packet_fence_expose, NULL); + gtk_signal_connect (GTK_OBJECT(pf->drawing_area),"configure_event", + (GtkSignalFunc) packet_fence_config_event_cb, NULL); +/* gtk_signal_connect (GTK_OBJECT(pf->drawing_area),"size_request", + (GtkSignalFunc) packet_fence_size_request_cb, NULL); +*/ + gtk_signal_connect(GTK_OBJECT(pf->drawing_area), "button_press_event", + GTK_SIGNAL_FUNC(packet_fence_pressed_cb), NULL); + gtk_widget_set_events (pf->drawing_area, GDK_EXPOSURE_MASK|GDK_BUTTON_PRESS_MASK ); + return pf; + +} + +/* return the relative time, in usecs, a frame was grabbed */ +static int +framereltime( frame_data * fdata) +/* compute total relative time */ +{ + return fdata->rel_secs * 1000000 + fdata->rel_usecs; +} + +/* convert time to pixels*/ +static int +timetopix( packet_fence * pf, int time ) +/* convert time to pixel position */ +{ + int timeoffset; + int pixtime; + timeoffset = time - pf->timeorigin;/* diff between now and origin */ + pixtime = timeoffset / pf->usecpix + pf->pixtimeorigin;/* pixels down relative to 0 */ + + return pixtime; +} + +/* convert pixels to time*/ +static int +pixtotime( packet_fence * pf, int pix ) +/* convert pixel position to time in usecs */ +{ + int pixoffset; + int time; + pixoffset = pix - pf->pixtimeorigin;/* diff between centre and position */ + time = pixoffset * pf->usecpix + pf->timeorigin;/* relative to time */ + + return time; +} + +/* draw a packet in the right spot */ +gboolean +packet_fence_draw_packet(gint row ) +{ + frame_data * fdata; + gint pixlen,time,pixdown; + GdkGC * packetgc; + GtkCListRow *clistrow; + fdata = (frame_data *) gtk_clist_get_row_data(GTK_CLIST(packet_list), row); + if (fdata == NULL ) return PF_END; /* might not be loaded yet */ + if (fdata->pkt_len > pf->maxpacketlength ) { + pf->maxpacketlength = fdata->pkt_len + 100; /* don't want to it toom often */ + calc_bytepix(pf); + return PF_REDRAW; + } + + pixlen = fdata->pkt_len / pf->bytepix; /* set packet length */ + time = framereltime(fdata); + pixdown = timetopix(pf,time); + if (pixdown <0 ) return PF_BOTTOM; /* reached a limit */ + if (pixdown >= pf->pixheight) return PF_TOP; /* reached a limit */ + if (pf->selectedrow == row) /* if it is selected in list add the blue bits*/ + { + gdk_draw_line(pf->pixmap,pf->selectgc,0,pixdown,pf->lmargin-2,pixdown); + gdk_draw_line(pf->pixmap,pf->selectgc,pf->pixwidth-pf->rmargin+1,pixdown,pf->pixwidth,pixdown); + } + + clistrow = gtk_clist_get_clistrow(GTK_CLIST(packet_list),row);/* this is the call to my hacked function to get the GtkCListRow info */ + if (!clistrow) return PF_END; /* reached a limit */ + + if (clistrow->fg_set) {/* its not default*/ + gdk_gc_set_foreground(pf->gc,&(clistrow->foreground)); + packetgc = pf->gc; + } else { /* its default colour*/ + packetgc = pf->drawing_area->style->black_gc ; + } + gdk_draw_line(pf->pixmap,packetgc,pf->lmargin,pixdown,pf->lmargin + pixlen,pixdown); + pf->framearray[pixdown] = fdata; /* save the (frame_data *) where we drew it for later */ + if (row <=0) return PF_BOTTOM; + return PF_COOL; /* sucessfully drawn */ +} +static int +packet_fence_clear_bg(packet_fence *pf) +{ + if(!pf || !pf->pixmap || !pf->drawing_area) return FALSE; + + gdk_draw_rectangle (pf->pixmap, + pf->drawing_area->style->white_gc, + TRUE, + 0, 0, + pf->drawing_area->allocation.width, + pf->drawing_area->allocation.height);/*make a clean slate */ + return TRUE; +} +static int +packet_fence_draw_zoomrect(packet_fence *pf) +{ + frame_data *fdata; + int time,zoomrecttop,zoomrectbot; + if(!pf || !pf->pixmap) return FALSE; + /* now print zoom rectangle. This shows where the displayed packet list is relative to the displayed packet fence*/ + if ((fdata = ((frame_data *) gtk_clist_get_row_data(GTK_CLIST(packet_list), pf->firstrow)) )){ + time = framereltime(fdata); + zoomrecttop = timetopix(pf,time) - 1; + } + else zoomrecttop = 0; + if ((fdata = ((frame_data *) gtk_clist_get_row_data(GTK_CLIST(packet_list), pf->lastrow)) )){ + time = framereltime(fdata); + zoomrectbot = timetopix(pf,time); + } + else zoomrectbot = pf->pixheight; + gdk_draw_rectangle(pf->pixmap,pf->zoomwingc,TRUE,pf->lmargin,zoomrecttop,pf->pixwidth - pf->lmargin - pf->rmargin, zoomrectbot - zoomrecttop + 2); /* draw it in */ + return TRUE; +} +static int +packet_fence_new_position(packet_fence *pf) +{ + frame_data *fdata; + GtkAdjustment *adj; + int i; + + + if (!pf || !packet_fence_active || !pf->framearray) { /* only update if we are ready, willing and able */ + return FALSE; + } + adj = GTK_CLIST(packet_list)->vadjustment; + for (i=0;i<pf->pixheight;i++) pf->framearray[i] = NULL; /* clear out the stored data as it will be all wrong */ + pf->adjvalue = adj->value; + pf->adjpagesize = adj->page_size; + pf->firstrow = (int)(adj->value)/(GTK_CLIST(packet_list)->row_height+1); /* get the first row in the packet list. (The +1 works for me) */ + pf->lastrow = pf->firstrow - 1 + (int)(adj->page_size)/(GTK_CLIST(packet_list)->row_height);/* work out what the last row should be. page_size and row_height are in pixels*/ + pf->midrow = (pf->firstrow + pf->lastrow) / 2; /* find the middle*/ + fdata = (frame_data *) gtk_clist_get_row_data(GTK_CLIST(packet_list), pf->midrow); + if (fdata == NULL ) { + return FALSE; + } + pf->timeorigin = framereltime(fdata); /* this is the time in the mid of widget */ + return TRUE; +} +static int +packet_fence_refresh_drawing_area(packet_fence *pf) +{ + GdkRectangle update_rect; + if(!pf || !pf->drawing_area) return FALSE; + update_rect.x = 0; + update_rect.y = 0; + update_rect.width = pf->drawing_area->allocation.width; + update_rect.height = pf->drawing_area->allocation.height; + gtk_widget_draw( pf->drawing_area, &update_rect);/* we can draw to screen now */ + return TRUE; +} +static int +packet_fence_update_ruler(packet_fence *pf) +{ + int firsttime,lasttime; + firsttime = pixtotime(pf,0); + lasttime = pixtotime(pf,pf->pixheight); + gtk_ruler_set_range( GTK_RULER(pf->ruler), firsttime/1000000.0, lasttime/1000000.0 ,pf->timeorigin/1000000.0,10000); /* set the ruler limits */ + return TRUE; +} +static int +packet_fence_update_packets(packet_fence *pf) +{ + int flag = TRUE; + int ret = 0; + int static draw_count=0; + while(flag) { + ret = packet_fence_draw_packet(pf->currentrow) ; /* draw until none left */ + if (ret == PF_BOTTOM) { + pf->currentrow = pf->midrow + 1; + continue; + } else if (ret == PF_REDRAW ) { + pf->currentrow = pf->midrow; + continue; + } else if (ret == PF_END || ret == PF_TOP ) { + flag = FALSE; + continue; + } + if(draw_count++>200) { + draw_count = 0; + packet_fence_refresh_drawing_area(pf); + if (gtk_events_pending()) {/* someone wants some time */ + pf->idleid = gtk_idle_add((GtkFunction)&packet_fence_update,pf);/* wait for someone else */ + return FALSE; + } + } + + if(pf->currentrow <= pf->midrow ){ + pf->currentrow--; + } + else if(pf->currentrow > pf->midrow ){ + pf->currentrow++; + } + } + return TRUE; + + +} +/* update the packet fence */ +static void +packet_fence_update(packet_fence * pf){ + + if(!pf) return ; + if(pf->idleid) {/* this is a return from being interrupted */ + gtk_idle_remove(pf->idleid); + pf->idleid = 0; + } + if(!packet_fence_new_position(pf)) return; + if(!packet_fence_clear_bg(pf)) return; + if(!packet_fence_draw_zoomrect(pf)) return; + pf->currentrow = pf->midrow; + pf->started = TRUE; + if(!packet_fence_update_packets(pf)) return; + pf->started = FALSE; + if(!packet_fence_refresh_drawing_area(pf)) return; + if(!packet_fence_update_ruler(pf))return; + return; +} + +/* packet list value has changed */ +void +packet_list_value_changed(GtkAdjustment *adj, gpointer user_data) +{ + packet_fence * pf; + pf = (packet_fence *)user_data; + if (!pf) return; + pf->adj_seq++; + pf->update = PF_POSCHANGED; + packet_fence_update(pf); +} +/* packet list has changed, might be resize */ +void +packet_list_changed(GtkAdjustment *adj, gpointer user_data) +{ + packet_fence * pf; + pf = (packet_fence *)user_data; + if (!pf) return; + if (adj->value == pf->adjvalue && adj->page_size == pf->adjpagesize) { + return; /* nothing really changed, the clist just got nudged. Probably by us writing to the zoom label */ + } + pf->update = PF_POSCHANGED; + packet_fence_update(pf); +} diff -urN ethereal-0.8.18/gtk/packet_fence.h ethereal-0.8.18-pf-1.1/gtk/packet_fence.h --- ethereal-0.8.18/gtk/packet_fence.h Thu Jan 1 09:30:00 1970 +++ ethereal-0.8.18-pf-1.1/gtk/packet_fence.h Sat May 19 14:16:06 2001 @@ -0,0 +1,69 @@ + +/* packet_fence.h + * Definitions for Packet Fence + * + * $Id: packet_fence.h,v 1.1 $ + * + * Copyright (c) 2000 by Martin Visser <martin.visser@xxxxxxxxxx> + * + * Ethereal - Network traffic analyzer + * By Gerald Combs + * Copyright 1999 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. + */ + +typedef struct _packet_fence { + GtkWidget *box ; + GtkWidget *drawing_area; + GtkWidget *ruler; + GtkWidget *zoomlevel; + GdkPixmap * pixmap; + GdkGC * gc; + GdkGC * zoomwingc; + GdkGC * selectgc; + int pixwidth; + int pixheight; + int hmargin; + int lmargin; + int rmargin; + float bytepix; + int usecpix; + int timeorigin; + int pixtimeorigin; + int selectedrow; + int currentrow; + int firstrow; + int lastrow; + int midrow; + int maxpacketlength; + int adj_seq; + int started; + int interrupted; + int update; + int idleid; + float begintime; + float endtime; + gfloat adjvalue; + gfloat adjpagesize; + frame_data **framearray; +} packet_fence; + + +packet_fence *packet_fence_new(); +void packet_list_value_changed(GtkAdjustment * adj, gpointer user_data); +void packet_list_changed(GtkAdjustment * adj, gpointer user_data); +void packet_fence_row_select(gint row); + +extern packet_fence * pf;
- Prev by Date: [Ethereal-dev] IGMP v0,v1,v2,v3
- Next by Date: [Ethereal-dev] Patch: Missing initializer warnings in gtkclist
- Previous by thread: [Ethereal-dev] IGMP v0,v1,v2,v3
- Next by thread: [Ethereal-dev] Patch: Missing initializer warnings in gtkclist
- Index(es):