I have some little comments:
- In the completion routine you should not mark the IRP pending,
because from the create dispatch routine you are returning without
STATUS_PENDING.
If some lower level driver have marked the IRP pending, you “eat”
this by waiting for IRP completing below you.
From you the request continues as synchronous and not ever posted.
- I have written routine called ZbfsCallNextLowerDriver which has done
all needed to call the next lower driver and wait to the request
completion
by it. I think something like this routine is useable more than one time
and thus why not to move the code into separate routine ?
But the general methodology is the same I use.
Paul
-----P?vodn? zpr?va-----
Od: Jamey Kirby [SMTP:xxxxx@storagecraft.com]
Odesl?no: 19. ?ervence 2000 20:02
Komu: File Systems Developers
P?edm?t: [ntfsd] RE: preventing recursive loop in create dispatch
hand lerSo, syn the create completion. Here is an example:
// _SyncComplete
NTSTATUS _SyncComplete
(
PDEVICE_OBJECT DeviceObject,
PIRP Irp,
PVOID Context
)
{
UNREFERENCED_PARAMETER(DeviceObject);
// Signal the IRP originator that its operation is complete.
if (Context != NULL)
KeSetEvent((PKEVENT)Context, IO_NO_INCREMENT, FALSE);
// Propagate the Pending stack location flag.
if (Irp->PendingReturned)
IoMarkIrpPending(Irp);
// Halt completing the IRP and give control back to the caller.
return (STATUS_MORE_PROCESSING_REQUIRED);
}// CreateSync
NTSTATUS BFilterCreateSync
(
PDEVICE_OBJECT DeviceObject,
PIRP Irp
)
{
NTSTATUS ntStatus;
PDEVICE_EXTENSION deviceExtension = DeviceObject->DeviceExtension;
PIO_STACK_LOCATION irpSp = IoGetCurrentIrpStackLocation(Irp);
ULONG requestedOptions = (irpSp->Parameters.Create.Options &
FILE_VALID_OPTION_FLAGS);
// Skip special cases we know about.
if
(
!(requestedOptions & FILE_DIRECTORY_FILE) &&
irpSp->FileObject->FileName.Length
)
{
KEVENT event;
// Initialize the event used to signla request completion.
KeInitializeEvent(&event, NotificationEvent, FALSE);
// Copy the stack to the next location for the target to use.
IoCopyCurrentIrpStackLocationToNext(Irp);
// Set the completion routine to make operation synchronous.
IoSetCompletionRoutine(Irp, _SyncComplete, &event, TRUE, TRUE,
TRUE);
// Call the target device with the request.
if ((ntStatus =
IoCallDriver(deviceExtension->FileSystemDeviceObject, Irp)) ==
STATUS_PENDING)
{
// Wait for it to complete.
KeWaitForSingleObject(&event, UserRequest, KernelMode, TRUE,
NULL);
// Reload local status with request status.
ntStatus = Irp->IoStatus.Status;
}
…
// Do some stuff to the file if you like.
…
}-----Original Message-----
From: xxxxx@lists.osr.com
[mailto:xxxxx@lists.osr.com]On Behalf Of Marc Sherman
Sent: Wednesday, July 19, 2000 10:34 AM
To: File Systems Developers
Subject: [ntfsd] RE: preventing recursive loop in create dispatch
hand lerDo you mean in the completion routine? If so, what if you need to
perform some operations that *must* be perfomed at passive level? The
completion routine could get invoked at dispatch level.Marc
> -----Original Message-----
> From: Jamey Kirby [mailto:xxxxx]
> > Sent: Wednesday, July 19, 2000 1:19 PM
> > To: File Systems Developers
> > Subject: [ntfsd] RE: preventing recursive loop in create dispatch
> hand
> > ler
> >
> >
> > Also, I am trying to understand the need to open a file via
> > an alternate IRP
> > in a creation routine. If you are getting an IRP_MJ_CREATE
> > and the file is,
> > say, “c:\x.x”, why would anyone create a seperate file
> > object, build a new
> > IRP and open the file “c:\x.x”? WOuld it not be better to
> > simply let the
> > original IRP_MJ_CREATE go through and then perform some
> > operation on the
> > file after completion?
> >
> > Am I missing something?
> >
> > Jamey
> >
> >
> > > -----Original Message-----
> > > From: xxxxx@lists.osr.com
> > > [mailto:xxxxx]On Behalf Of Pavel
> Hrdina
> > > Sent: Wednesday, July 19, 2000 9:51 AM
> > > To: File Systems Developers
> > > Subject: [ntfsd] RE: preventing recursive loop in create
> > dispatch hand
> > > ler
> > >
> > >
> > > I think the Geoff Clow is nearest to the TRUTH.
> > > It is neccessary to disassemble some parts of NTOS to
> > > definitely understand some interactions between components.
> > >
> > > I have used the following techniques:
> > >
> > > 1. I am using no Io Manager’s and Memory Manager’s ZwXxxx
> routines
> > > inside the FSD filter. I use them only from some system
> > thread where
> > > I know I’m the Request Iniciator (mostly in Nt variant,
> > > because there is
> > > evident the Thread->PreviousMode is KernelMode and thus
> > the mechanism
> > > for system calls [int 2e] is not needed at all).
> > >
> > > 2. For every mounted volume there is in our VCB:
> > >
> > > a) Physical device (named, eg. \Device\Harddisk0\Partition5)
> > > b) FSD device (mostly unnamed)
> > > c) Next lower device
> > >
> > > - to NextLowerDevice we will forward all requests
> > > - if we are attached right to FSD device, these two will
> > be the same
> > > - for network redirectors the Physical device and FSD device
> > > are the same
> > > eg. \Device\LanmanRedirector
> > >
> > > 3. If I want to open the file, query or set some info on it:
> > >
> > > I have written some synchronous routines like a
> NtCreateFile,
> > > NtQueryInformationFile and NtSetInformation file. Each of
> > > it builds an IRP and sends it down to the
> Vcb->NextLowerDevice.
> > > Thus I’m always calling all the filter stack below me, but
> no
> > > filter above me gets called.
> > >
> > > I am appending the file APISUP.C which contains these routines
> and
> > > mechanisms I’m using. (Hardest routine to implement is Create
> and
> > > currently I know some of its disadvantages - base methods are
> taken
> > > from the IopParseDevice routine)
> > >
> > > Paul
> > >
> > > > <<apisup.c>>
> > >
> > >
> >
> >
> > —
> > You are currently subscribed to ntfsd as: xxxxx@bionetrix.com
> > To unsubscribe send a blank email to
> $subst(‘Email.Unsub’)
> >
></apisup.c></mailto:xxxxx></mailto:xxxxx>