how to make a correct IRP_MJ_READ request

Hello I am making file system filter driver and I have some question regarding little issues I have encountered.

First of all my filter is bases on the sfilter example from the WDK, if there are user that don’t know the sample, It uses the attaching to the file system device exitent technique.

Now in my IRP_MJ_WRITE routine for example, let’s say I want to make a reading from, a file, that exists on a local volume.
It is obvious that I can’t use the NtReadFile routine, because I will filter myself.
I try to make an IRP for the lower filter device, to send it so it can write to the file for me.
the problem is, how to get the file_object structure, if for example the file has yet to have been opened.
I use IoCreateFileSpecifyDeviceObjectHint, to get the handle, and then ObReferenceObjectByHandle to get the FILE_OBJECT for my file
Is this the correct approach. How do I close the handle without calling ZwClose.
I tried making and IRP with the IRP_MJ_CLOSE in the irpstack major function.
So my main issue is how do I get a file object of a file if I have the path, and how do I close any handles if needed.
thank you.

Comments inline:

wrote in message news:xxxxx@ntfsd…
> Hello I am making file system filter driver and I have some
> question regarding little issues I have encountered.
>
>
> First of all my filter is bases on the sfilter example from the WDK,
> if there are user that don’t know the sample, It uses the attaching to
> the file system device exitent technique.
>
> Now in my IRP_MJ_WRITE routine for example, let’s say I want to make a
> reading from, a file, that exists on a local volume.
> It is obvious that I can’t use the NtReadFile routine, because I will
> filter myself.
> I try to make an IRP for the lower filter device, to send it so it can
> write to the file for me.
> the problem is, how to get the file_object structure, if for example the
> file has yet to have been opened.
> I use IoCreateFileSpecifyDeviceObjectHint, to get the handle, and then
> ObReferenceObjectByHandle to get the FILE_OBJECT for my file

Yes this is correct…

> Is this the correct approach. How do I close the handle without calling
> ZwClose.

Call ZwClose, you will have to be careful on the IRP_MJ_CLEANUP handling,
since you will see it. This is one of the advantages mini-filters they
will take care of this for you so you do not see the recursion.

> I tried making and IRP with the IRP_MJ_CLOSE in the irpstack major
> function.
> So my main issue is how do I get a file object of a file if I have the
> path, and how do I close any handles if needed.
> thank you.
>


Don Burn (MVP, Windows DDK)
Windows 2k/XP/2k3 Filesystem and Driver Consulting
Website: http://www.windrvr.com
Blog: http://msmvps.com/blogs/WinDrvr
Remove StopSpam to reply

My question was if the way I am getting the File_Object, knowing the fact that I am file system filter driver attached to a device is corect.
I will write the function I wrote from my code:

NTSTATUS
GetFileObjectFromPathEx(
PDEVICE_OBJECT DeviceObject,
PUNICODE_STRING Path,
PFILE_OBJECT *FileObject,
PHANDLE FileHandle,
IN ACCESS_MASK DesiredAccess)
{

NTSTATUS Status;
OBJECT_ATTRIBUTES ObjAttr;
IO_STATUS_BLOCK IoStatusBlock;
OBJECT_HANDLE_INFORMATION HandleInfo;
HANDLE hFile;

InitializeObjectAttributes(&ObjAttr,Path,OBJ_KERNEL_HANDLE,NULL,NULL);

Status=IoCreateFileSpecifyDeviceObjectHint(
&hFile,
DesiredAccess,
&ObjAttr,
&IoStatusBlock,
NULL,
FILE_ATTRIBUTE_NORMAL,
FILE_SHARE_READ,
FILE_OPEN,
FILE_SYNCHRONOUS_IO_NONALERT,
NULL,
0,
CreateFileTypeNone,
NULL,
IO_FORCE_ACCESS_CHECK,
DeviceObject); //this is the lower device that I am attached to

if (!NT_SUCCESS(Status))
{
*FileObject=NULL;
return Status;
}

Status = ObReferenceObjectByHandle(
hFile,
DesiredAccess,
*IoFileObjectType,
KernelMode,
FileObject,
&HandleInfo);

if (NT_SUCCESS(Status))
{
*FileHandle=hFile;
return Status;
}
else
{
ZwClose(hFile); //this is probrably wrong
return Status;

}

return STATUS_SUCCESS;
}

and now the code where I make the read request to the lower device I am attached to:

NTSTATUS
MakeReadRequest(
PDEVICE_OBJECT DeviceObject, //this is the lower device object I am attached to
PFILE_OBJECT FileObject, //this is the file Object I get from the function above
PVOID Buffer, //this is the buffer in which I want to read
ULONG Length, //this is the length of the buffer
PLARGE_INTEGER Offset,
ULONG POINTER_ALIGNMENT Key)
{
NTSTATUS Status,localStatus;
PIRP RequestIrp;
KEVENT SyncEvent;
IO_STATUS_BLOCK iosb;
PIO_STACK_LOCATION irpStack;

try
{

RequestIrp=IoAllocateIrp(DeviceObject->StackSize,FALSE);

if (RequestIrp==NULL)
{
return STATUS_INSUFFICIENT_RESOURCES;
}

RequestIrp->Tail.Overlay.Thread=PsGetCurrentProcessId();

iosb.Information=0;
iosb.Status=STATUS_SUCCESS;

RequestIrp->UserIosb=&iosb;
RequestIrp->UserEvent=NULL;

RequestIrp->Flags=IRP_SYNCHRONOUS_API|IRP_READ_OPERATION|IRP_BUFFERED_IO;

RequestIrp->RequestorMode=KernelMode;

irpStack=IoGetNextIrpStackLocation(RequestIrp);

irpStack->MajorFunction=IRP_MJ_READ;

irpStack->Parameters.Read.Length=Length;
irpStack->Parameters.Read.Key=Key;

irpStack->Parameters.Read.ByteOffset.HighPart=Offset->HighPart;
irpStack->Parameters.Read.ByteOffset.LowPart=Offset->LowPart;
irpStack->Parameters.Read.ByteOffset.QuadPart=Offset->QuadPart;
irpStack->Parameters.Read.ByteOffset.u.HighPart=Offset->u.HighPart;
irpStack->Parameters.Read.ByteOffset.u.LowPart=Offset->u.LowPart;

irpStack->FileObject=FileObject;

RequestIrp->AssociatedIrp.SystemBuffer=Buffer;

KeInitializeEvent(&SyncEvent,NotificationEvent,FALSE);

IoSetCompletionRoutine(RequestIrp,IoReadRequestCompletion,&SyncEvent,TRUE,TRUE,TRUE);

Status=IoCallDriver(DeviceObject,RequestIrp);

if (Status==STATUS_PENDING)
{
(VOID)KeWaitForSingleObject(
&SyncEvent,
Executive,
KernelMode,
FALSE,
NULL);
}

ASSERT(KeReadStateEvent(&SyncEvent) ||
!NT_SUCCESS(iosb.Status));

Status=iosb.Status;

}
finally
{
DbgPrint(“Read request finished”);

}

return Status;
}

