ObReferenceObjectByHandle fails when device is not in D0 state

In WDF USB driver I use ObReferenceObjectByHandle function to convert user-mode event handle to kernel-mode PKEVENT. I found that this function succeedes only if device is in D0 state. If device is not in D0 state, function returns C0000008 (incorrect handle). If I send some command to device immidiately before calling ObReferenceObjectByHandle to wake it up, this doesn’t help. But if I wake up device from user mode sending any command, and after this call command with ObReferenceObjectByHandle, it works.
Why does this happen? Possibly there is something in power management that I don’t understand.
Thanks.


Yahoo! Mail
Use Photomail to share photos without annoying attachments.

That is because there are not guarantees that any of your queue callbacks will be called in the context of the application. If you need to be in the context of the calling application, you must set an in process callback, EvtIoInCallerContext, via WdfDeviceInitSetIoInCallerContextCallback. Because you want to notify more then one application, this path is not viable anyways, but to complete the loop, I would do this

Have KMDF create a context per WDFFILEOBJECT by calling WdfDeviceInitSetFileObjectConfig(). Also register for a file cleanup routine
When you get the set event IOCTL, store the event pointer in the fileobject context as well as your device extension
In the file cleanup routine, clear the fileobject form the file object context and the device extension, make sure you are synchronized against your interrupt read completion routine

d


From: xxxxx@lists.osr.com [mailto:xxxxx@lists.osr.com] On Behalf Of Alex Farber
Sent: Tuesday, February 21, 2006 6:51 AM
To: Windows System Software Devs Interest List
Subject: [ntdev] ObReferenceObjectByHandle fails when device is not in D0 state

In WDF USB driver I use ObReferenceObjectByHandle function to convert user-mode event handle to kernel-mode PKEVENT. I found that this function succeedes only if device is in D0 state. If device is not in D0 state, function returns C0000008 (incorrect handle). If I send some command to device immidiately before calling ObReferenceObjectByHandle to wake it up, this doesn’t help. But if I wake up device from user mode sending any command, and after this call command with ObReferenceObjectByHandle, it works.
Why does this happen? Possibly there is something in power management that I don’t understand.
??? Thanks.


Yahoo! Mail
Use Photomail to share photos without annoying attachments. — Questions? First check the Kernel Driver FAQ at http://www.osronline.com/article.cfm?id=256 You are currently subscribed to ntdev as: xxxxx@microsoft.com To unsubscribe send a blank email to xxxxx@lists.osr.com

Doron, from your answer I understand that I cannot be sure that ObReferenceObjectByHandle will allways succeed even if device is in D0 state. I will try to implement EvtIoInCallerContext context, thank you very much for information.

Doron Holan wrote: That is because there are not guarantees that any of your queue callbacks will be called in the context of the application. If you need to be in the context of the calling application, you must set an in process callback, EvtIoInCallerContext, via WdfDeviceInitSetIoInCallerContextCallback. Because you want to notify more then one application, this path is not viable anyways, but to complete the loop, I would do this

Have KMDF create a context per WDFFILEOBJECT by calling WdfDeviceInitSetFileObjectConfig(). Also register for a file cleanup routine
When you get the set event IOCTL, store the event pointer in the fileobject context as well as your device extension
In the file cleanup routine, clear the fileobject form the file object context and the device extension, make sure you are synchronized against your interrupt read completion routine

d


From: xxxxx@lists.osr.com [mailto:xxxxx@lists.osr.com] On Behalf Of Alex Farber
Sent: Tuesday, February 21, 2006 6:51 AM
To: Windows System Software Devs Interest List
Subject: [ntdev] ObReferenceObjectByHandle fails when device is not in D0 state

In WDF USB driver I use ObReferenceObjectByHandle function to convert user-mode event handle to kernel-mode PKEVENT. I found that this function succeedes only if device is in D0 state. If device is not in D0 state, function returns C0000008 (incorrect handle). If I send some command to device immidiately before calling ObReferenceObjectByHandle to wake it up, this doesn’t help. But if I wake up device from user mode sending any command, and after this call command with ObReferenceObjectByHandle, it works.
Why does this happen? Possibly there is something in power management that I don’t understand.
Thanks.

