Kernel-Mode Driver Framework

From Wikipedia, the free encyclopedia

The Kernel-Mode Driver Framework (KMDF) is a Microsoft-developed driver framework that was developed to make it easier for driver developers to create and maintain Kernel mode device drivers for Windows 2000[1] and later releases. It is one of the frameworks included in the Windows Driver Foundation. The current version is 1.5.

Contents

In general, KMDF supports drivers that were written for the Windows Driver Model, and it runs on WDM. WDM is the driver model used for Windows 98, Windows Me, Windows 2000 and beyond, whereas KMDF is the driver framework Microsoft is planning to use for Windows 2000 and beyond.

In general, because more features like Power Management and Plug and Play are handled by the framework, a KMDF driver is less complicated and has less code than an equivalent WDM driver.

KMDF is object based, built on top of WDM. The functionality is contained in different types of objects, KMDF implementation contains of:

Every driver starts with a DriverEntry function in Windows, DriverEntry is the driver entry point. In DriverEntry implementation, you need to instantiate your WDFDRIVER object, and tell the WDF framework where to call you back of your devices in system.

NTSTATUS DriverEntry(
   IN PDRIVER_OBJECT  DriverObject, 
   IN PUNICODE_STRING  RegistryPath
   )
{
 WDF_DRIVER_CONFIG config;
 NTSTATUS status = S_OK;

 KdPrint((__DRIVER_NAME "DriverEntry Begin\n"));

 WDF_DRIVER_CONFIG_INIT(&config, EvtDeviceAdd);
 status = WdfDriverCreate(
                     DriverObject,
                     RegistryPath,
                     WDF_NO_OBJECT_ATTRIBUTES,
                     &config, // Pointer to config structure
                     WDF_NO_HANDLE); // or NULL, Pointer to get WDFDRIVER handle
 if(!NT_SUCCESS(status))
 {
   KdPrint((__DRIVER_NAME "WdfDriverCreate failed with status 0x%08x\n", status));
 }

 KdPrint((__DRIVER_NAME "DriverEntry End\n"));

 return status;
}

In Framework, EvtDeviceAdd event is called from the PnP manager with a handle to our WDFDRIVER object, and a pointer to a WDFDEVICE_INIT structure. Before the device created, the driver needs to configure the device initialization.

WDFSTATUS DioEvtDeviceAdd(WDFDRIVER Driver, PWDFDEVICE_INIT DeviceInit)
{
 WDFSTATUS status = STATUS_SUCCESS;
 WDF_PNPPOWER_EVENT_CALLBACKS pnpPowerCallbacks;
 WDF_OBJECT_ATTRIBUTES objAttributes;
 WDFDEVICE device;
 PDIO_DEVICE_CONTEXT devContext;
 WDF_IO_QUEUE_CONFIG ioCallbacks;
 WDF_INTERRUPT_CONFIG interruptConfig;
 WDF_DEVICE_POWER_POLICY_IDLE_SETTINGS idleSettings;

 WDF_PNPPOWER_EVENT_CALLBACKS_INIT(&pnpPowerCallbacks);
 pnpPowerCallbacks.EvtDevicePrepareHardware = DioEvtPrepareHardware;
 pnpPowerCallbacks.EvtDeviceReleaseHardware = DioEvtReleaseHardware;
 pnpPowerCallbacks.EvtDeviceD0Entry= DioEvtDeviceD0Entry;
 pnpPowerCallbacks.EvtDeviceD0Exit = DioEvtDeviceD0Exit;
 
 WdfDeviceInitSetPnpPowerEventCallbacks(DeviceInit, pnpPowerCallbacks);

 WDF_OBJECT_ATTRIBUTES_INIT(&objAttributes);

 WDF_OBJECT_ATTRIBUTES_SET_CONTEXT_TYPE(&objAttributes, DIO_DEVICE_CONTEXT);

 status = WdfDeviceInitUpdateName(DeviceInit, L"\\device\\WDFDIO");

 status = WdfDeviceCreate(&DeviceInit,    // Device Init structure
                          &objAttributes, // Attributes for WDF Device
                          &device);       // return new WDF Device pointer, 

 devContext = DioGetContextFromDevice(device); // Get device extension

 devContext->WdfDevice = device;

 // Create a symbolic link for the control object 
 status = WdfDeviceCreateSymbolicLink(device, L"\\DosDevices\\WDFDIO");

 WDF_IO_QUEUE_CONFIG_INIT(&ioCallbacks,
                            WdfIoQueueDispatchSerial,
                            WDF_NO_EVENT_CALLBACK,     // StartIo
                            WDF_NO_EVENT_CALLBACK);    // CancelRoutine

 ioCallbacks.EvtIoDeviceControl = DioEvtDeviceControlIoctl;
 status = WdfDeviceCreateDefaultQueue(device,
                                       &ioCallbacks,
                                       WDF_NO_OBJECT_ATTRIBUTES,
                                       NULL); // pointer to default queue

 WDF_INTERRUPT_CONFIG_INIT(&interruptConfig,       // Configure the Interrupt object
                           DioIsr,                 // ISR
                           DioDpc);                // Deferred Procedure Call

 interruptConfig.EvtInterruptEnable  = DioEvtInterruptEnable;
 interruptConfig.EvtInterruptDisable = DioEvtInterruptDisable;

 status = WdfInterruptCreate(device,
                             &interruptConfig,
                             &objAttributes,
                             &devContext->WdfInterrupt);
 
 WDF_DEVICE_POWER_POLICY_IDLE_SETTINGS_INIT(&idleSettings,  // Initialize idle policy
                                             IdleCannotWakeFromS0);

 status = WdfDeviceUpdateS0IdleSettings(device, &idleSettings);

 return status;
}

