[Gd-chatter] r10855 - in trunk/libraries: gui-sniffer pcap

hannes at gwydiondylan.org hannes at gwydiondylan.org
Tue Aug 15 23:20:49 CEST 2006


Author: hannes
Date: Tue Aug 15 23:20:46 2006
New Revision: 10855

Modified:
   trunk/libraries/gui-sniffer/gui-sniffer.dylan
   trunk/libraries/pcap/library.dylan
   trunk/libraries/pcap/pcap.dylan
Log:
Bug: 7299
*implement filter expression history
*add a list view of available devices


Modified: trunk/libraries/gui-sniffer/gui-sniffer.dylan
==============================================================================
--- trunk/libraries/gui-sniffer/gui-sniffer.dylan	(original)
+++ trunk/libraries/gui-sniffer/gui-sniffer.dylan	Tue Aug 15 23:20:46 2006
@@ -112,7 +112,11 @@
   let filter-string = gadget-value(frame.filter-field);
   let old = frame.filter-expression;
   if (filter-string.size > 0)
-    frame.filter-expression := parse-filter(filter-string)
+    frame.filter-expression := parse-filter(filter-string);
+    if (old ~= frame.filter-expression & every?(curry(\~=, filter-string), frame.filter-history))
+      frame.filter-history := add!(frame.filter-history, filter-string);
+      gadget-items(frame.filter-field) := frame.filter-history;
+    end;
   else
     frame.filter-expression := #f
   end;
@@ -170,6 +174,43 @@
        end;
 end;
 
+define method compute-absolute-offset (frame :: <ethernet-frame>)
+ => (res :: <integer>)
+  sorted-frame-fields(frame).last.start-offset
+end;
+
+define method compute-absolute-offset (frame :: <header-frame>)
+ => (res :: <integer>)
+  if (frame.parent)
+    compute-absolute-offset(frame.parent) + sorted-frame-fields(frame).last.start-offset
+  else
+    0
+  end;
+end;
+
+define method compute-absolute-offset (frame :: <frame-field>)
+ => (res :: <integer>)
+  if (instance?(frame-field.frame, <ethernet-frame>))
+    0
+  else
+    compute-absolute-offset(frame-field.frame.parent)
+  end;
+end;
+
+define method highlight-hex-dump (mframe :: <gui-sniffer-frame>)
+  let packet = mframe.packet-table.gadget-value;
+  let tree = mframe.packet-tree-view;
+  let frame-field = tree.gadget-items[tree.gadget-selection[0]];
+  let off = compute-absolute-offset(frame-field);
+
+  let start-highlight = off + frame-field.start-offset;
+  let end-highlight = off + frame-field.end-offset;
+
+  format-out("start %d end %d\n",
+             start-highlight,
+             end-highlight);
+end;
+
 define variable *count* :: <integer> = 0;
 define method counter ()
   *count* := *count* + 1;
@@ -181,11 +222,14 @@
   slot filter-expression = #f;
   slot ethernet-interface = #f;
   slot first-packet-arrived :: false-or(<date>) = #f;
+  slot filter-history :: <list> = make(<list>);
 
   pane filter-field (frame)
-    make(<text-field>,
+    make(<combo-box>,
          label: "Filter expression",
-         activate-callback: method(x) apply-filter(frame) end);
+         value-changed-callback: method(x) apply-filter(frame) end,
+         activate-callback: method(x) apply-filter(frame) end,
+         items: frame.filter-history);
 
   pane filter-pane (frame)
     horizontally()
@@ -309,21 +353,19 @@
 define method prompt-for-interface
   (#key title = "Please specify interface", owner)
  => (interface-name :: false-or(<string>), promiscious? :: <boolean>)
-  let interface-text = make(<text-field>,
-                            label: "Interface:",
-                            activate-callback: exit-dialog);
+  let devices = find-all-devices();
+  let interfaces = make(<list-box>, items: devices);
   let promiscious? = make(<check-box>, items: #("promiscious"), selection: #[0]);
   let interface-selection-dialog
     = make(<dialog-frame>,
            title: title,
            owner: owner,
            layout: horizontally()
-                     interface-text;
+                     interfaces;
                      promiscious?
-                   end,
-           input-focus: interface-text);
+                   end);
   if (start-dialog(interface-selection-dialog))
-    values(gadget-value(interface-text), size(gadget-value(promiscious?)) > 0)
+    values(gadget-value(interfaces), size(gadget-value(promiscious?)) > 0)
   end;
 end;
 

Modified: trunk/libraries/pcap/library.dylan
==============================================================================
--- trunk/libraries/pcap/library.dylan	(original)
+++ trunk/libraries/pcap/library.dylan	Tue Aug 15 23:20:46 2006
@@ -25,6 +25,6 @@
   use byte-vector;
   use flow;
   use packetizer, import: { unparsed-class, <ethernet-frame>, <frame>, assemble-frame };
-  export <ethernet-interface>, interface-name, running?-setter, running?;
+  export <ethernet-interface>, interface-name, running?-setter, running?, find-all-devices;
 end;
 

Modified: trunk/libraries/pcap/pcap.dylan
==============================================================================
--- trunk/libraries/pcap/pcap.dylan	(original)
+++ trunk/libraries/pcap/pcap.dylan	Tue Aug 15 23:20:46 2006
@@ -108,6 +108,22 @@
     error("Device %s not found", interface.interface-name);
   end;
 end;
+
+define method find-all-devices () => (res :: <collection>)
+  let res = make(<stretchy-vector>);
+  let errbuf = make(<byte-vector>);
+  let (errorcode, devices) = pcap-find-all-devices(buffer-offset(errbuf, 0));
+  for (device = devices then device.next, while: device ~= null-pointer(<pcap-if*>))
+    let str = make(<string>, size: device.description.size);
+    //XXX: isn't there a convinience function for converting <C-string> to <string>
+    //XXX: generate a real object, and also return device-name
+    for (ele in device.description, i from 0)
+      str[i] := ele;
+    end;
+    add!(res, str)
+  end;
+  res;
+end;
  
 define C-struct <pcap-if>
   slot next :: <pcap-if*>;
@@ -144,11 +160,17 @@
   c-name: "pcap_sendpacket";
 end;
 
+define C-function pcap-close
+  parameter pcap-t :: <C-void*>;
+  //result error :: <C-void>;
+  c-name: "pcap_close";
+end;
+
 define method push-data-aux (input :: <push-input>,
                              node :: <ethernet-interface>,
                              frame :: <frame>)
   let buffer = assemble-frame(frame);
-  let res = pcap-inject(node.pcap-t, buffer-offset(buffer, 0), buffer.size);
+  pcap-inject(node.pcap-t, buffer-offset(buffer, 0), buffer.size);
 end;
 
 define method toplevel (interface :: <ethernet-interface>)
@@ -159,5 +181,6 @@
                   receive-callback,
                   export-c-dylan-object(interface));
   end;
+  pcap-close(interface.pcap-t);
 end;
 



More information about the chatter mailing list