Getting legacy driver to support Power Management

Hi,

I’m working on getting an old legacy XP Embedded driver
to support Standby and Hibernate states. In particular,
the Start\Shutdown menu needs to have the “Stand by” option.

The driver started off life as an NT Embedded driver, based
on the old (1991?) atdisk.c code and it is used to provide
a proprietary interface to some Flash memory and other things.
The code calls IoCreateController, and then uses the
associated device extension to store its private information.

The driver had an AddDevice function which gets called
with a PDO with a DeviceType of FILE_DEVICE_CONTROLLER.
The original code ignored the PDO and returned success.
I created an FDO and called IoAttachDeviceToDeviceStack,
having first cleared the DO_DEVICE_INITIALIZING flag bit.

After creating the FDO, the PNP dispatch code is now
getting called. I assumed that informing XP of power
mapping and other support via the DeviceCapabilities
struct in IRP_MN_QUERY_CAPABILITES, as well as adding
support for IRP_MJ_POWER, would be enough to persuade
XP that the driver could go into StandBy mode.

I can see the effect of the DeviceCapabilities data being
returned in the Device Manager. Selecting the device,
then Properties\Details, the “Power State Mappings”
pane shows the Dx to Sx mappings that were returned
in the IRP_MN_QUERY_CAPABILITES call.

However, the IRP_MJ_POWER dispatch function is never
getting called and Shutdown doesn’t have a StandBy selection.
If the driver is disabled, StandBy is an option.

Any suggestions on where to look for reasons as to why
the IRP_MJ_POWER dispatch code is not getting called?

Also, is there something else that needs to occur in
order to get XPe to treat the driver as supporting
power management and therefore enable StandBy mode?

Thanks!

++ Todd

I don’t really know if it suits your purposes, but you can simply rewrite your whole driver using KMDF, so that all PnP and power-related issues will be solved by the framework…

Anton Bassov

Thanks but the client is unlikely to support that option. Multiple
reasons covered by a NDA. And this client likes the Golden Rule:
He who has the gold makes the rules…

++ Todd

test

Adding support for IRP_MJ_POWER is not enough to support power. You must also support IRP_MJ_PNP and all of the state changing IRPs as well. After that, you will have to add support for queueing and restarting i/o on power and pnp state transitions which is also no small task. In the end if the majority of your driver is processing io and programming hw, the port to KMDF will be rather trivial and nearly all of your driver will remain the same.

Are you sure your AddDevice being called at all? If not, the OS is still considering your driver to be legacy. Also remember to remove all of the HAL calls to find/query your resources.

d

-----Original Message-----
From: xxxxx@lists.osr.com [mailto:xxxxx@lists.osr.com] On Behalf Of xxxxx@pioneercomputing.com
Sent: Saturday, September 22, 2007 9:47 PM
To: Windows System Software Devs Interest List
Subject: RE:[ntdev] Getting legacy driver to support Power Management

Thanks but the client is unlikely to support that option. Multiple
reasons covered by a NDA. And this client likes the Golden Rule:
He who has the gold makes the rules…

++ Todd


NTDEV is sponsored by OSR

For our schedule of WDF, WDM, debugging and other seminars visit:
http://www.osr.com/seminars

To unsubscribe, visit the List Server section of OSR Online at http://www.osronline.com/page.cfm?name=ListServer

>I created an FDO and called IoAttachDeviceToDeviceStack,

having first cleared the DO_DEVICE_INITIALIZING flag bit.

It it all that you do with flags??? I think if you don’t set either DO_POWER_PAGABLE or DO_POWER_INRUSH flag in your device flags (actually, on Vista you can even set them both, which is not permitted on earlier OS versions), power manager is just not going to send IRP_MJ_POWER requests to your device…

Anton Bassov

Thanks for the replies – I appreciate your support.

I’d implemented support for PNP Irps as well as Power and
state changing Irps, but nothing was getting called. It wasn’t
until I noticed that the original AddDevice code was ignoring
the PDO and fixed that by creating a new FDO & adding it to the
device stack, that I started to get calls into the PNP dispatch code.

No, the driver was not setting the DO_POWER_PAGABLE bit.
I must need new glasses – that is plain as day in the MSDN docs.
I will check that out tomorrow. The embedded device is having
issues booting and I’m waiting for a new device to be shipped.

++ Todd

> It wasn’t until I noticed that the original AddDevice code was ignoring

the PDO and fixed that by creating a new FDO & adding it to the device stack,

Hold on - in your original you said that you call IoAttachDeviceToDeviceStack() with your FDO in AddDevice(). If you ignored PDO that get passed to your AddDevice(), what on Earth (or maybe, even on another planet) were you attaching your FDO to???

Anton Bassov

> Hold on - in your original you said that you call IoAttachDeviceToDeviceStack()

with your FDO in AddDevice(). If you ignored PDO that get passed to your
AddDevice(), what on Earth (or maybe, even on another planet) were you attaching
your FDO to???

Sorry if I wasn’t clear. The original code (before I got it) had an AddDevice function,
which essentially ignored the PDO. When I saw that situation, I added code
to create a FDO, which then called IoAttachDeviceToDeviceStack(fdo, pdo).

The original code created several device objects in the DriverEntry function.
It attempted to find one of those objects and use that in conjunction with the
pdo, but only if the pdo was of DeviceType FILE_DEVICE_DISK. This never
happened (which was probably a very good thing) as the pdo is a
FILE_DEVICE_CONTROLLER. So, the pdo was ignored. My guess is
that as a Legacy driver, it was able to limp along.

This driver was originally an NT Embedded driver, and has had a dozen folks
work on it over the years. It even used to work on a Windows CE system;
the conditional compilation definitions are abysmal. And then there’s
the code where someone tried to get it to be a Linux driver as well;
the debris is still scattered throughout the code. Without a good editor
like Source Insight, I would have been lost.

++ Todd

Someone tried to make a NT driver run on Linux after the fact? I feel for you. I couldn’t agree more about the value of a good editor (I’m not familiar with Source Insight; I use SlickEdit), particularly when it comes to source code with a lot of conditional compilation.

Good luck,

mm

xxxxx@evitechnology.com wrote:

Someone tried to make a NT driver run on Linux after the fact? I feel for you.

It’s been done before. NDIS was pretty easy (after all, it was designed
to be OS independent), and there is a wrapper that lets some video
capture drivers work as well.


Tim Roberts, xxxxx@probo.com
Providenza & Boekelheide, Inc.

I’m not surprised that it is possible, but I am sort of surprised that it is profitable/efficient, assuming that these two you mentioned are implemented in the same way as the dev’s driver - code added after the fact and conditional compilation all over the place. That’s the reason I feel for the guy. I just find large scale use of conditional compilation thoroughly unenjoyable and confusing.

Thanks for the support – multiple levels of conditional compilation
is quite unenjoyable. However, we do what we need to do to
get the job done. I try to remember to wash my hands afterwards.

I got the driver to limp along and support Standby and Hibernation.
After I fixed the DO_POWER_PAGABLE issue, it still failed. Eventually
I found an old ntdev forum post from Maxim Shatskih which said
that power management was disabled by using IoAssignResources.
Some other portion of the driver was using this call and the data
it returned to get a physical address that, once upon a time, was
used as a backup address (per the comments) for doing some of
the proprietary work in the driver.

Thanks to all for your comments, support and suggestions!

++ Todd