If the EvtDeviceAdd function has succeeded, EvtDevicePrepareHardware is the next function, to make sure that the driver can access the hardware, that will be called by the framework.

NTSTATUS EvtDevicePrepareHardware(
   IN WDFDEVICE    Device,
   IN WDFCMRESLIST ResourceList,
   IN WDFCMRESLIST ResourceListTranslated
   )
{
 NTSTATUS status = STATUS_SUCCESS;

 UNREFERENCED_PARAMETER(Device);
 UNREFERENCED_PARAMETER(ResourceList);
 UNREFERENCED_PARAMETER(ResourceListTranslated);

 return status;
}

EvtDeviceD0Entry is first called, after EvtDevicePrepareHardware has been called. EvtDeviceD0Entry function is responsible for starting the activities that the driver is supposed to perform. The EvtDeviceD0Exit function performs actions that are the opposite of the EvtDeviceD0Entry function.

NTSTATUS EvtDeviceD0Entry(
   IN WDFDEVICE  Device,
   IN WDF_POWER_DEVICE_STATE  PreviousState
   )
{
 NTSTATUS status = STATUS_SUCCESS;
 
 return status;
}

NTSTATUS EvtDeviceD0Exit(
   IN WDFDEVICE  Device,
   IN WDF_POWER_DEVICE_STATE  TargetState
   )
{
 NTSTATUS status = STATUS_SUCCESS;

 return status;
}

There is only one IO handler was registered, EvtDeviceIoDefault would be built , when default IO queue was created. The EvtDeviceIoDefault function will accept any request, and will fail because no IO functionality has yet been implemented.

VOID EvtDeviceIoDefault(
   IN WDFQUEUE  Queue,
   IN WDFREQUEST  Request
   )
{
 WdfRequestComplete(Request, STATUS_NOT_IMPLEMENTED);
}

  1. ^ The original release of KMDF only supported Windows XP and Server 2003. Support for Windows 2000 was added in KMDF version 1.1.

Advanced Search
Included Web Search Engines


Safe Search

close

Top Matching Results

Occasionally Search.com will highlight specialized results that are based on the context of your query. Examples of specialized results include specific links to news, images, or video.

Top Matching Results may highlight information from other Search.com pages, content from the CNET Network of sites, or third party content. The listings are based purely on relevance. Search.com does not receive payment for listings in this section but our partners that provide this data may get paid for listing these products.

Sponsored Links

This section contains paid listings which have been purchased by companies that want to have their sites appear for specific search terms and related content. These listings are administered, sorted and maintained by a third party and are not endorsed by Search.com.

Search Results

Search.com sends your search query to several search engines at one time and integrates the results into one list which has been sorted by relevance using Search.com's proprietary algorithm. You can customize the list of search engines included in your metasearch from the preferences.

The search engines that are used in your metasearch may allow companies to pay to have their Web sites included within the results. To view the Paid Inclusion policy for a specific search engine, please visit their Web site. Search.com does not accept payment or share revenue with any search engine partner for listings in this section.