question about async io on sync IRP_MJ_READ/WRITE implementation

Hi guys, i have a third part device driver with IRP_MJ_READ/WRITE implemented in sync way, e.g. reads and writes are completed in dispatch routine directly without being marked as pending. Can i somehow access it with overlapped ReadFile/WriteFile for async I/O?

Yes, sure. But you’re overlapped I/Os will all be serviced synchronously, so you’ll never get back “in progress” as a status.

You could fix this with a filter driver, if you were desperate enough…

Peter

@“Peter_Viscarola_(OSR)” said:
Yes, sure. But you’re overlapped I/Os will all be serviced synchronously, so you’ll never get back “in progress” as a status.

You could fix this with a filter driver, if you were desperate enough…

Peter

Thank you Peter, you mean overlapped ReadFile/WriteFile won’t return until I/O completes, right? But i need them to return immediately with pending status so that it does not block caller.

But i need them to return immediately with pending status

Yeah, well… if the driver doesn’t work properly, there’s nothing you can do to make it do so. Except, as I said, write a filter driver that sits above the errant driver and makes the Request asynchronous.

Peter

Thank you Peter, you mean overlapped ReadFile/WriteFile won’t return until I/O completes, right?

Yes. The driver dispatch routines always run on the user mode process’ thread. It’s just a series of function calls, one of which happens to shift into kernel mode. Nothing can continue until the dispatch routine returns and the call stack unwinds back to you.

This is even true with drivers that do asynchronous properly. The dispatch routines still run on the user thread until they queue up the IRP and return STATUS_PENDING, at which point the stack unwinds back to the original caller. The difference with overlapped is that, without overlapped, the unwind gets blocked in the I/O manager until the IRP shows “complete”. With overlapped, it unwinds back to the caller right away.

1 Like

Just to put a fine point on this: “driver dispatch routines” in Mr. Roberts’ reply, above, literally means “WDM driver dispatch routines.”

This does not apply to KMDF, which reserves the right to post your Requests, return STATUS_PENDING to the caller, and call your EvtIoXxx Event Processing Callbacks “whenever” and in an arbitrary process and thread context.

Peter

If you are choosing between changing the application to handle the sync io or adding the filter driver to force async io, I would strongly recommend you update the app. Since you want async io, I have to assume the app already handles async I/O so it should be relatively simple to move the ReadFile/WriteFile calls to a thread pool request (CreateThreadpoolIo and friends) and keep the app’s wait for IO to complete logic the same.

@Doron_Holan

That’s actually quite a clever solution. “Simple” change to the user-mode code. I mean, I’m not saying it’s not UGLY. But it’s a whole lot more practical that actually writing a filter driver JUST to post the Request.

Peter

Thank you for your explainations guys, very helpful.