Minifilter Micro-Filtration Framework: Introduction to the framework and communication between the drive layer and the application layer

Source: Internet
Author: User

Minifilter is the filter-driven framework introduced by Microsoft after sfilter. Compared to sfilter, he is easier to use and requires more concise coding by programmers.
The system has specifically created a filter manager for Minifilter, which is itself a traditional filter driver that provides many interfaces to minifilter users, making it easy to drive a complex file filter. The simple reason is that the traditional filter driver puts a lot of work on the binding device, and now the work is given to the filter manager in Minifilter.
Cons: pure use of minifilter provided by the interface can not see the device object and the IRP, so the programming freedom is not small.
The first step in writing to Minifilter is to register a micro-filter with the filter manager, which is a component that contains some callback functions that may be needed when the file is operating.
The simplest version of the drive entry is only two functions: the registration function and the start function.
[CPP]View PlainCopy
  1. Ntstartus driverentry (__in pdriver_object driverobject,__in punicode_string registrypath)
  2. {
  3. NTSTATUS status;
  4. Unreferenced_parameter (Registrypath);
  5. Status = Fltregisterfilter (Driverobject,&filterregisteraion,&gfilterhandle);
  6. ASSERT (nt_success (status));
  7. if (nt_success (status)) {
  8. Status = Fltstartfiltering (Gfilterhandle);
  9. if (! Nt_successs (status)) {
  10. Fltunregisterfilter (Gfilterhandle);
  11. }
  12. }
  13. return status;
  14. }


