Registering Context Types

When a minifilter driver calls FltRegisterFilter from its DriverEntry routine, it must register each type of context that it uses.

To register context types, the minifilter driver creates a variable-length array of FLT_CONTEXT_REGISTRATION structures and stores a pointer to the array in the ContextRegistration member of the FLT_REGISTRATION structure that the minifilter driver passes in the Registration parameter of FltRegisterFilter. The order of the elements in this array does not matter. However, the last element in the array must be {FLT_CONTEXT_END}.

For each context type that the minifilter driver uses, it must supply at least one context definition in the form of an FLT_CONTEXT_REGISTRATION structure. Each FLT_CONTEXT_REGISTRATION structure defines the type, size, and other information for the context.

When the minifilter driver creates a new context by calling FltAllocateContext, the filter manager uses the Size parameter of the FltAllocateContext routine, as well as the Size and Flags members of the FLT_CONTEXT_REGISTRATION structure, to select the context definition to be used.

For fixed-size contexts, the Size member of the FLT_CONTEXT_REGISTRATION structure specifies the size, in bytes, of the portion of the context structure that is defined by the minifilter driver. The maximum size for a context is MAXUSHORT (64 KB). Zero is a valid size value. The filter manager implements fixed-size contexts using lookaside lists. The filter manager creates two lookaside lists for each size value: one paged and one nonpaged.

For variable-size contexts, the Size member must be set to FLT_VARIABLE_SIZED_CONTEXTS. The filter manager allocates variable-size contexts directly from paged or nonpaged pool.

In the Flags member of the FLT_CONTEXT_REGISTRATION structure, the FLTFL_CONTEXT_REGISTRATION_NO_EXACT_SIZE_MATCH flag can be specified. If the minifilter driver uses fixed-size contexts and this flag is specified, the filter manager allocates a context from the lookaside list if the context's size is greater than or equal to the requested size. Otherwise, the context's size must be equal to the requested size.

For a given context type, the minifilter driver can supply up to three fixed-size context definitions, each with a different size, and one variable-size definition. For more information, see FLT_CONTEXT_REGISTRATION.

The minifilter driver can optionally supply a context cleanup callback routine to be called before the context is freed. For more information, see PFLT_CONTEXT_CLEANUP_CALLBACK.

A minifilter driver can optionally define its own callback routines for allocating and freeing contexts, instead of relying on the filter manager to perform these tasks. However, this is very rarely necessary. For more information, see PFLT_CONTEXT_ALLOCATE_CALLBACK and PFLT_CONTEXT_FREE_CALLBACK.

The following code example, which is taken from the CTX sample minifilter driver, shows an array of FLT_CONTEXT_REGISTRATION structures that are used to register instance, file, stream, and file object (stream handle) contexts.

const FLT_CONTEXT_REGISTRATION contextRegistration[] =
    { FLT_INSTANCE_CONTEXT,              //ContextType
      0,                                 //Flags
      CtxContextCleanup,                 //ContextCleanupCallback
      CTX_INSTANCE_CONTEXT_SIZE,         //Size
      CTX_INSTANCE_CONTEXT_TAG           //PoolTag
    { FLT_FILE_CONTEXT,                  //ContextType
      0,                                 //Flags
      CtxContextCleanup,                 //ContextCleanupCallback
      CTX_FILE_CONTEXT_SIZE,             //Size
      CTX_FILE_CONTEXT_TAG               //PoolTag
    { FLT_STREAM_CONTEXT,                //ContextType
      0,                                 //Flags
      CtxContextCleanup,                 //ContextCleanupCallback
      CTX_STREAM_CONTEXT_SIZE,           //Size
      CTX_STREAM_CONTEXT_TAG             //PoolTag
    { FLT_STREAMHANDLE_CONTEXT,          //ContextType
      0,                                 //Flags
      CtxContextCleanup,                 //ContextCleanupCallback