NO_MORE_IRP_STACK_LOCATIONS

Hi,

We have a filter device driver for encryption that works OK.
On a single customer machine with Windows 2000 service pack 4 that has
symantec corporate 7.6 installed, we get an NO_MORE_IRP_STACK_LOCATIONS
whenever he tries to use a USB flash disk.
If I debug the system, I see that the IRP that causes the crash has only 4
stack locations (that were all exhausted).
Disabling the symantec driver solves the problem (and also when disabling
my driver).

My question is why there are so few stack locations to begin with, and
whether there is an option to increase the number.

I also tried to put some ‘safety’ code in my driver that will check when
the no. of available stack locations is too low and if so, performs an
IoSkipCurrentIrpStackLocation. This helped somewhat but the system still
crashed.

Aha! I had this particular problem. What i did was check if
Irp->CurrentLocation == 1 and just return and error.
This happened though ONLY if I had EXACTLY 4 FS filter installed (doesn’t
matter which ones).
I’ve done weeks of testing on this, and finally gave up - taking it as a
3rd party bug. (Not related to NAV)

Regards, Dejan.

xxxxx@aliroo.com wrote:

Hi,

We have a filter device driver for encryption that works OK.
On a single customer machine with Windows 2000 service pack 4 that has
symantec corporate 7.6 installed, we get an NO_MORE_IRP_STACK_LOCATIONS
whenever he tries to use a USB flash disk.
If I debug the system, I see that the IRP that causes the crash has only 4
stack locations (that were all exhausted).
Disabling the symantec driver solves the problem (and also when disabling
my driver).

My question is why there are so few stack locations to begin with, and
whether there is an option to increase the number.

I also tried to put some ‘safety’ code in my driver that will check when
the no. of available stack locations is too low and if so, performs an
IoSkipCurrentIrpStackLocation. This helped somewhat but the system still
crashed.


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. MVP for DDK
http://www.alfasp.com E-mail: xxxxx@alfasp.com
Alfa Transparent File Encryptor - Transparent file encryption services.
Alfa File Protector - File protection and hiding library for Win32 developers.

Alfa File Monitor - File monitoring library for Win32 developers.

My safety code was even more histerical:

BOOLEAN HaveEnoughIrpLocations(IN PIRP Irp)
{
if(Irp->CurrentLocation < 4) {
return FALSE;
}
return TRUE;
}

and in various handlers:

if (!HaveEnoughIrpLocations(Irp)) {
IoSkipCurrentIrpStackLocation( Irp );
return IoCallDriver( FileSystemDeviceObject, Irp );
}

Still, although the crash was postponed, it finally did happen.
You suggest then to fail the request (with what code ?) instead of passing
it through ?

Rami

Aha! I had this particular problem. What i did was check if
Irp->CurrentLocation == 1 and just return and error.
This happened though ONLY if I had EXACTLY 4 FS filter installed (doesn’t
matter which ones).
I’ve done weeks of testing on this, and finally gave up - taking it as a
3rd party bug. (Not related to NAV)

Regards, Dejan.

xxxxx@aliroo.com wrote:

> Hi,
>
> We have a filter device driver for encryption that works OK.
> On a single customer machine with Windows 2000 service pack 4 that has
> symantec corporate 7.6 installed, we get an NO_MORE_IRP_STACK_LOCATIONS
> whenever he tries to use a USB flash disk.
> If I debug the system, I see that the IRP that causes the crash has only 4
> stack locations (that were all exhausted).
> Disabling the symantec driver solves the problem (and also when disabling
> my driver).
>
> My question is why there are so few stack locations to begin with, and
> whether there is an option to increase the number.
>
> I also tried to put some ‘safety’ code in my driver that will check when
> the no. of available stack locations is too low and if so, performs an
> IoSkipCurrentIrpStackLocation. This helped somewhat but the system still
> crashed.
>
> —
> 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. MVP for DDK
http://www.alfasp.com E-mail: xxxxx@alfasp.com
Alfa Transparent File Encryptor - Transparent file encryption services.
Alfa File Protector - File protection and hiding library for Win32 developers.

Alfa File Monitor - File monitoring library for Win32 developers.

If you simply do this there is NOTHING you do except not doing whatever your
driver is supposed to do:-)
You have to fail the request. STATUS_INVALID_DEVICE_REQUEST is what I’d suggest.

xxxxx@aliroo.com wrote:

My safety code was even more histerical:

BOOLEAN HaveEnoughIrpLocations(IN PIRP Irp)
{
if(Irp->CurrentLocation < 4) {
return FALSE;
}
return TRUE;
}

and in various handlers:

if (!HaveEnoughIrpLocations(Irp)) {
IoSkipCurrentIrpStackLocation( Irp );
return IoCallDriver( FileSystemDeviceObject, Irp );
}

Still, although the crash was postponed, it finally did happen.
You suggest then to fail the request (with what code ?) instead of passing
it through ?

Rami

> Aha! I had this particular problem. What i did was check if
> Irp->CurrentLocation == 1 and just return and error.
> This happened though ONLY if I had EXACTLY 4 FS filter installed (doesn’t
> matter which ones).
> I’ve done weeks of testing on this, and finally gave up - taking it as a
> 3rd party bug. (Not related to NAV)
>
> Regards, Dejan.
>
> xxxxx@aliroo.com wrote:
>
> > Hi,
> >
> > We have a filter device driver for encryption that works OK.
> > On a single customer machine with Windows 2000 service pack 4 that has
> > symantec corporate 7.6 installed, we get an NO_MORE_IRP_STACK_LOCATIONS
> > whenever he tries to use a USB flash disk.
> > If I debug the system, I see that the IRP that causes the crash has only 4
> > stack locations (that were all exhausted).
> > Disabling the symantec driver solves the problem (and also when disabling
> > my driver).
> >
> > My question is why there are so few stack locations to begin with, and
> > whether there is an option to increase the number.
> >
> > I also tried to put some ‘safety’ code in my driver that will check when
> > the no. of available stack locations is too low and if so, performs an
> > IoSkipCurrentIrpStackLocation. This helped somewhat but the system still
> > crashed.
> >
> > —
> > 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. MVP for DDK
> http://www.alfasp.com E-mail: xxxxx@alfasp.com
> Alfa Transparent File Encryptor - Transparent file encryption services.
> Alfa File Protector - File protection and hiding library for Win32 developers.
>
> Alfa File Monitor - File monitoring library for Win32 developers.


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. MVP for DDK
http://www.alfasp.com E-mail: xxxxx@alfasp.com
Alfa Transparent File Encryptor - Transparent file encryption services.
Alfa File Protector - File protection and hiding library for Win32 developers.
Alfa File Monitor - File monitoring library for Win32 developers.

(This is a bit long, but I think that you will find this information
useful…)

If you hit this situation, it is a bug – a system with all components
correctly implemented will NOT have this problem.

When an IRP is allocated, the proper stack size should be stored in the
top device’s DeviceObject->StackSize in the device stack to which the
IRP will be targeted. The component initiating the IRP should call
IoAllocateIrp and provide this stack size so that an IRP of the proper
size is allocated, setup the IRP parameters, then send the IRP to the
same device object from which the StackSize was retrieved.

There are a couple common bugs that can generate this error:

  1. The component that is allocating and initializing the IRP uses a pool
    of IRPs and does not make sure that the stack size of the IRPs is large
    enough for the stack to which the IRP is going to be sent.

  2. A filter driver attaching to the device stack is reusing a device
    object which was previously attached to another device stack AND there
    are filter drivers attached above this device object from the old stack.
    The proper DeviceObject->StackSize gets set when the device object
    attaches to the device stack by calling an IoAttachDevice* API (you
    should be using IoAttachDeviceToDeviceStackSafe on XP and later). If a
    lower device object, let’s call it DeviceObjectX, in the stack changes
    stacks later because it was detached from one stack then reattached to
    another, the device objects attached to DeviceObjectX higher in the
    stack will *NOT* get their StackSize updated. Therefore, if the new
    stack is larger, the stack allocated by looking at the top device object
    will not be large enough.

** PLEASE NOTE ** The Sfilter sample from the NT 4.0 IFS Kit had this
exact bug! This code has been fixed in the Sfilter versions for the
Windows 2000 IFS Kit and later, so if you based your filter on the NT
4.0 sample, PLEASE get a more recent version of the kit and fix your
filter.

The bug specifically was in the logic for the dispatch routine for
IRP_MJ_FILE_SYSTEM_CONTROL - SfFsControl(). To handle
IPR_MN_LOAD_FILE_SYSTEM, Sfilter detached it’s device object from the
file system recognizer and put this device object on a global queue
called FsDeviceQueue. If it later received a mount request
(IRP_MJ_FILE_SYSTEM_CONTROL, IRP_MN_MOUNT_VOLUME), Sfilter first tries
to find an available device object in the FsDeviceQueue to reuse,
otherwise it allocates a new one. This is what is incorrect – device
objects should never be reused in this manner. You end up with
something like this:

*******************
* Filter Y *
* DeviceObjectY *
* StackSize = 4 *
*******************
|
|
*******************
* Filter X *
* DeviceObjectX *
* StackSize = 3 *
*******************
|
|
*******************
* \FatDiskRecog. *
* DeviceObjectX *
* StackSize = 2 *
*******************