Yahoo! Mail
Use Photomail to share photos without annoying attachments. — Questions? First check the Kernel Driver FAQ at http://www.osronline.com/article.cfm?id=256 You are currently subscribed to ntdev as: xxxxx@microsoft.com To unsubscribe send a blank email to xxxxx@lists.osr.com


Questions? First check the Kernel Driver FAQ at http://www.osronline.com/article.cfm?id=256

You are currently subscribed to ntdev as: unknown lmsubst tag argument: ‘’
To unsubscribe send a blank email to xxxxx@lists.osr.com

---------------------------------
Yahoo! Mail
Use Photomail to share photos without annoying attachments.

It has nothing to do with D0 state. It has everything to do with *when* you
can ObReferenceObjectByHandle.

You should *not* store the handle in you data structures, and then use
ObReferenceObjectByHandle when you feel like interacting with the handle.
The reason is that you have no idea what process context you’ll be running
in, and ObReferenceObjectByHandle operates on the handle table of the
current process. (Note: There are exceptions for kernel handles, but they
do not apply here.)

You *should* call ObReferenceObjectByHandle in IRP_MJ_DEVICE_CONTROL
dispatch handler, and store the *pointer* to the device in your data
structures. This pointer is guaranteed to be valid in all process contexts,
since it points directly to the object. Then, when you are done using the
pointer, you should call ObDereferenceObject. Otherwise, the object will
never be released.

– arlie


From: xxxxx@lists.osr.com
[mailto:xxxxx@lists.osr.com] On Behalf Of Alex Farber
Sent: Wednesday, February 22, 2006 1:28 AM
To: Windows System Software Devs Interest List
Subject: RE: [ntdev] ObReferenceObjectByHandle fails when device is not in
D0 state

Doron, from your answer I understand that I cannot be sure that
ObReferenceObjectByHandle will allways succeed even if device is in D0
state. I will try to implement EvtIoInCallerContext context, thank you very
much for information.

To further emphasize the importance of *when* convert the handle to a pointer, let me explain how the request pipe line works. By the time a WDFQUEUE related callback is invoked, you are no longer guaranteed to be in the context of the calling process. This is especially true if the request arrives to a power managed queue and the device is currently not in D0. The request will only be presented when the device is in D0 which will be in some other thread context.

EvtIoInCallerContext is guaranteed to be in the caller’s context, but there are no other guarantees. For instance, there is no guarantee about device power state at the time the function is called nor is there a guarantee that the top level queue which will process the event is even dispatching (note that you are not passed a WDFQUEUE, rather your WDFDEVICE). The only thing you should do in this callback is map Xxx (be it a handle, raw UM pointers, etc) from the caller’s context to your driver’s/request’s context area.

d

– I can spell, I just can’t type.


From: xxxxx@lists.osr.com [mailto:xxxxx@lists.osr.com] On Behalf Of Arlie Davis
Sent: Wednesday, February 22, 2006 7:15 AM
To: Windows System Software Devs Interest List
Subject: RE: [ntdev] ObReferenceObjectByHandle fails when device is not in D0 state

It has nothing to do with D0 state.? It has everything to do with *when* you can ObReferenceObjectByHandle.
?
You should *not* store the handle in you data structures, and then use ObReferenceObjectByHandle when you feel like interacting with the handle.? The reason is that you have no idea what process context you’ll be running in, and ObReferenceObjectByHandle operates on the handle table of the current process.? (Note: There are exceptions for kernel handles, but they do not apply here.)
?
You *should* call ObReferenceObjectByHandle in IRP_MJ_DEVICE_CONTROL dispatch handler, and store the *pointer* to the device in your data structures.? This pointer is guaranteed to be valid in all process contexts, since it points directly to the object.? Then, when you are done using the pointer, you should call ObDereferenceObject.? Otherwise, the object will never be released.
?
– arlie
?