after I do this I call ZwClose() on the handle obtained with my first function and Obdereferenceobject on the file object.
The thing is that after several calls the computer starts to freeze.
this is my IRP_MJ_CLOSE handling:

PSFILTER_DEVICE_EXTENSION devExt = (PSFILTER_DEVICE_EXTENSION)(DeviceObject->DeviceExtension);
PIO_STACK_LOCATION irpSp;

PAGED_CODE();

DbgPrint(“SFilter Close cleanup”);

irpSp = IoGetCurrentIrpStackLocation( Irp );

//
// Sfilter doesn’t allow handles to its control device object to be
// created, therefore, no other operation should be able to come through.
//

ASSERT(!IS_MY_CONTROL_DEVICE_OBJECT( DeviceObject ));

ASSERT(IS_MY_DEVICE_OBJECT( DeviceObject ));

//
// File systems should NEVER receive a power IRP
//

ASSERT(irpSp->MajorFunction != IRP_MJ_POWER);

//
// Get this driver out of the driver stack and get to the next driver as
// quickly as possible.
//

IoSkipCurrentIrpStackLocation( Irp );

//
// Now call the appropriate file system driver with the request.
//

return IoCallDriver( ((PSFILTER_DEVICE_EXTENSION) DeviceObject->DeviceExtension)->NLExtHeader.AttachedToDeviceObject,
Irp );

shoul I make the call synchronously ?
what is wrong, or how should I do this read request
thank you

> RequestIrp->Tail.Overlay.Thread=PsGetCurrentProcessId();
Just a (posibly irrelevant) note: why process, not thead? Why Id?

From http://msdn2.microsoft.com/en-us/library/aa491631.aspx:
Tail.Overlay.Thread is a pointer to the caller’s thread control block.
How about
RequestIrp->Tail.Overlay.Thread = PsGetCurrentThread();
?
Note: not ThreadId, but Thread.

-------------- Original message --------------
From: xxxxx@gmail.com

My question was if the way I am getting the File_Object, knowing the fact that I
am file system filter driver attached to a device is corect.
I will write the function I wrote from my code:

NTSTATUS
GetFileObjectFromPathEx(
PDEVICE_OBJECT DeviceObject,
PUNICODE_STRING Path,
PFILE_OBJECT *FileObject,
PHANDLE FileHandle,
IN ACCESS_MASK DesiredAccess)
{

NTSTATUS Status;
OBJECT_ATTRIBUTES ObjAttr;
IO_STATUS_BLOCK IoStatusBlock;
OBJECT_HANDLE_INFORMATION HandleInfo;
HANDLE hFile;

InitializeObjectAttributes(&ObjAttr,Path,OBJ_KERNEL_HANDLE,NULL,NULL);

Status=IoCreateFileSpecifyDeviceObjectHint(
&hFile,
DesiredAccess,
&ObjAttr,
&IoStatusBlock,
NULL,
FILE_ATTRIBUTE_NORMAL,
FILE_SHARE_READ,
FILE_OPEN,
FILE_SYNCHRONOUS_IO_NONALERT,
NULL,
0,
CreateFileTypeNone,
NULL,
IO_FORCE_ACCESS_CHECK,
DeviceObject); //this is the lower device that I am
attached to

if (!NT_SUCCESS(Status))
{
*FileObject=NULL;
return Status;
}

Status = ObReferenceObjectByHandle(
hFile,
DesiredAccess,
*IoFileObjectType,
KernelMode,
FileObject,
&HandleInfo);

if (NT_SUCCESS(Status))
{
*FileHandle=hFile;
return Status;
}
else
{
ZwClose(hFile); //this is probrably wrong
return Status;

}

return STATUS_SUCCESS;
}

and now the code where I make the read request to the lower device I am attached
to:

NTSTATUS
MakeReadRequest(
PDEVICE_OBJECT DeviceObject, //this is the lower device object I
am attached to
PFILE_OBJECT FileObject, //this is the file Object I get from
the function above
PVOID Buffer, //this is the buffer in which I want to read
ULONG Length, //this is the length of the buffer
PLARGE_INTEGER Offset,
ULONG POINTER_ALIGNMENT Key)
{
NTSTATUS Status,localStatus;
PIRP RequestIrp;
KEVENT SyncEvent;
IO_STATUS_BLOCK iosb;
PIO_STACK_LOCATION irpStack;

try
{

RequestIrp=IoAllocateIrp(DeviceObject->StackSize,FALSE);

if (RequestIrp==NULL)
{
return STATUS_INSUFFICIENT_RESOURCES;
}

RequestIrp->Tail.Overlay.Thread=PsGetCurrentProcessId();

iosb.Information=0;
iosb.Status=STATUS_SUCCESS;

RequestIrp->UserIosb=&iosb;
RequestIrp->UserEvent=NULL;

RequestIrp->Flags=IRP_SYNCHRONOUS_API|IRP_READ_OPERATION|IRP_BUFFERED_IO;

RequestIrp->RequestorMode=KernelMode;

irpStack=IoGetNextIrpStackLocation(RequestIrp);

irpStack->MajorFunction=IRP_MJ_READ;

irpStack->Parameters.Read.Length=Length;
irpStack->Parameters.Read.Key=Key;

irpStack->Parameters.Read.ByteOffset.HighPart=Offset->HighPart;
irpStack->Parameters.Read.ByteOffset.LowPart=Offset->LowPart;
irpStack->Parameters.Read.ByteOffset.QuadPart=Offset->QuadPart;

irpStack->Parameters.Read.ByteOffset.u.HighPart=Offset->u.HighPart;

irpStack->Parameters.Read.ByteOffset.u.LowPart=Offset->u.LowPart;

irpStack->FileObject=FileObject;

RequestIrp->AssociatedIrp.SystemBuffer=Buffer;

KeInitializeEvent(&SyncEvent,NotificationEvent,FALSE);

IoSetCompletionRoutine(RequestIrp,IoReadRequestCompletion,&SyncEvent,TRUE,TRUE,T
RUE);

Status=IoCallDriver(DeviceObject,RequestIrp);

if (Status==STATUS_PENDING)
{
(VOID)KeWaitForSingleObject(
&SyncEvent,
Executive,
KernelMode,
FALSE,
NULL);
}

ASSERT(KeReadStateEvent(&SyncEvent) ||
!NT_SUCCESS(iosb.Status));

Status=iosb.Status;

}
finally
{
DbgPrint(“Read request finished”);

}

return Status;
}

after I do this I call ZwClose() on the handle obtained with my first function
and Obdereferenceobject on the file object.
The thing is that after several calls the computer starts to freeze.
this is my IRP_MJ_CLOSE handling:

PSFILTER_DEVICE_EXTENSION devExt =
(PSFILTER_DEVICE_EXTENSION)(DeviceObject->DeviceExtension);
PIO_STACK_LOCATION irpSp;

PAGED_CODE();

DbgPrint(“SFilter Close cleanup”);

irpSp = IoGetCurrentIrpStackLocation( Irp );

//
// Sfilter doesn’t allow handles to its control device object to be
// created, therefore, no other operation should be able to come through.
//

ASSERT(!IS_MY_CONTROL_DEVICE_OBJECT( DeviceObject ));

ASSERT(IS_MY_DEVICE_OBJECT( DeviceObject ));

//
// File systems should NEVER receive a power IRP
//

ASSERT(irpSp->MajorFunction != IRP_MJ_POWER);

//
// Get this driver out of the driver stack and get to the next driver as
// quickly as possible.
//

IoSkipCurrentIrpStackLocation( Irp );

//
// Now call the appropriate file system driver with the request.
//

return IoCallDriver( ((PSFILTER_DEVICE_EXTENSION)
DeviceObject->DeviceExtension)->NLExtHeader.AttachedToDeviceObject,
Irp );

shoul I make the call synchronously ?
what is wrong, or how should I do this read request
thank you


Questions? First check the IFS FAQ at
https://www.osronline.com/article.cfm?id=17

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