Once FAT loads, Filter X detaches from the recognizer and puts its
device object in a global list and this device object may get reused
when a volume device object gets mounted. Once that happens you end up
with a stack that looks like this:

*******************
* Filter Y *
* DeviceObjectY *
* StackSize = 4 * <– STACK SIZE NOT UPDATED!!!
*******************
|
|
*******************
* Filter X *
* DeviceObjectX *
* StackSize = 9 * <– Updated stack size
*******************
|
|
*******************
* D: (FAT) *
* DeviceObjectX *
* StackSize = 8 *
*******************

While Filter Y may also be implemented to detach when from the
\FatDiskRecognizer and therefore detach from DeviceObjectX, you should
not count on that. Your filter driver will be more robust if you code
it such that you never reused device objects in this manner. Device
stacks come and go from the system sufficiently infrequently that you do
not need to be concerned about the overhead of the extra IoDeleteDevice
and IoCreateDevice calls.

Although the early IFS Kit samples show how to attach to recognizers,
most filters do not need to attach to file system recognizers. Your
filter has registered for a callback when file systems load by calling
IoRegisterFsRegistrationChange from DriverEntry(). You will get called
when the file system loads and you can attach to the file system control
device object at that time to see volume mount request. Starting with
the XP RTM version of the IFS Kit, the samples do not attach to the file
system recognizers by default (although it does still show how in case
your filter needs to do this for some reason).

Thanks for reading this far :).

Molly Brown
Microsoft Corporation

This posting is provided “AS IS” with no warranties and confers no
rights.

-----Original Message-----
From: xxxxx@lists.osr.com
[mailto:xxxxx@lists.osr.com] On Behalf Of Dejan Maksimovic
Sent: Sunday, November 02, 2003 4:59 AM
To: Windows File Systems Devs Interest List
Subject: [ntfsd] Re: NO_MORE_IRP_STACK_LOCATIONS

If you simply do this there is NOTHING you do except not doing
whatever your driver is supposed to do:-)
You have to fail the request. STATUS_INVALID_DEVICE_REQUEST is what
I’d suggest.

xxxxx@aliroo.com wrote:

My safety code was even more histerical:

BOOLEAN HaveEnoughIrpLocations(IN PIRP Irp) {
if(Irp->CurrentLocation < 4) {
return FALSE;
}
return TRUE;
}

and in various handlers:

if (!HaveEnoughIrpLocations(Irp)) {
IoSkipCurrentIrpStackLocation( Irp );
return IoCallDriver( FileSystemDeviceObject, Irp );
}

Still, although the crash was postponed, it finally did happen.
You suggest then to fail the request (with what code ?) instead of
passing it through ?

Rami

> Aha! I had this particular problem. What i did was check if
> Irp->CurrentLocation == 1 and just return and error.
> This happened though ONLY if I had EXACTLY 4 FS filter installed

> (doesn’t matter which ones).
> I’ve done weeks of testing on this, and finally gave up - taking

> it as a 3rd party bug. (Not related to NAV)
>
> Regards, Dejan.
>
> xxxxx@aliroo.com wrote:
>
> > Hi,
> >
> > We have a filter device driver for encryption that works OK.
> > On a single customer machine with Windows 2000 service pack 4 that

> > has symantec corporate 7.6 installed, we get an
> > NO_MORE_IRP_STACK_LOCATIONS whenever he tries to use a USB flash
disk.
> > If I debug the system, I see that the IRP that causes the crash
> > has only 4 stack locations (that were all exhausted).
> > Disabling the symantec driver solves the problem (and also when
> > disabling my driver).
> >
> > My question is why there are so few stack locations to begin with,

> > and whether there is an option to increase the number.
> >
> > I also tried to put some ‘safety’ code in my driver that will
> > check when the no. of available stack locations is too low and if
> > so, performs an IoSkipCurrentIrpStackLocation. This helped
> > somewhat but the system still crashed.
> >
> > —
> > 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. MVP for DDK
> http://www.alfasp.com E-mail: xxxxx@alfasp.com Alfa Transparent File

> Encryptor - Transparent file encryption services.
> Alfa File Protector - File protection and hiding library for Win32
developers.
>
> Alfa File Monitor - File monitoring library for Win32 developers.


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. MVP for DDK
http://www.alfasp.com E-mail: xxxxx@alfasp.com Alfa Transparent File
Encryptor - Transparent file encryption services.
Alfa File Protector - File protection and hiding library for Win32
developers.
Alfa File Monitor - File monitoring library for Win32 developers.


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