The Selective Suspend driver
- The selective suspend driver is a generic function driver based on the
Windows Driver Model (WDM).
- Supports Plug and Play(PnP), Power
Management(PM), Windows Management Instrumentation (WMI) and the Selective
Suspend (SS) features.
- The support for PnP, PM and the WMI feature
is essential for any driver based on the WDM model.
- The SS feature, described in detail later, is
a new feature in the core USB stack.
Plug and Play
- The Plug and Play system allows for dynamic
recognition of installed hardware and configuration of resources.
- The selective suspend driver (function
driver) registers a dispatch routine to receive and process PnP requests
from the PnP manager.
- In the dispatch routine, the driver examines
the minor function of the PnP requests and delegates them for further
processing.
Please refer the Windows XP DDK docs and the Toaster sample in the DDK to
understand the kernel-driver responsibilities and handling of PnP requests.
- The selective suspend driver has the
following delegate-routines to process the PnP requests.
IRP_MN_START_DEVICE |
HandleStartDevice() |
IRP_MN_QUERY_STOP_DEVICE |
HandleQueryStopDevice() |
IRP_MN_CANCEL_STOP_DEVICE |
HandleCancelStopDevice() |
IRP_MN_STOP_DEVICE |
HandleStopDevice() |
IRP_MN_QUERY_REMOVE_DEVICE |
HandleQueryRemoveDevice() |
IRP_MN_CANCEL_REMOVE_DEVICE |
HandleCancelRemoveDevice() |
IRP_MN_SURPRISE_REMOVAL |
HandleSurpriseRemoval() |
IRP_MN_REMOVE_DEVICE |
HandleRemoveDevice() |
IRP_MN_QUERY_CAPABILITIES |
HandleQueryCapabilities() |
Power Management
- The power manager is the global power-policy owner for the system and the
devices.
- The selective suspend driver registers a dispatch routine to receive and
process power requests.
- In the dispatch routine, the driver examines the minor function of the
power requests and delegates them for further processing.
- Please refer the Windows XP DDK docs and the Toaster sample in the DDK to
understand the kernel-driver responsibilities and handling of power requests.
IRP_MN_QUERY_POWER(SystemPowerState) |
HandleSystemQueryPower() |
IRP_MN_QUERY_POWER(DevicePowerState) |
HandleDeviceQueryPower() |
IRP_MN_SET_POWER (DevicePowerState) |
HandleDeviceSetPower() |
IRP_MN_SET_POWER (SystemPowerState) |
HandleSystemSetPower() |
Remote Wakeup capability
The selective suspend driver supports the remote wakeup capability. The
routines which implement this capability are:
IssueWaitWake()
WaitWakeCallback()
WaitWakeCompletionRoutine()
- After the device is configured and is in a D0 power state, the selective
suspend driver requests an IRP_MN_WAIT_WAKE
request for the device - IssueWaitWake.
- A pointer to the callback function in the driver, WaitWakeCallback,
is passed along this request.
- The wait-wake request is sent to the PDO for the driver.
- When this request is received by the selective
suspend driver , the dispatch routine sets a completion routine, WaitWakeCompletionRoutine,
for this request.
- The request is then passed down the stack.
- The request remains pending with the hub driver until completed by the hub
driver.
- On resume signaling, the wait wake request is completed and the callback
function is invoked.
The WaitWakeCallback routine powers up the
device and issues a new wait-wake request for the device.
- The wait wake request should not be sent when the device is in a low power
state.
Selective Suspend feature
The USB core stack supports a new feature called the selective suspend
feature. This feature allows the driver to power down the device while the
system remains in the S0 power state.
- The device driver "observes" that the device is idle and sends
an idle request down the stack - SubmitIdleRequestIrp.
The exact notion of the device in idle
state is
described in the selective suspend model section.
- A pointer to the callback function in the driver, IdleNotificationCallback,
is passed along with it.
- The driver also sets a completion routine, IdleNotificationRequestComplete
for this request.
- The hub driver pends this idle request for the device.
- When the hub "deems it appropriate" to selectively suspend the
device, the callback function IdleNotificationCallback
is invoked.
This function powers down the device. The device is powered down to
the DeviceWake
state (initialized while handling the IRP_MN_QUERY_CAPABILITIES).
If the DeviceWake state is not known, then
the device should power down to the D2 power state.
Notes
- Since the hub invokes the callback function, IdleNotificationCallback,
only when it deems appropriate, the function driver should never assume that
the device will power down as soon as the idle request is sent down the
stack.
- Since it is not appropriate to send requests down the stack when the
device is in low power state,
the function driver should send an idle request only when the device is in D0
power state.
- As soon as the device is "not idle", the driver should cancel
the idle request - CancelSelectSuspend.
- No assumptions should be made on the completion of idle request. If the
driver needs to pass requests (reads/writes/ioctls) down the stack, then the
driver should wait for the idle request to complete before proceeding to
submit one.
- If the idle request completes in error, the IdleNotificationRequestComplete
powers
up the device.
- Only one idle request can be pending for the device at any time.
Selective Suspend model
- The selective suspend driver interprets the device as idle when
a) there are no open handles to the device and
b) no PnP requests are being processed.
This is a mere suggestion. A function driver may have a different
interpretation of the idle state.
As an example, an open handle need not violate the idle state of the device
if this does not cause any request to be sent down the stack.
- The selective suspend driver initializes a timer to fire at fixed
intervals.
- The DPC associated with the timer checks the idle state of the device and
queues a work item to submit an idle request for the device.
- The timer is cancelled when the idle request is passed down the stack.
- The timer is re-initialized when the idle request completes.
Please refer the inline comments in the selSusp sample for implementation of
the above suggestions.