howto allow user process to modify IRP_MJ_READ buffers?

I need to move some functionality out of my filter driver and into a
helper application.

I know how to map some locked kernel memory out to a user process via
IoAllocateMdl, MmBuildMdlForNonPagedPool, and MmMapLockedPages. A
more-or-less standard way to share some data buffer between a driver and
an application.

Given a buffer presented in an IRP_MJ_READ call to a file system filter
driver, is it possible to do the same with said buffer and make it
accessible to a helper application for modification? In the NON_PAGED I/O
case, even for the filter to access the read buffer, it requires an
IoAllocateMdl and MmProbeAndLockPages, but I understand that in the
PAGING_IO case we already have a valid MDL but cannot probe/lock those
pages.

In either case, the end result is a valid system address for the filter to
access the read buffer via MmGetSystemAddressForMdlSafe. How should I go
efficiently (and safely) from that system address to one accessible to the
helper application? This would be done in the helper’s context, say
during an event-triggered ioctl callback.

I never tried shared memory in DD and UM, so I won’t try to answer that.
Just let me remind you that paging read ALMOST always occur at APC_LEVEL.
Be prepared to handle that!

Bill wrote:

I need to move some functionality out of my filter driver and into a
helper application.

I know how to map some locked kernel memory out to a user process via
IoAllocateMdl, MmBuildMdlForNonPagedPool, and MmMapLockedPages. A
more-or-less standard way to share some data buffer between a driver and
an application.

Given a buffer presented in an IRP_MJ_READ call to a file system filter
driver, is it possible to do the same with said buffer and make it
accessible to a helper application for modification? In the NON_PAGED I/O
case, even for the filter to access the read buffer, it requires an
IoAllocateMdl and MmProbeAndLockPages, but I understand that in the
PAGING_IO case we already have a valid MDL but cannot probe/lock those
pages.

In either case, the end result is a valid system address for the filter to
access the read buffer via MmGetSystemAddressForMdlSafe. How should I go
efficiently (and safely) from that system address to one accessible to the
helper application? This would be done in the helper’s context, say
during an event-triggered ioctl callback.


You are currently subscribed to ntfsd as: xxxxx@alfasp.com
To unsubscribe send a blank email to xxxxx@lists.osr.com


Kind regards, Dejan M. www.alfasp.com
E-mail: xxxxx@alfasp.com ICQ#: 56570367
Alfa File Monitor - File monitoring library for Win32 developers.
Alfa File Protector - File protection and hiding library for Win32 developers.

> IoAllocateMdl and MmProbeAndLockPages, but I understand that in the

PAGING_IO case we already have a valid MDL but cannot probe/lock
those

MDLs for paging IO are built by MM. Not all MDL-related functions are
available on them.

Max

