How to use TDI at Dispatch Level

My bus driver loaded the USBSTOR driver on it. It has to deal with the IRPs with URBs from USBSTOR at Dispatch Level. And before compeleting the IRP, I have to use TDI to send and receive data. Some interfaces for using TDI can only work at less than Dispatch Level, like TdiBuildInternalDeviceControlIrp(). And I have to know when the transfer was finished, but I can not use KeWaitForSingleObject(), because it can not work at Dispatch Level when the timeout parameter is NULL or set to be non-zero. What can I do?

You can build all of the IRPs you need for TDI send/receive either (a) in
advance (when you open the endpoint) or (b) at IRQL <= DISPATCH_LEVEL using
IoAllocateIrp() and the TDI macros to initialize the IoStackLocation.
TdiBuildInternalDeviceControlIrp() is not required.

For receive I recommend using the event callback mechanism but of course
there is the possibility that your specific logic is better suited to IRP
completion to handle receives.

You can know when an operation finishes by allocating an extra
IoStackLocation in the IRP and using it for your own driver to set a
completion routine and context. Do the completion processing in the CRTN
instead of ‘waiting’ for the IRP to complete.

Good Luck,
Dave Cattley

-----Original Message-----
From: xxxxx@lists.osr.com
[mailto:xxxxx@lists.osr.com] On Behalf Of disney_cheng@qq.com
Sent: Saturday, December 18, 2010 7:26 AM
To: Windows System Software Devs Interest List
Subject: [ntdev] How to use TDI at Dispatch Level

My bus driver loaded the USBSTOR driver on it. It has to deal with the IRPs
with URBs from USBSTOR at Dispatch Level. And before compeleting the IRP, I
have to use TDI to send and receive data. Some interfaces for using TDI can
only work at less than Dispatch Level, like
TdiBuildInternalDeviceControlIrp(). And I have to know when the transfer was
finished, but I can not use KeWaitForSingleObject(), because it can not work
at Dispatch Level when the timeout parameter is NULL or set to be non-zero.
What can I do?


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

Thanks, David. I’ll try it tomorrow when I’m back to the office.

-----Original Message-----
You can build all of the IRPs you need for TDI send/receive either (a) in
advance (when you open the endpoint) or (b) at IRQL <= DISPATCH_LEVEL using
IoAllocateIrp() and the TDI macros to initialize the IoStackLocation.
TdiBuildInternalDeviceControlIrp() is not required.

For receive I recommend using the event callback mechanism but of course
there is the possibility that your specific logic is better suited to IRP
completion to handle receives.

You can know when an operation finishes by allocating an extra
IoStackLocation in the IRP and using it for your own driver to set a
completion routine and context. Do the completion processing in the CRTN
instead of ‘waiting’ for the IRP to complete.

Good Luck,
Dave Cattley

>TdiBuildInternalDeviceControlIrp().

Forget this ugly macro.

Among other things, it requires the threaded IRP, which is just plain stupid at the layer your code resides.

Write your own routine based on IoAllocateIrp, copy/paste the next stack location filling procedure from this macro, and use it.

After this, TDI send/receive is fine at DISPATCH_LEVEL.

Surely you cannot create the TDI file objects at DISPATCH, but IIRC (I’m not sure 100% for now) even CONNECT is fine at DISPATCH_LEVEL.


Maxim S. Shatskih
Windows DDK MVP
xxxxx@storagecraft.com
http://www.storagecraft.com