2004-01-12 ■ analysis of using C # development of network firewall technology: seafrog ■ Source: Forum
N-BYTE Network Watcher is a single-machine version of the network security tool, in short, is a personal version of the personal version of the. In the development of N-BYTE Network Watcher 1.0, Ndis Hook Driver technology uses NDIS Hook Driver technology to implement network packet filtering, which enables N-BYTE network watchmakers to filter network packages in the network layer, thereby achieving powerful functions. Since the main program of the software is written in C #, there is no drive device control function with similar Deviceiocontrol function functions in C #, and the driver under Ndis Hook Driver technology is written in the C language under DDK, in order to enable the main program The control and mutual communication of the driver uses the following design: In the above scheme, a module DriverDll.dll responsible for the main program and the NDIS Hook Driver driver communication and control, and encapsulated by a package driver written in C # The module of the information can send this driver information to the main program, the main program can identify and operate the data type in the module. On the .NET application uses drivers, face two questions: 1. How to implement the .NET application to control the function of the driver? 2. How to pass unmanaged data types from the driver to the .NET application? The following is a detailed solution we have these issues: How to implement the "Net application control the function of the driver? DRIVERDLL.DLL written in hosted C implements direct control of the driver, and the main program implements indirect control over the driver by calling the method. For example, in the NByte.h file, the Start_IP_HOOK constant is used as a parameter to turn on the driver package to open the driver package filter, which defines the IOCTRL hosted class in the managed C module and defines the following to the buffer write. Parameter method:
/ / Write data to the buffer. DWORD WriteIo (DWORD code, PVOID buffer, DWORD count) {if (hDriverHandle == NULL) return ERROR_DRIVER_HANDLE; DWORD bytesReturned; BOOL returnCode = DeviceIoControl (hDriverHandle, code, buffer, count, NULL, 0, & bytesReturned, NULL); if ( ReturnCode) Return Error_io_ctrl; Return Success;} Of course, use this method is not convenient, so defined a public function to provide the main program call: // Start the package filter Bool Startiphook () {Return (Writeio (Writeio (START_IP_HOOK, NULL, 0) == Success);
In this way, as long as the object IC of IOCTRL is declared in the main program, it can be opened via IC.Startiphook (), and the driving of the driver filtering can be implemented, and the driver can be used to perform other operations, such as add, modify Packet filtering rules.
How to pass unmanaged data types from the driver to the .NET application? In order to be able to output a security log, you must give the main program to get the package information in the driver. Use the semaphore mechanism that can easily implement the information transfer between the drivers and the non-hosting code, then? This requires the .NET application to deliver unmanaged data types access_info. In nbyte.h, this is defined in this Access_info structure:
Typed_info {ushort protocol; ulong source; ulong destinationip; ushort sourceport; ushort destinationport;} access_info; Obviously, directly transmitting the non-managed data type is not possible, need to be converted. First, in the octrl class define a few package information parameters to be passed:
Public __gc class ioCtrl {public: ushort protocol; // Internet Protocol Type Ulong SourceIP; // Source IP Address Ulong DestinationIP; // Destination IP Address Ushort Sourceport; // Source Port Ushort DestinationPort; // Destination Port ............... ...}
Then, assign these parameters to these parameters in the getAccessinfo () function:
Void getAccessinfo () {Access_info ai; Bool Result = (Readio) == SUCCESS; this-> protocol = ai.protocol; this-> sourceip = ai.sourceip; this-> destinationIP = ai.destinationip; this-> sourceport = ai.sourceport; this-> destinationport = ai.destinationport;
Since this information is obtained in the ioctrl class, you need to encapsulate the data type that is easy to handle in a master program so that the InfoEvent class is implemented with C # to encapsulate this information:
// This class encapsulates the details of the packet, which can be passed between its modules through the event.
Public class infoEvent: Eventargs {string sinfo; // Used to store the private member of the output information public INT PLENGTH; //commonfunction.sport array length public ushort protocol; // network communication protocol type public uint source sourceIP; // data packet of PUBLIC UINT SOURCEIP; // Source IP Public Uint DestinationIP; // Destination IP Public Ushort Source Region; // Packet Source Port Public Ushort DestinationPort; // Destination Port of // Packet .....................................
Below the InfoProvider Driver Information Provider class that is implemented with hosted C to the main program, you need to use a commission to generate an event:
// Declare the commissioned event to transfer data to the main program. __delegate void driverinfo (Object * sender, infoEvent * e); // declare the response event function. __event driverinfo * onDriverinfo;
Then define a method in the InfoProvider driver information provider class, run this method in the main program, using the event function OnDriverInfo in this method:
// The process used to get the driver information will turn on the process in the main program. Void getInfothreadProc () {this-> HEVENT = Openevent (Synchronize, False, "Nbevent"); if (! IC-> getDriverHandle ()) {return;} while (true) {f (!}) exitthread (0); WaitforsingleObject (this-> HEVENT, INFINITE); NPACKETS ; IC-> getAccessinfo (); IC-> resetEvent (); // Defines an object that can be identified by OndriverInfo to the main program. InfoEvent * ie = new infoEvent (IC-> Protocol, IC-> SourceIP, IC-> DestinationIP, IC-> Sourceport, IC-> DestinationPort); OnDriverInfo (this, IE);} IC-> ClosedRiverHandle (); return; } In the main program, this process will be turned on and define the handle of the OndriverInfo DEALWITHINFO:
pInfo = new InfoProvider (); // open exchange of information with the drive process FilterThread = new Thread (new ThreadStart (pInfo.GetInfoThreadProc)); FilterThread.IsBackground = true; FilterThread.Start (); pInfo.OnDriverInfo = new InfoProvider.DriverInfo DEALWITHINFO;
This master program can add the processing of the InfoEvent object in the DealWithInfo function. It can be seen that through the conversion of the intermediate module IOCTRL, the acquisition and processing of the non-managed data type in the driver is implemented. Net main program.