OK. I hear the cautionary note, but that leaves me confused… The
traditional way of handling any filter read manipulations is to set a
completion routine and either do the work there or back in the dispatch
routine after the read completes. Either way, the dispatch routine must
wait for a signal from the completion routine. Since you cannot
KeWaitForSingleObject (with a non-zero timeout) above PASSIVE_LEVEL, how
can it be that PAGING reads come in at APC_LEVEL? I’m doing this
completion wait today, and it is working rock solid. Or, am I missing
something else really obvious? (Wouldn’t be the first time! :wink:

I never tried shared memory in DD and UM, so I won’t try to answer that.
Just let me remind you that paging read ALMOST always occur at APC_LEVEL.
Be prepared to handle that!
I never tried shared memory in DD and UM, so I won’t try to answer that.
Just let me remind you that paging read ALMOST always occur at APC_LEVEL.
Be prepared to handle that!

Hi Max,
I understand that. For paging I/O requests I simply use the MDL that was
passed to me as an argument to MMGetSystemAddressForMdlSafe. For
non-paging, I alloc my ownl MDL, probe and lock, then call
MmGetSystemAddressblahblah. I use these kernel mode addresses in my
completion routine to access the read data after the file system has
copied it out.

So, the question really is… What is the protocol for converting the
kernel address I have to an address suitable for use in a given Ring 3
context. Assuming I wait to do the mapping until called from that
context, is it as simple as MmMapLockedPages since, if the
mmGetSystemAddressForMdlSafe succeeded, the input MDL to that call now
represents non paged pool addresses?

MDLs for paging IO are built by MM. Not all MDL-related functions are
available on them.

Max

FastFat quite happily calls KeWaitForSingleObject at APC_LEVEL on line
196 of read.cpp, where it posts paging file I/O to an overflow thread
and waits on the result. But if you don’t absolutely have to do it, I
wouldn’t, because it is technically prohibited in the
KeWaitForSingleObject docs. Waiting at APC_LEVEL means the current
thread won’t be available for processing APCs of any kind, which could
delay completion of IRPs (but your completion routine will still be
called since it doesn’t require original thread context to execute).

  • Nicholas Ryan

-----Original Message-----
From: xxxxx@lists.osr.com
[mailto:xxxxx@lists.osr.com] On Behalf Of Bill
Sent: Monday, January 27, 2003 10:15 AM
To: File Systems Developers
Subject: [ntfsd] Re: howto allow user process to modify
IRP_MJ_READ buffers?

OK. I hear the cautionary note, but that leaves me
confused… The traditional way of handling any filter read
manipulations is to set a completion routine and either do
the work there or back in the dispatch routine after the read
completes. Either way, the dispatch routine must wait for a
signal from the completion routine. Since you cannot
KeWaitForSingleObject (with a non-zero timeout) above
PASSIVE_LEVEL, how can it be that PAGING reads come in at
APC_LEVEL? I’m doing this completion wait today, and it is
working rock solid. Or, am I missing something else really
obvious? (Wouldn’t be the first time! :wink:

> I never tried shared memory in DD and UM, so I won’t try to
answer that.
> Just let me remind you that paging read ALMOST always occur at
> APC_LEVEL. Be prepared to handle that! I never tried shared
memory in
> DD and UM, so I won’t try to answer that.
> Just let me remind you that paging read ALMOST always occur at
> APC_LEVEL. Be prepared to handle that!


You are currently subscribed to ntfsd as: xxxxx@nryan.com
To unsubscribe send a blank email to xxxxx@lists.osr.com

Aside from the usual, APCs cannot be delivered to the thread, you also cannot
query the file system for file information - this will certainly lead to a
deadlock.

Bill wrote:

OK. I hear the cautionary note, but that leaves me confused… The
traditional way of handling any filter read manipulations is to set a
completion routine and either do the work there or back in the dispatch
routine after the read completes. Either way, the dispatch routine must
wait for a signal from the completion routine. Since you cannot
KeWaitForSingleObject (with a non-zero timeout) above PASSIVE_LEVEL, how
can it be that PAGING reads come in at APC_LEVEL? I’m doing this
completion wait today, and it is working rock solid. Or, am I missing
something else really obvious? (Wouldn’t be the first time! :wink:

> I never tried shared memory in DD and UM, so I won’t try to answer that.
> Just let me remind you that paging read ALMOST always occur at APC_LEVEL.
> Be prepared to handle that!
> I never tried shared memory in DD and UM, so I won’t try to answer that.
> Just let me remind you that paging read ALMOST always occur at APC_LEVEL.
> Be prepared to handle that!


You are currently subscribed to ntfsd as: xxxxx@alfasp.com
To unsubscribe send a blank email to xxxxx@lists.osr.com


Kind regards, Dejan M. www.alfasp.com
E-mail: xxxxx@alfasp.com ICQ#: 56570367
Alfa File Monitor - File monitoring library for Win32 developers.
Alfa File Protector - File protection and hiding library for Win32 developers.

If you will use IoAllocateIrp for a query - why not?

----- Original Message -----
From: “Dejan Maksimovic”
To: “File Systems Developers”
Sent: Monday, January 27, 2003 11:02 PM
Subject: [ntfsd] Re: howto allow user process to modify IRP_MJ_READ
buffers?

>
> Aside from the usual, APCs cannot be delivered to the thread,
you also cannot
> query the file system for file information - this will certainly
lead to a
> deadlock.
>
> Bill wrote:
>
> > OK. I hear the cautionary note, but that leaves me confused…
The
> > traditional way of handling any filter read manipulations is to
set a
> > completion routine and either do the work there or back in the
dispatch
> > routine after the read completes. Either way, the dispatch
routine must
> > wait for a signal from the completion routine. Since you cannot
> > KeWaitForSingleObject (with a non-zero timeout) above
PASSIVE_LEVEL, how
> > can it be that PAGING reads come in at APC_LEVEL? I’m doing this
> > completion wait today, and it is working rock solid. Or, am I
missing
> > something else really obvious? (Wouldn’t be the first time! :wink:
> >
> > > I never tried shared memory in DD and UM, so I won’t try to
answer that.
> > > Just let me remind you that paging read ALMOST always occur
at APC_LEVEL.
> > > Be prepared to handle that!
> > > I never tried shared memory in DD and UM, so I won’t try to
answer that.
> > > Just let me remind you that paging read ALMOST always occur
at APC_LEVEL.
> > > Be prepared to handle that!
> >
> > —
> > You are currently subscribed to ntfsd as: xxxxx@alfasp.com
> > To unsubscribe send a blank email to
xxxxx@lists.osr.com
>
> –
> Kind regards, Dejan M. www.alfasp.com
> E-mail: xxxxx@alfasp.com ICQ#: 56570367
> Alfa File Monitor - File monitoring library for Win32 developers.
> Alfa File Protector - File protection and hiding library for Win32
developers.
>
>
>
>
>
>
>
> —
> You are currently subscribed to ntfsd as: xxxxx@storagecraft.com
> To unsubscribe send a blank email to xxxxx@lists.osr.com
>

Just try it - I don’t know why, but it will happen under lower stress
situations.

“Maxim S. Shatskih” wrote:

If you will use IoAllocateIrp for a query - why not?


Kind regards, Dejan M. www.alfasp.com
E-mail: xxxxx@alfasp.com ICQ#: 56570367
Alfa File Monitor - File monitoring library for Win32 developers.
Alfa File Protector - File protection and hiding library for Win32
developers.