1. Registration function Fltregisterfilter
Its second parameter is a struct to fill out its own complete, the structure of the content contains all aspects of the micro-filter.
The structure mentioned above is called flt_registration, and some parts of this structure are basic information, some of which are callback functions. So this structure is somewhat oriented toward the sense of class in the object language. The most NB (Chinese meaning "important") field in this structure is flt_operation_registration (we all know that when the operating system is going to operate on the filesystem, it is by sending a variety of event requests (IRP), The file system is responsible for handling these requests, and the field flt_operation_registration is an array of event requests (this array contains all the events that the filter driver can handle), and each array element itself is a five-tuple. Includes 1. The event that is currently being processed, 2. The identity bit (this flag bit generally write 0, for full filtering, there are two different values are not filter cache read and write and do not filter page read and write operations), 3. The event is processed before the function (pre-operation), 4. The function (post-operation) After the event is processed.
About filter Functions: Now the filter function is in standard format (??). Is it? Because the IRP is now inaccessible, so minifilter sets up a structure to hold all the information in the request package, in which the structure is often the first parameter of the filter function .... The traditional filter driver, and the corresponding request to bind the direct processing function of the format seems to be fixed ... If you want to customize the format of the processing function, it should be encapsulated in the first level processing function. 】
The first parameter is the driver object that knows our own drive. This object is our driver at the time of initialization, the system helps us generate.
The third parameter is an output value, and when our driver is successfully registered, this parameter is the handle to our micro-filter driver.
2. Start function fltstartfiltering
Just one parameter-the filter-driven handle is the output value of the above registered function.
Write your own device filter driver, and plainly write the pre-processing (pre-operation) or complete (post-operation) function of the event you want to filter. As described above, the preprocessing and completion functions for each event are declared well in the flt_operation_registration structure of the structure flt_registration.
So all we have to do is write the function body of the preprocessing and completion functions given in the flt_operation_registration.
For example, in Flt_operation_registration we wrote a field {irp_io_create,0,npprecreate,nppostcreate}. Here we set the preprocessing function of this event npprecreate and the completion function Nppostcreate for event irp_io_create.
As a simple example, the following implementation npprecreate:
[CPP]View PlainCopy
    1. Flt_preop_callback_status Npprecreate (
    2. __inout Pflt_callback_data DATA,
    3. __in pcflt_related_objects Fltobjects,
    4. __deref_out_opt PVOID *completioncontext
    5. )
    6. {
    7. ...
    8. Data->iostatus.status = status_access_denied;
    9. data->iostatus.information = 0;
    10. return flt_preop_complete;
    11. }


Here is the framework of a filter function, first look at the parameter table of the function. The first parameter is the most important one, Pflt_callback_data DATA. For those who have been exposed to the traditional Sfilter framework filter drive, it must be known that when our filter driver filters to the top of the request, it intercepts an IRP request packet, which has almost all the information for this request. Now in the minifilter frame, this parameter is the IRP of the year, only the name is changed, and the information we need to operate (IRP) is in this structure.
Fundamentals of a file request operation:
For those who have not been in touch with the file filter driver, here is simply how the file filter driver works. When some file system requests are made in the upper layer, the request is packaged into an IRP, sent to the underlying filesystem, and when the task is processed, the file system will make the task completion into an IRP packet back to the upper layer, notifying the upper level that the request was processed. When we install our own filter drivers onto the filesystem, our filter drivers can intercept the IRP. At this time, we can open to look at the IRP in the things, do some records, and then nothing changes the IRP continues to send, of course, you can also directly fill in the IRP some fields and then directly to the upper layer, the upper layer received the IRP after the last request is considered to be over, It doesn't matter whether the IRP was sent to him or not by the file system.
So you can see the above example function, fill in the pflt_callback_data structure of the two fields. The last return value Flt_preop_complete indicates that the request is over, and that the IRP is not passed down.
In Minifilter, we want to write the preprocessing and completion functions of the request that we want to filter in addition to ourselves. There are other callback functions that can be written, but they are optional and not necessarily implemented. Specifically, what is not listed here.
Another feature of minifilter: communication with the application layer
When we write the file filter driver, we often communicate with the top-level applications, in the traditional file-filtering drive framework, the communication between the driver and the application layer is usually through Diviceiocontrol to the processing control request in the kernel module, or request a piece of shared storage implementation , are more troublesome. The API for communication is specifically provided in Minifilter, and the API is as easy to use as the socket communication in network programming.
The following code is the process of establishing a communication port:
[CPP]View PlainCopy
    1. PSECURITY_DESCRIPTOR SD;  
    2. object_ attributes oa;  
    3.   
    4. status =  Fltbuilddefaultsecuritydescriptor (&sd,flt_port_all_access);   
    5.   
    6. if (! Nt_success (status) {  
    7.     goto  final;  
    8. }  
    9. rtlinitunicodestring (&unistring, Minispy_port_name);   
    10.   
    11. initializeobejectattributes (&oa, &unistring,obj_kernel_handle| OBJ_CASE_INSENSITIVE,NULL,SD);   
    12.   
    13. status =  Fltcreatecommunicationport (Gfilterhandle,&gserverport,&oa,null,npminiconnect,npminidisconnect, npminimessage,1);   


First, the function fltbuilddefaultsecuritydescriptor is used to apply for a security narrative (the sum, simple point, is to use the communication port users to apply for permission, here you can see the permission to apply is flt_port_all_access, This means: The user-level program connects to a communication port that has the permission level set, and can get all the operation permissions.
The following initializeobejectattributes is used to set some property values for the object we are creating (name: Minispy_port_name).
Finally, the most important fltcreatecommunicationport is to define the required three functions for this port, and register the port (before it is registered). The three functions registered here are:
This function is called when a connection is established between the Npminiconnect user layer and the kernel layer
This function is called when the Npminidisconnect user layer and the kernel layer are disconnected
Npminimessage is called when the user layer and the kernel layer communicate
Of course, since they are called callback functions, they are not called by our user-level program, so we are making requests at the user level through two api:filterconnectcommunicationport and Filtersendmessage. Then the communication port will call these three functions according to our request to do the specific work. The former corresponds to Npminiconnect and the latter corresponds to Npminimessage.
After completing the three callback functions above, the communication code in the kernel is ready.
Here's what's on the other end of the communication: the user layer (application layer). It is important to note that when writing a program, it is necessary to include several minifilter header and library files: Fltuser.h,fltlib.lib,fltmgr.lib, as follows:
#include <FltUser.h>
#progma comment (lib, "FltLib.lib")
#progma comment (lib, "FltMgr.lib")
The following code needs to understand a simple process: first Filterconnectcommunicationport connect to the destination port, and then filtersendmessage send the message. The principle is introduced so much, the specific code in the download connection, wherein the user layer and communication port connection is made into a DLL, the first to build a DLL, and then to use the DLL on which app project, which will load the DLL. Another minifilter can generate a sys system file, the system file with the INF file installed, and in cmd input net start XXX (here is the file name of Sys, is actually the service name, but the two name is the same in most cases) the communication port is opened, Then the app can try to connect and communicate.
Minifilter code Download http://download.csdn.net/detail/arvon2012/4687632
More articles about Technology bash: Blah Paradise Forum Technical Area

http://blog.csdn.net/arvon2012/article/details/7926366

Minifilter Micro-Filtration Framework: Introduction to the framework and communication between the drive layer and the application layer

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.