:((((((((( u’re right

I took another way in building this IRP correctly.
this is it:

if (!Once)
if (RtlCompareUnicodeString(&TestFile,&(fileName->Name),TRUE)==0)
{
Once=TRUE;

ReadBuffer=ExAllocatePoolWithTag(PagedPool,
1024,
‘abc’);

KeInitializeEvent(
&SyncEvent,
NotificationEvent,
FALSE);

RtlZeroMemory(&StartOffset,sizeof(LARGE_INTEGER));

RequestIrp=IoBuildAsynchronousFsdRequest(
IRP_MJ_READ,
devExt->NLExtHeader.AttachedToDeviceObject,
ReadBuffer,
1024,
&StartOffset,
&iosb);

if (RequestIrp)
{
RequestStack=IoGetNextIrpStackLocation(RequestIrp);

RequestStack->FileObject=irpSp->FileObject;
RequestIrp->Tail.Overlay.OriginalFileObject=irpSp->FileObject;

IoSetCompletionRoutine(
RequestIrp,
IoReadRequestCompletion,
&SyncEvent,
TRUE,
TRUE,
TRUE);

Status = IoCallDriver(
devExt->NLExtHeader.AttachedToDeviceObject,
RequestIrp);

if (Status==STATUS_PENDING)
KeWaitForSingleObject(
&SyncEvent,
Executive,
KernelMode,
FALSE,
NULL);

if (NT_SUCCESS(iosb.Status))
{
DbgPrint(“Am citit cu success: %s”,ReadBuffer);

}
else
DbgPrint(“Error reading: 0x%x”,iosb.Status);

ExFreePoolWithTag(ReadBuffer,‘abc’);

}

Well this code actually works.
I put this code in my IRP_MJ_WRITE routine and It works fine, but when I put the same code in the IRP_MJ_READ routine i get blue screen.
in the IRP_MJ_READ routine i try to send this packet I am building to the same file the packet in the IRP_MJ_READ is going, but this sould be fine.

this is how it should work:
That string comparison from the above actually tests if the IRP_MJ_READ is sent to the file I want, then I try to send that file a request (but I get blue) screen, then I continue sendig the initial IRP.
I don’t know why I get this. Should I not send read request in the IRP_MJ_READ, or should I first let the initial request go and then send mine.
Why do I get blue screen

and another thing, you see I put that condition there, unless the my file has been sent the read request I don;t try to make the request neither, but the thing is that when I start the driver, I get blue screen instantaneusly without my file being sent the request. Why is that. if I comment the part where I make and send my IRP the driver works fine, and I see in the windbg that I am right, that the file doesn’t get the request instantaneusly.
please help

> but when I put the same code in the IRP_MJ_READ routine i get blue screen

Let’s look on your request, I do not want to tell you about using the name
from the file object in routines different from IRP_MJ_CREATE, search this
list.

Firstly, look on a string -

RequestIrp->Tail.Overlay.OriginalFileObject=irpSp->FileObject;

this string marks the IRP as sent from the routine like NtReadFile and the
system presumes in this case that the FileObject has been opened by
NtCreateFile and behaves accordingly, for example, it sets the file object’s
event in a signal state, but this might result in a premature awakening of a
thread waiting on this event and many other errors, because the system will
go on a wrong path during the IRP completion.
Secondly, file object used by the system might be a stream file object,
especially if this is a read request from the page fault handler, in this
case it is illegal to check its name( actually, it is illegal in any case,
but works for debug purposes ).


Slava Imameyev, xxxxx@hotmail.com

wrote in message news:xxxxx@ntfsd…
>I took another way in building this IRP correctly.
> this is it:
>
> if (!Once)
> if (RtlCompareUnicodeString(&TestFile,&(fileName->Name),TRUE)==0)
> {
> Once=TRUE;
>
> ReadBuffer=ExAllocatePoolWithTag(PagedPool,
> 1024,
> ‘abc’);
>
> KeInitializeEvent(
> &SyncEvent,
> NotificationEvent,
> FALSE);
>
> RtlZeroMemory(&StartOffset,sizeof(LARGE_INTEGER));
>
> RequestIrp=IoBuildAsynchronousFsdRequest(
> IRP_MJ_READ,
> devExt->NLExtHeader.AttachedToDeviceObject,
> ReadBuffer,
> 1024,
> &StartOffset,
> &iosb);
>
> if (RequestIrp)
> {
> RequestStack=IoGetNextIrpStackLocation(RequestIrp);
>
> RequestStack->FileObject=irpSp->FileObject;
> RequestIrp->Tail.Overlay.OriginalFileObject=irpSp->FileObject;
>
>
>
> IoSetCompletionRoutine(
> RequestIrp,
> IoReadRequestCompletion,
> &SyncEvent,
> TRUE,
> TRUE,
> TRUE);
>
>
> Status = IoCallDriver(
> devExt->NLExtHeader.AttachedToDeviceObject,
> RequestIrp);
>
> if (Status==STATUS_PENDING)
> KeWaitForSingleObject(
> &SyncEvent,
> Executive,
> KernelMode,
> FALSE,
> NULL);
>
>
> if (NT_SUCCESS(iosb.Status))
> {
> DbgPrint(“Am citit cu success: %s”,ReadBuffer);
>
> }
> else
> DbgPrint(“Error reading: 0x%x”,iosb.Status);
>
>
> ExFreePoolWithTag(ReadBuffer,‘abc’);
>
> }
>
> Well this code actually works.
> I put this code in my IRP_MJ_WRITE routine and It works fine, but when I
> put the same code in the IRP_MJ_READ routine i get blue screen.
> in the IRP_MJ_READ routine i try to send this packet I am building to the
> same file the packet in the IRP_MJ_READ is going, but this sould be fine.
>
> this is how it should work:
> That string comparison from the above actually tests if the IRP_MJ_READ is
> sent to the file I want, then I try to send that file a request (but I get
> blue) screen, then I continue sendig the initial IRP.
> I don’t know why I get this. Should I not send read request in the
> IRP_MJ_READ, or should I first let the initial request go and then send
> mine.
> Why do I get blue screen
>
>

this is the Dispatch write routine. This worked with the request that I showed you, but if I modified instead of IRP_MJ_READ, IRP_MJ_WRITE i get blue screen instantaneusly
When the IRP_MJ_READ succeded I get this on dbgview, besides my usual messages:
EX: Pageble Code at IRQL 2 (DISPATCH_LEVEL I presume) is this an exception ?
the reading is done correctly.
Is something I am missing.
the NLXxxx functions are from the sfilter example from microsoft and I think they are done correctly :stuck_out_tongue:

here is Dispatch write:

NTSTATUS
SfWrite (
__in PDEVICE_OBJECT DeviceObject,
__in PIRP Irp
)
{
NTSTATUS Status;
PNAME_CONTROL fileName = NULL;
PSFILTER_DEVICE_EXTENSION devExt = (PSFILTER_DEVICE_EXTENSION)(DeviceObject->DeviceExtension);
PIO_STACK_LOCATION irpSp = IoGetCurrentIrpStackLocation( Irp );
BOOLEAN cacheName;
NAME_LOOKUP_FLAGS LookupFlags = 0x00000000;
KEVENT waitEvent;
NTSTATUS localStatus;
char *ReadBuffer;
//PMDL Mdl;
PIRP RequestIrp;
KEVENT SyncEvent;
IO_STATUS_BLOCK iosb;
PIO_STACK_LOCATION RequestStack;
UNICODE_STRING TestFile2;
LARGE_INTEGER StartOffset;
HANDLE hFile;
PFILE_OBJECT FileObject;

PAGED_CODE();

if (IS_MY_CONTROL_DEVICE_OBJECT(DeviceObject)) {

/*
nu filtram propriul device
*/

Irp->IoStatus.Status = STATUS_INVALID_DEVICE_REQUEST;
Irp->IoStatus.Information = 0;

IoCompleteRequest( Irp, IO_NO_INCREMENT );

return STATUS_INVALID_DEVICE_REQUEST;
}

ASSERT(IS_MY_DEVICE_OBJECT( DeviceObject ));

Status = NLAllocateNameControl( &fileName, &gSfNameBufferLookasideList );

if (NT_SUCCESS( Status )) {

//
// We are okay not checking the return value here because
// the GetFullPathName function will set the Unicode String
// length to 0. So either way, in an error it will print an empty string
//

if (devExt->NLExtHeader.DosName.Length!=0)
SetFlag(LookupFlags,NLFL_USE_DOS_DEVICE_NAME);

localStatus = NLGetFullPathName(irpSp->FileObject,
fileName,
&devExt->NLExtHeader,
LookupFlags,
&gSfNameBufferLookasideList,
&cacheName );

//if (!Once)
__try
{
if (RtlCompareUnicodeString(&TestFile,&(fileName->Name),TRUE)==0)
{

ReadBuffer=ExAllocatePoolWithTag(PagedPool,
1024,
‘abc’);

KeInitializeEvent(
&SyncEvent,
NotificationEvent,
FALSE);

RtlZeroMemory(&StartOffset,sizeof(LARGE_INTEGER));
RtlCopyMemory(ReadBuffer,“Test de scris in fisier”,sizeof(“Test de scris in fisier”));

RequestIrp=IoBuildAsynchronousFsdRequest(
IRP_MJ_WRITE,
devExt->NLExtHeader.AttachedToDeviceObject,
ReadBuffer,
sizeof(“Test de scris in fisier”),
&StartOffset,
&iosb);

if (RequestIrp)
{
RequestStack=IoGetNextIrpStackLocation(RequestIrp);

ObReferenceObjectByPointer(
irpSp->FileObject,
GENERIC_WRITE|GENERIC_READ,
*IoFileObjectType,
KernelMode);

RequestStack->FileObject=irpSp->FileObject;
RequestIrp->Tail.Overlay.OriginalFileObject=irpSp->FileObject;

IoSetCompletionRoutine(
RequestIrp,
IoReadRequestCompletion,
&SyncEvent,
TRUE,
TRUE,
TRUE);

Status = IoCallDriver(
devExt->NLExtHeader.AttachedToDeviceObject,
RequestIrp);

if (Status==STATUS_PENDING)
KeWaitForSingleObject(
&SyncEvent,
Executive,
KernelMode,
FALSE,
NULL);

if (NT_SUCCESS(iosb.Status))
{
DbgPrint("Success writting: %u ",iosb.Information);

}
else
DbgPrint(“Error writting: 0x%x”,iosb.Status);

ObDereferenceObject(irpSp->FileObject);

ExFreePoolWithTag(ReadBuffer,‘abc’);

}

}
}
__except(EXCEPTION_EXECUTE_HANDLER)
{

Status=GetExceptionCode();
DbgPrint(“Exception raised: 0x%x”,Status);
}

DbgPrint(“IRP_MJ_WRITE: FILE: %S Process: %s, ReadLength: %u, Offset %u”,
fileName->Name.Buffer?fileName->Name.Buffer:L"N/A",
PsGetProcessImageFileName(IoGetCurrentProcess()),irpSp->Parameters.Read.Length,irpSp->Parameters.Read.ByteOffset.QuadPart);

if (NT_SUCCESS(localStatus))
NLFreeNameControl(fileName,&gSfNameBufferLookasideList);
}
else
{
DbgPrint(“Could not get name in IRP_MJ_WRITE”);
}

KeInitializeEvent( &waitEvent, NotificationEvent, FALSE );

//
// Copy the stack and set our Completion routine
//

IoCopyCurrentIrpStackLocationToNext( Irp );

IoSetCompletionRoutine(
Irp,
SfReadCompletion,
&waitEvent,
TRUE,
TRUE,
TRUE );

//
// Call the next driver in the stack.
//

Status = IoCallDriver( devExt->NLExtHeader.AttachedToDeviceObject, Irp );

//
// Wait for the completion routine to be called
//

if (STATUS_PENDING == Status)

localStatus = KeWaitForSingleObject( &waitEvent,
Executive,
KernelMode,
FALSE,
NULL );

Status = Irp->IoStatus.Status;

IoCompleteRequest( Irp, IO_NO_INCREMENT );

return Status;

}

> i get blue screen instantaneusly

Did you read what I wrote?

Remove the string

RequestIrp->Tail.Overlay.OriginalFileObject=irpSp->FileObject; < remove
this!

Only internal system’s functions can use THIS field to provide information
about the caller( which is Nt* function ) to internal system’s completion
routine( IopCompleteRequest ). Search the WDK - there is no any example
using this field!


Slava Imameyev, xxxxx@hotmail.com

wrote in message news:xxxxx@ntfsd…
> this is the Dispatch write routine. This worked with the request that I
> showed you, but if I modified instead of IRP_MJ_READ, IRP_MJ_WRITE i get
> blue screen instantaneusly
> When the IRP_MJ_READ succeded I get this on dbgview, besides my usual
> messages:
> EX: Pageble Code at IRQL 2 (DISPATCH_LEVEL I presume) is this an exception
> ?
> the reading is done correctly.
> Is something I am missing.
> the NLXxxx functions are from the sfilter example from microsoft and I
> think they are done correctly :stuck_out_tongue:
>
> here is Dispatch write:
>
> NTSTATUS
> SfWrite (
> in PDEVICE_OBJECT DeviceObject,
>
in PIRP Irp
> )
> {
> NTSTATUS Status;
> PNAME_CONTROL fileName = NULL;
> PSFILTER_DEVICE_EXTENSION devExt =
> (PSFILTER_DEVICE_EXTENSION)(DeviceObject->DeviceExtension);
> PIO_STACK_LOCATION irpSp = IoGetCurrentIrpStackLocation( Irp );
> BOOLEAN cacheName;
> NAME_LOOKUP_FLAGS LookupFlags = 0x00000000;
> KEVENT waitEvent;
> NTSTATUS localStatus;
> char ReadBuffer;
> //PMDL Mdl;
> PIRP RequestIrp;
> KEVENT SyncEvent;
> IO_STATUS_BLOCK iosb;
> PIO_STACK_LOCATION RequestStack;
> UNICODE_STRING TestFile2;
> LARGE_INTEGER StartOffset;
> HANDLE hFile;
> PFILE_OBJECT FileObject;
>
>
>
> PAGED_CODE();
>
> if (IS_MY_CONTROL_DEVICE_OBJECT(DeviceObject)) {
>
> /

> nu filtram propriul device
> */
>
> Irp->IoStatus.Status = STATUS_INVALID_DEVICE_REQUEST;
> Irp->IoStatus.Information = 0;
>
> IoCompleteRequest( Irp, IO_NO_INCREMENT );
>
> return STATUS_INVALID_DEVICE_REQUEST;
> }
>
> ASSERT(IS_MY_DEVICE_OBJECT( DeviceObject ));
>
>
> Status = NLAllocateNameControl( &fileName, &gSfNameBufferLookasideList );
>
>
>
> if (NT_SUCCESS( Status )) {
>
> //
> // We are okay not checking the return value here because
> // the GetFullPathName function will set the Unicode String
> // length to 0. So either way, in an error it will print an empty string
> //
>
> if (devExt->NLExtHeader.DosName.Length!=0)
> SetFlag(LookupFlags,NLFL_USE_DOS_DEVICE_NAME);
>
>
>
> localStatus = NLGetFullPathName(irpSp->FileObject,
> fileName,
> &devExt->NLExtHeader,
> LookupFlags,
> &gSfNameBufferLookasideList,
> &cacheName );
>
>
> //if (!Once)
> __try
> {
> if (RtlCompareUnicodeString(&TestFile,&(fileName->Name),TRUE)==0)
> {
>
>
> ReadBuffer=ExAllocatePoolWithTag(PagedPool,
> 1024,
> ‘abc’);
>
> KeInitializeEvent(
> &SyncEvent,
> NotificationEvent,
> FALSE);
>
> RtlZeroMemory(&StartOffset,sizeof(LARGE_INTEGER));
> RtlCopyMemory(ReadBuffer,“Test de scris in fisier”,sizeof(“Test de scris
> in fisier”));
>
> RequestIrp=IoBuildAsynchronousFsdRequest(
> IRP_MJ_WRITE,
> devExt->NLExtHeader.AttachedToDeviceObject,
> ReadBuffer,
> sizeof(“Test de scris in fisier”),
> &StartOffset,
> &iosb);
>
> if (RequestIrp)
> {
> RequestStack=IoGetNextIrpStackLocation(RequestIrp);
>
> ObReferenceObjectByPointer(
> irpSp->FileObject,
> GENERIC_WRITE|GENERIC_READ,
> *IoFileObjectType,
> KernelMode);
>
>
> RequestStack->FileObject=irpSp->FileObject;
> RequestIrp->Tail.Overlay.OriginalFileObject=irpSp->FileObject;
>
>
>
> IoSetCompletionRoutine(
> RequestIrp,
> IoReadRequestCompletion,
> &SyncEvent,
> TRUE,
> TRUE,
> TRUE);
>
>
> Status = IoCallDriver(
> devExt->NLExtHeader.AttachedToDeviceObject,
> RequestIrp);
>
> if (Status==STATUS_PENDING)
> KeWaitForSingleObject(
> &SyncEvent,
> Executive,
> KernelMode,
> FALSE,
> NULL);
>
>
> if (NT_SUCCESS(iosb.Status))
> {
> DbgPrint("Success writting: %u “,iosb.Information);
>
> }
> else
> DbgPrint(“Error writting: 0x%x”,iosb.Status);
>
> ObDereferenceObject(irpSp->FileObject);
>
>
> ExFreePoolWithTag(ReadBuffer,‘abc’);
>
>
>
>
>
> }
>
>
> }
> }
>__except(EXCEPTION_EXECUTE_HANDLER)
> {
>
> Status=GetExceptionCode();
> DbgPrint(“Exception raised: 0x%x”,Status);
> }
>
>
>
>
>
> DbgPrint(“IRP_MJ_WRITE: FILE: %S Process: %s, ReadLength: %u, Offset %u”,
> fileName->Name.Buffer?fileName->Name.Buffer:L"N/A”,
> PsGetProcessImageFileName(IoGetCurrentProcess()),irpSp->Parameters.Read.Length,irpSp->Parameters.Read.ByteOffset.QuadPart);
>
> if (NT_SUCCESS(localStatus))
> NLFreeNameControl(fileName,&gSfNameBufferLookasideList);
> }
> else
> {
> DbgPrint(“Could not get name in IRP_MJ_WRITE”);
> }
>
>
> KeInitializeEvent( &waitEvent, NotificationEvent, FALSE );
>
> //
> // Copy the stack and set our Completion routine
> //
>
> IoCopyCurrentIrpStackLocationToNext( Irp );
>
> IoSetCompletionRoutine(
> Irp,
> SfReadCompletion,
> &waitEvent,
> TRUE,
> TRUE,
> TRUE );
>
> //
> // Call the next driver in the stack.
> //
>
> Status = IoCallDriver( devExt->NLExtHeader.AttachedToDeviceObject, Irp );
>
> //
> // Wait for the completion routine to be called
> //
>
> if (STATUS_PENDING == Status)
>
> localStatus = KeWaitForSingleObject( &waitEvent,
> Executive,
> KernelMode,
> FALSE,
> NULL );
>
>
> Status = Irp->IoStatus.Status;
>
> IoCompleteRequest( Irp, IO_NO_INCREMENT );
>
>
> return Status;
>
>
>
> }
>
>
>

I saw what you wrote but gave u my dispatch routine to see if it is OK
What about the EX at IRQL 2, is that normal ?

i removed the string and I still get the blue screen instantaneusly, the thing is that the condition for the file, if (RtlCompareUnicodeString(&TestFile,&(fileName->Name),TRUE)==0) isn’t accomplished, so the code for the request isn’t executed, I know this because if I modify it, and pur IRP_MJ_READ instead of IRP_MJ_WRITE the code works OK, i see this in debug view.
Could it be because I ran the code many times on the same machine. I ran it in virtual machine (Microsoft Virtual PC Windows XP sp2)

I don’t get this.
What am I missing.

>but gave u my dispatch routine to see if it is OK

At first glance it looks OK, except the line I mentioned. But I did not do a
thorough investigation of your code.

What about the EX at IRQL 2, is that normal ?

No, definitely this is not normal, check your code, the underlying FSD wont
be able to process read request at DISPATCH_LEVEL.


Slava Imameyev, xxxxx@hotmail.com

wrote in message news:xxxxx@ntfsd…
>I saw what you wrote but gave u my dispatch routine to see if it is OK
> What about the EX at IRQL 2, is that normal ?
>

>i removed the string and I still get the blue screen

Provide us with the output for “!analyze -v” command


Slava Imameyev, xxxxx@hotmail.com

wrote in message news:xxxxx@ntfsd…
>i removed the string and I still get the blue screen instantaneusly, the
>thing is that the condition for the file, if
>(RtlCompareUnicodeString(&TestFile,&(fileName->Name),TRUE)==0) isn’t
>accomplished, so the code for the request isn’t executed, I know this
>because if I modify it, and pur IRP_MJ_READ instead of IRP_MJ_WRITE the
>code works OK, i see this in debug view.
> Could it be because I ran the code many times on the same machine. I ran
> it in virtual machine (Microsoft Virtual PC Windows XP sp2)
>
>
> I don’t get this.
> What am I missing.
>

Hello
I figured out what was going on, and I am very surprized.
The problem was the RtlCompareUnicodeString,
I commented the line and everything works fine
the MakeQueryNameInformationRequest function is not the problem it works fine.
The RtlCompareUnicodeString. I mean whenever I try to compare the memory in fileName->Name.Buffer with another memory I get blue screen.
The IRQL was 0 at what IRQL the RtlCompareUnicodeString should be called at.
In this case how do I compare the filenames to see if the current file is the file I am interrested in.
The NLGetFullPathName function, provided by Microsoft get the name by making a IRP_MJ_QUERY_INFORMATION request to the lower driver, with the class FILE_NAME_INFORMATION.
The buffer is allocated, and everything, and I don’t see why I can’t read the memory from it.
DbgPrint prints it fine.
please help.

this is the !analyze -v output:

kd> !analyze -v
*******************************************************************************
* *
* Bugcheck Analysis *
* *
*******************************************************************************

PAGE_FAULT_IN_NONPAGED_AREA (50)
Invalid system memory was referenced. This cannot be protected by try-except,
it must be protected by a Probe. Typically the address is just plain bad or it
is pointing at freed memory.
Arguments:
Arg1: f8dce700, memory referenced.
Arg2: 00000000, value 0 = read operation, 1 = write operation.
Arg3: 8056c95a, If non-zero, the instruction address which referenced the bad memory
address.
Arg4: 00000000, (reserved)

Debugging Details:

***** Kernel symbols are WRONG. Please fix symbols to do analysis.

MODULE_NAME: sfilter

FAULTING_MODULE: 804d7000 nt

DEBUG_FLR_IMAGE_TIMESTAMP: 46955c44

READ_ADDRESS: unable to get nt!MmSpecialPoolStart
unable to get nt!MmSpecialPoolEnd
unable to get nt!MmPoolCodeStart
unable to get nt!MmPoolCodeEnd
f8dce700

FAULTING_IP:
nt!RtlCompareUnicodeString+40
8056c95a 668b3a mov di,[edx]

MM_INTERNAL_CODE: 0

DEFAULT_BUCKET_ID: DRIVER_FAULT

BUGCHECK_STR: 0x50

LAST_CONTROL_TRANSFER: from 805333be to 804e3b25

STACK_TEXT:
WARNING: Stack unwind information not available. Following frames may be wrong.
f8997130 805333be 00000003 806ed03c c03e3738 nt!DbgBreakPointWithStatus+0x4
f8997510 805339ae 00000050 f8dce700 00000000 nt!KeDeregisterBugCheckReasonCallback+0x6c7
f8997530 805246fb 00000050 f8dce700 00000000 nt!KeBugCheckEx+0x1b
f899757c 804e1ff1 00000000 f8dce700 00000000 nt!PoSetSystemState+0xc140
f89975b4 f8dc4ee7 f8dc7f08 f8997608 ffff0000 nt!Kei386EoiHelper+0x26f6
f8997620 f8dc87f2 f8dc8028 f8dc7f80 00000001 sfilter!MakeQueryNameInformationRequest+0x147 [c:\winddk\6000\src\filesys\filter\file_system_filter\ioutils.c @ 78]
f89976e0 804e3d77 ffab4250 ffb2b158 806ed070 sfilter!SfWrite+0x3e2 [c:\winddk\6000\src\filesys\filter\file_system_filter\sfilter.c @ 2259]
f8997704 8057a510 ffab4250 ffb2b158 811c4f30 nt!IofCallDriver+0x32
f89977b8 804df06b 00000090 00000000 00000000 nt!NtWriteFile+0x3eb
f89977e4 7c90eb94 badb0d00 0007f8b4 0007fe80 nt!ZwYieldExecution+0xb96
f89977e8 badb0d00 0007f8b4 0007fe80 0000003b ntdll!KiFastSystemCallRet
f89977ec 0007f8b4 0007fe80 0000003b 77d494cf 0xbadb0d00
f89977f0 0007fe80 0000003b 77d494cf 0000001b 0x7f8b4
f89977f4 00000000 77d494cf 0000001b 00000246 0x7fe80

FOLLOWUP_IP:
sfilter!MakeQueryNameInformationRequest+147 [c:\winddk\6000\src\filesys\filter\file_system_filter\ioutils.c @ 78]
f8dc4ee7 83c40c add esp,0xc

>WARNING: Stack unwind information not available. Following frames may be

wrong.

I doubt that you will receive any help until you correct debugger’s symbol
search path, the call stack that you provided is useless.
At least, execute “.symfix” command before executing “!analyze -v” and
check that your debugger has access to
http://msdl.microsoft.com/download/symbols.


Slava Imameyev, xxxxx@hotmail.com

wrote in message news:xxxxx@ntfsd…
> Hello
> I figured out what was going on, and I am very surprized.
> The problem was the RtlCompareUnicodeString,
> I commented the line and everything works fine
> the MakeQueryNameInformationRequest function is not the problem it works
> fine.
> The RtlCompareUnicodeString. I mean whenever I try to compare the memory
> in fileName->Name.Buffer with another memory I get blue screen.
> The IRQL was 0 at what IRQL the RtlCompareUnicodeString should be called
> at.
> In this case how do I compare the filenames to see if the current file is
> the file I am interrested in.
> The NLGetFullPathName function, provided by Microsoft get the name by
> making a IRP_MJ_QUERY_INFORMATION request to the lower driver, with the
> class FILE_NAME_INFORMATION.
> The buffer is allocated, and everything, and I don’t see why I can’t read
> the memory from it.
> DbgPrint prints it fine.
> please help.
>
>
> this is the !analyze -v output:
>
> kd> !analyze -v
> ***
> *
>
> * Bugcheck Analysis
>
> *
>
>

>
> PAGE_FAULT_IN_NONPAGED_AREA (50)
> Invalid system memory was referenced. This cannot be protected by
> try-except,
> it must be protected by a Probe. Typically the address is just plain bad
> or it
> is pointing at freed memory.
> Arguments:
> Arg1: f8dce700, memory referenced.
> Arg2: 00000000, value 0 = read operation, 1 = write operation.
> Arg3: 8056c95a, If non-zero, the instruction address which referenced the
> bad memory
> address.
> Arg4: 00000000, (reserved)
>
> Debugging Details:
> ------------------
>
> ***** Kernel symbols are WRONG. Please fix symbols to do analysis.
>
>
> MODULE_NAME: sfilter
>
> FAULTING_MODULE: 804d7000 nt
>
> DEBUG_FLR_IMAGE_TIMESTAMP: 46955c44
>
> READ_ADDRESS: unable to get nt!MmSpecialPoolStart
> unable to get nt!MmSpecialPoolEnd
> unable to get nt!MmPoolCodeStart
> unable to get nt!MmPoolCodeEnd
> f8dce700
>
> FAULTING_IP:
> nt!RtlCompareUnicodeString+40
> 8056c95a 668b3a mov di,[edx]
>
> MM_INTERNAL_CODE: 0
>
> DEFAULT_BUCKET_ID: DRIVER_FAULT
>
> BUGCHECK_STR: 0x50
>
> LAST_CONTROL_TRANSFER: from 805333be to 804e3b25
>
> STACK_TEXT:
> WARNING: Stack unwind information not available. Following frames may be
> wrong.
> f8997130 805333be 00000003 806ed03c c03e3738
> nt!DbgBreakPointWithStatus+0x4
> f8997510 805339ae 00000050 f8dce700 00000000
> nt!KeDeregisterBugCheckReasonCallback+0x6c7
> f8997530 805246fb 00000050 f8dce700 00000000 nt!KeBugCheckEx+0x1b
> f899757c 804e1ff1 00000000 f8dce700 00000000 nt!PoSetSystemState+0xc140
> f89975b4 f8dc4ee7 f8dc7f08 f8997608 ffff0000 nt!Kei386EoiHelper+0x26f6
> f8997620 f8dc87f2 f8dc8028 f8dc7f80 00000001
> sfilter!MakeQueryNameInformationRequest+0x147
> [c:\winddk\6000\src\filesys\filter\file_system_filter\ioutils.c @ 78]
> f89976e0 804e3d77 ffab4250 ffb2b158 806ed070 sfilter!SfWrite+0x3e2
> [c:\winddk\6000\src\filesys\filter\file_system_filter\sfilter.c @ 2259]
> f8997704 8057a510 ffab4250 ffb2b158 811c4f30 nt!IofCallDriver+0x32
> f89977b8 804df06b 00000090 00000000 00000000 nt!NtWriteFile+0x3eb
> f89977e4 7c90eb94 badb0d00 0007f8b4 0007fe80 nt!ZwYieldExecution+0xb96
> f89977e8 badb0d00 0007f8b4 0007fe80 0000003b ntdll!KiFastSystemCallRet
> f89977ec 0007f8b4 0007fe80 0000003b 77d494cf 0xbadb0d00
> f89977f0 0007fe80 0000003b 77d494cf 0000001b 0x7f8b4
> f89977f4 00000000 77d494cf 0000001b 00000246 0x7fe80
>
>
> FOLLOWUP_IP:
> sfilter!MakeQueryNameInformationRequest+147
> [c:\winddk\6000\src\filesys\filter\file_system_filter\ioutils.c @ 78]
> f8dc4ee7 83c40c add esp,0xc
>
>
>