From: xxxxx@lists.osr.com [mailto:xxxxx@lists.osr.com] On Behalf Of Alex Farber
Sent: Wednesday, February 22, 2006 1:28 AM
To: Windows System Software Devs Interest List
Subject: RE: [ntdev] ObReferenceObjectByHandle fails when device is not in D0 state
Doron, from your answer I understand that I cannot be sure that ObReferenceObjectByHandle? will allways succeed even if device is in D0 state. I will try to implement EvtIoInCallerContext context, thank you very much for information.


Questions? First check the Kernel Driver FAQ at http://www.osronline.com/article.cfm?id=256

You are currently subscribed to ntdev as: unknown lmsubst tag argument: ‘’
To unsubscribe send a blank email to xxxxx@lists.osr.com

Thank you for information. I moved to EvtIoInCallerContext and now conversion from HANDLE to PKEVENT always successful. I have another problem with this callback which is posted in separate question.

Doron Holan wrote: To further emphasize the importance of when convert the handle to a pointer, let me explain how the request pipe line works. By the time a WDFQUEUE related callback is invoked, you are no longer guaranteed to be in the context of the calling process. This is especially true if the request arrives to a power managed queue and the device is currently not in D0. The request will only be presented when the device is in D0 which will be in some other thread context.

EvtIoInCallerContext is guaranteed to be in the caller’s context, but there are no other guarantees. For instance, there is no guarantee about device power state at the time the function is called nor is there a guarantee that the top level queue which will process the event is even dispatching (note that you are not passed a WDFQUEUE, rather your WDFDEVICE). The only thing you should do in this callback is map Xxx (be it a handle, raw UM pointers, etc) from the caller’s context to your driver’s/request’s context area.

d

– I can spell, I just can’t type.

From: xxxxx@lists.osr.com [mailto:xxxxx@lists.osr.com] On Behalf Of Arlie Davis
Sent: Wednesday, February 22, 2006 7:15 AM
To: Windows System Software Devs Interest List
Subject: RE: [ntdev] ObReferenceObjectByHandle fails when device is not in D0 state

It has nothing to do with D0 state. It has everything to do with when you can ObReferenceObjectByHandle.

You should not store the handle in you data structures, and then use ObReferenceObjectByHandle when you feel like interacting with the handle. The reason is that you have no idea what process context you’ll be running in, and ObReferenceObjectByHandle operates on the handle table of the current process. (Note: There are exceptions for kernel handles, but they do not apply here.)

You should call ObReferenceObjectByHandle in IRP_MJ_DEVICE_CONTROL dispatch handler, and store the pointer to the device in your data structures. This pointer is guaranteed to be valid in all process contexts, since it points directly to the object. Then, when you are done using the pointer, you should call ObDereferenceObject. Otherwise, the object will never be released.

– arlie


From: xxxxx@lists.osr.com [mailto:xxxxx@lists.osr.com] On Behalf Of Alex Farber
Sent: Wednesday, February 22, 2006 1:28 AM
To: Windows System Software Devs Interest List
Subject: RE: [ntdev] ObReferenceObjectByHandle fails when device is not in D0 state
Doron, from your answer I understand that I cannot be sure that ObReferenceObjectByHandle will allways succeed even if device is in D0 state. I will try to implement EvtIoInCallerContext context, thank you very much for information.


Questions? First check the Kernel Driver FAQ at http://www.osronline.com/article.cfm?id=256

You are currently subscribed to ntdev as: unknown lmsubst tag argument: ‘’
To unsubscribe send a blank email to xxxxx@lists.osr.com


Questions? First check the Kernel Driver FAQ at http://www.osronline.com/article.cfm?id=256

You are currently subscribed to ntdev as: unknown lmsubst tag argument: ‘’
To unsubscribe send a blank email to xxxxx@lists.osr.com

---------------------------------
Yahoo! Mail
Use Photomail to share photos without annoying attachments.