.NET WinPCap

As I stated in my last post, I am currently geeking out on packet capture software.  The WireShark network analysis tool is pretty awesome and is built using the WinPCap library which is itself a port of libpcap to the Win32 environment.  The unfortunate part, or at least for us .NET developers, is that there is no (IMHO of course) good .NET binding to WinPCap.  Well, I've gone ahead and spent some time getting an initial wrapper done using P/Invoke.

I've taken a different initial strategy from the other project I found and I think it makes more sense in the long run.  The other project attempts to provide a more elegant binding by wrapping the native functions of WinPCap in a couple of simple objects.  This isn't necessarily bad, however the author decided to hide the actual P/Invoke calls, which means if you (like me) don't like his class structure, you can't simply use the P/Invokes directly to build your own.  So, I went ahead and I wrote my own set of P/Invoke calls to bind to WinPCap.

I tried to stick to the following rules:

  1. All P/Invoke method name exactly match the native function names
  2. All managed type names used in marshalling exactly match the native struct names
  3. All method parameters in the P/Invokes have the same name as in their native functions
  4. Marshal parameters as closely as possible (i.e. don't just use IntPtr for everything)

Of course, I couldn't stick to the rules 100% due to some technical limitations, but in most cases it is obvious where I deviated.

We should see the following advantages from this:

  1. All documentation already in existence for WinPCap is still 100% relevant.
  2. All C/C++ code samples using the native WinPCap can be ported (more or less) directly into C# code.
  3. Developers now have the freedom to build their own tools using WinPCap in .NET using whatever class structure they'd like

The Library

Aside from the supporting structs that are used to marshal the unmanaged types, there are only two classes you need to be concerned with in the library.

WinPCapConstants - Holds the constants translated from the #defines of the pcap.h header file

WinPCapDriver - Static class that holds all P/Invoke declarations used to bind to WinPCap.  All functions except those that are listed in the WinPCap docs as Windows specific or dealing with packet filtering are currently available.  The Windows specific functions and packet filtering functions will be added as the project progresses.

There is also one handy extension method that I added to help with marshalling the various data structures used by WinPCap.  It is defined as follows:

namespace Nomad.Net.PacketCapture.Interop { public static class IntPtrExtensions {

    public static TStruct AsStruct<TStruct>(this IntPtr ptr)
    {

        return (TStruct)Marshal.PtrToStructure(ptr, typeof(TStruct));

    }

}

}

Normally, we'd have to write something like the following to marshal a pcap_if structure from unmanaged to managed code:

pcap_if nic = (pcap_if)Marshal.PtrToStructure(nicPointer, typeof(pcap_if));

This is pretty heinous...In C we would have been able to just cast or dereference the pointer.  With the extension method above, the code becomes more readable:

pcap_if nic = nicPointer.AsStruct<pcap_if>();

It isn't all that much shorter in terms of length, but it reads much more like English.

Going Forward

My next step is to continue porting the original WinPCap examples from C to C#.  This will help me test the P/Invoke calls and learn more about WinPCap and how it is supposed to operate.  After that I will create my own higher-level wrapper using C# to abstract the details.  Again, the best part of all this is that if you don't like my high level code then you should still at least be able to access WinPCap via .NET, albeit in a more raw form.

The following code should work, but you first need to install WinPCap.  I also recommend you download the developer pack so you can compare the native C examples with the couple of .NET ones I've done so far. The differences are relatively minor, but important since they mostly have to do with features/limitations of mixing C and .NET.  Also, the HTML based documentation for WinPCap is still valid, and I have yet to put much in the way of comments in my code. 

Consider the following downloads as Alpha quality at best:

This article is part of the GWB Archives. Original Author: newman

New on Geeks with Blogs

  • We Won The One Award I Actually Care About

    Full Scale made the Inc. 5000 for the fifth year straight, the 12th listing across my three companies. Here is why the one award you cannot buy is worth stopping for.

  • Your Customers Build the Features Now

    I let a tool I liked sit dead for a year rather than build the features I wanted. An MCP server meant I never had to, and your customers can do the same to your product.

  • Get the Size of a Directory in Linux the Easy Way

    du -sh for the quick answer, ncdu for the cleanup, df for the disk itself: every command for checking directory size in Linux, plus why du and df never agree.

  • Vim Search and Replace: The Ultimate Guide

    One :%s command replaces every match in a file before a find dialog would even open. The Vim substitute patterns worth the muscle memory: flags, ranges, capture groups, and multi-file edits.