Problem with IoBuildSynchronousFsdRequest in filter driver

Hi.
I’m trying to implement COW in filter driver. In my FilterDispatchWrite,I created a synchronous IRP_MJ_READ according to the IRP_MJ_WRITE using IoBuildSynchronousFsdRequest. I use IoCallDriver to send my Irp to next driver.But my driver keeps waiting my Irp to complete. Sometimes even worse I got blue screen crase, IRQL_NO_LESS_OR_EQUAL…
Here’s the code…

Any help?Thank you!!

Frente Chou

NTSTATUS FilterDispatchWrite(PDEVICE_OBJECT DeviceObject,PIRP Irp)
{
NTSTATUS orgIrpStatus;
PDEVICE_EXTENSION deviceExtension;
PIO_STACK_LOCATION pIrpStackLocation;

KEVENT event;

ULONG Length;
ULONGLONG ByteIndex;
ULONG SectorIndex;
PDEVICE_OBJECT TargetDeviceObject;

PVOID buffer;
PIO_STATUS_BLOCK IoStatusBlock;
PIRP shReadIrp;
PLARGE_INTEGER StartingOffset;
NTSTATUS readStatus;

deviceExtension = (PDEVICE_EXTENSION) DeviceObject->DeviceExtension;

pIrpStackLocation = IoGetCurrentIrpStackLocation(Irp);

Length = pIrpStackLocation->Parameters.Write.Length;

ByteIndex = pIrpStackLocation->Parameters.Write.ByteOffset.QuadPart;

SectorIndex = (ULONG)( ByteIndex / 512 );
////////////////////////////////////////

TargetDeviceObject = deviceExtension->TargetDeviceObject;
StartingOffset = &pIrpStackLocation->Parameters.Write.ByteOffset;

if(KeGetCurrentIrql() > PASSIVE_LEVEL){
DebugPrint((0,“Current IRQL > PASSIVE_LEVEL.\n”));
}else{

buffer = ExAllocatePool(NonPagedPool, pIrpStackLocation->Parameters.Write.Length);

IoStatusBlock = (PIO_STATUS_BLOCK)ExAllocatePool(NonPagedPool,sizeof(IO_STATUS_BLOCK));
if(NULL != buffer){
DebugPrint((0,
“NsFilterDispatchWrite Buffer allocated.\n”));
}
if(NULL != IoStatusBlock){
DebugPrint((0,“NsFilterDispatchWrite IoStatusBlock allocated.\n”));
}

KeInitializeEvent(&event,SynchronizationEvent, FALSE);

shReadIrp = IoBuildSynchronousFsdRequest(IRP_MJ_READ,TargetDeviceObject,buffer,Length,StartingOffset,&event,IoStatusBlock);

if(NULL != shReadIrp){
DebugPrint((0,“shReadIrp created.”));
readStatus = IoCallDriver(TargetDeviceObject, shReadIrp);
if (readStatus == STATUS_PENDING){
DebugPrint((0,“Waiting shReadIrp…\n”));
//KeWaitForSingleObject(&event, Executive, KernelMode, FALSE, NULL);
DebugPrint((0,“shReadIrp completed!\n”));
}
}
}
//////////////////////////////////////////

DebugPrint((0,
“NsFilterDispatchWrite write:Length::%u,ByteIndex::%u,SectorIndex::%u\n”,Length,ByteIndex,SectorIndex));

IoSkipCurrentIrpStackLocation(Irp);
orgIrpStatus = IoCallDriver(deviceExtension->TargetDeviceObject, Irp);

IoReleaseRemoveLock(&deviceExtension->RemoveLock, NULL);

return orgIrpStatus;

} // end FilterDispatchWrite()

> StartingOffset = &pIrpStackLocation->Parameters.Write.ByteOffset;

Don’t you see a bug in the above line??? It is pretty bizzare that your code does not crash right on the spot…

Therefore, ‘StartingOffset’ parameter that you specify in IoBuildSynchronousFsdRequest() call is just invalid. When you pass IRP down the stack, lower-level drivers get “confused”…

Anton Bassov

oh…Thank you …I made a stupid mistake…-_-!