Should I See IRP_MJ_CREATE when I open a file

Hi All:
I have a problem of writing a usb storage device filter driver
I wrote a filter driver , now I can see the IRP_MJ_READ and IRP_MJ_WRITE
when I open a file in the usb storage device, but now I want to get the
file name
of the file when file open or file write happened…
what should I do?
I got
PIO_STACK_LOCATION Current = IoGetCurrentIrpStackLocation(Irp);
PFILE_OBJECT pFileObject = Current->FileObject;
if(!pFileObject){
DbgPrint(“this is null”);
}else{
DbgPrint(“this is not null”);
}
I always got this is null when IRP_MJ_READ and IRP_MJ_WRITE happened…
only “this is not null” when IRP_MJ_CREATE happened , but I found that
IRP_MJ_CREATE only apears when the usb device insert into myPC
here is my filter driver below…

Need your help …thanx alot…

/*++

Copyright (c) 1996 Microsoft Corporation

Module Name:

filter.c

Abstract: NULL filter driver – boilerplate code

Author:

ervinp

Environment:

Kernel mode

Revision History:

–*/

#include <wdm.h>
#include <stdio.h>
#include “filter.h”

#ifdef ALLOC_PRAGMA
#pragma alloc_text(INIT, DriverEntry)
#pragma alloc_text(PAGE, VA_AddDevice)
#pragma alloc_text(PAGE, VA_DriverUnload)
#endif

NTSTATUS DriverEntry(
IN PDRIVER_OBJECT DriverObject,
IN PUNICODE_STRING RegistryPath
)
/++

Routine Description:

Installable driver initialization entry point.
This entry point is called directly by the I/O system.

Arguments:

DriverObject - pointer to the driver object

RegistryPath - pointer to a unicode string representing the path,
to driver-specific key in the registry.

Return Value:

STATUS_SUCCESS if successful,
STATUS_UNSUCCESSFUL otherwise

/
{

ULONG i;

PAGED_CODE();

UNREFERENCED_PARAMETER(RegistryPath);

DBGOUT((“DriverEntry”));
DbgPrint(“DriverEntry==================”);
for (i = 0; i <= IRP_MJ_MAXIMUM_FUNCTION; i++){
DriverObject->MajorFunction[i] = VA_Dispatch;
}

DriverObject->DriverExtension->AddDevice = VA_AddDevice;
DriverObject->DriverUnload = VA_DriverUnload;

return STATUS_SUCCESS;
}

NTSTATUS VA_AddDevice(
IN PDRIVER_OBJECT driverObj,
IN PDEVICE_OBJECT physicalDevObj
)
/++

Routine Description:

The PlugPlay subsystem is handing us a brand new
PDO (Physical Device Object), for which we
(by means of INF registration) have been asked to filter.

We need to determine if we should attach or not.
Create a filter device object to attach to the stack
Initialize that device object
Return status success.

Remember: we can NOT actually send ANY non pnp IRPS to the given driver
stack, UNTIL we have received an IRP_MN_START_DEVICE.

Arguments:

driverObj - pointer to a device object.

physicalDevObj - pointer to a physical device object pointer
created by the underlying bus driver.

Return Value:

NT status code.

/

{

NTSTATUS status;
PDEVICE_OBJECT filterDevObj = NULL;

PAGED_CODE();

DBGOUT((“VA_AddDevice: drvObj=%ph, pdo=%ph”, driverObj,
physicalDevObj));
DbgPrint(“######### —Add_Device— #########”);
status = IoCreateDevice( driverObj,
sizeof(struct DEVICE_EXTENSION),
NULL,
FILE_DEVICE_FILE_SYSTEM,
FILE_REMOVABLE_MEDIA,
FALSE, // not exclusive
&filterDevObj); // our device object
if (NT_SUCCESS(status)){
struct DEVICE_EXTENSION devExt;

ASSERT(filterDevObj);
devExt = (struct DEVICE_EXTENSION )filterDevObj->DeviceExtension;
RtlZeroMemory(devExt, sizeof(struct DEVICE_EXTENSION));
devExt->signature = DEVICE_EXTENSION_SIGNATURE;
devExt->state = STATE_INITIALIZED;
devExt->filterDevObj = filterDevObj;
devExt->physicalDevObj = physicalDevObj;

devExt->pendingActionCount = 0;
KeInitializeEvent(&devExt->removeEvent, NotificationEvent, FALSE);
#ifdef HANDLE_DEVICE_USAGE
KeInitializeEvent(&devExt->deviceUsageNotificationEvent,
SynchronizationEvent, TRUE);
#endif // HANDLE_DEVICE_USAGE
devExt->topDevObj = IoAttachDeviceToDeviceStack(filterDevObj,
physicalDevObj);
ASSERT(devExt->topDevObj);
DBGOUT((“created filterDevObj %ph attached to %ph.”, filterDevObj,
devExt->topDevObj));
filterDevObj->Flags |=
(devExt->topDevObj->Flags & (DO_BUFFERED_IO | DO_DIRECT_IO));
filterDevObj->Flags |= (devExt->topDevObj->Flags &
(DO_POWER_INRUSH | DO_POWER_PAGABLE /
| DO_POWER_NOOP
/));

#ifdef HANDLE_DEVICE_USAGE
if ((devExt->topDevObj->Flags & DO_POWER_PAGABLE)
/|| (devExt->topDevObj->Flags & DO_POWER_NOOP)/)
{
}
else
{
DBGOUT(( “LOCKing some driver code (non-pageable) (b/c init
conditions)” ));
devExt->initUnlockHandle = MmLockPagableCodeSection( VA_Power );
// some func that’s inside the code section that we want to lock
ASSERT( NULL != devExt->initUnlockHandle );
}
devExt->initialFlags = filterDevObj->Flags &
~DO_DEVICE_INITIALIZING;
#endif // HANDLE_DEVICE_USAGE
filterDevObj->Flags &= ~DO_DEVICE_INITIALIZING;
RegistryAccessSample(devExt, devExt->physicalDevObj);
}
ASSERT(NT_SUCCESS(status));
return status;
}
VOID VA_DriverUnload(IN PDRIVER_OBJECT DriverObject)
/++

Routine Description:

Free all the allocated resources, etc.

Note: Although the DriverUnload function often does nothing,
the driver must set a DriverUnload function in
DriverEntry; otherwise, the kernel will never unload
the driver.

Arguments:

DriverObject - pointer to a driver object.

Return Value:

VOID.

/
{
PAGED_CODE();
DBGOUT((“VA_DriverUnload”));
}
void testread(IN PDEVICE_OBJECT DeviceObject,IN PIRP Irp){
PIO_STACK_LOCATION Current = IoGetCurrentIrpStackLocation(Irp);
PFILE_OBJECT pFileObject = Current->FileObject;

if(!pFileObject){
DbgPrint(“this is null”);
}else{
DbgPrint(“this is not null”);
}
}

NTSTATUS VA_Dispatch(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
/++

Routine Description:

Common entrypoint for all Io Request Packets

Arguments:

DeviceObject - pointer to a device object.
Irp - Io Request Packet

Return Value:

NT status code.

/

{
struct DEVICE_EXTENSION *devExt;
PIO_STACK_LOCATION irpSp;
BOOLEAN passIrpDown = TRUE;
UCHAR majorFunc, minorFunc;
NTSTATUS status;

devExt = DeviceObject->DeviceExtension;
ASSERT(devExt->signature == DEVICE_EXTENSION_SIGNATURE);

irpSp = IoGetCurrentIrpStackLocation(Irp);
majorFunc = irpSp->MajorFunction;
minorFunc = irpSp->MinorFunction;
DBGOUT((“VA_Dispatch: majorFunc=%d, minorFunc=%d”,
(ULONG)majorFunc, (ULONG)minorFunc));
if (!((majorFunc == IRP_MJ_PNP) && (minorFunc ==
IRP_MN_REMOVE_DEVICE))){
IncrementPendingActionCount(devExt);
}

if ((majorFunc != IRP_MJ_PNP) &&
(majorFunc != IRP_MJ_CLOSE) &&
((devExt->state == STATE_REMOVING) ||
(devExt->state == STATE_REMOVED))){
status = Irp->IoStatus.Status = STATUS_DELETE_PENDING;
IoCompleteRequest(Irp, IO_NO_INCREMENT);
passIrpDown = FALSE;
}
else {
switch (majorFunc){
case IRP_MJ_READ:
DbgPrint(“######### IRP_MJ_READ #########”);
testread(DeviceObject,Irp);
break;
case IRP_MJ_WRITE:
DbgPrint(“######### IRP_MJ_WRITE #########”);
testread(DeviceObject,Irp);
break;
case IRP_MJ_PNP:
status = VA_PnP(devExt, Irp);
passIrpDown = FALSE;
break;
case IRP_MJ_POWER:
status = VA_Power(devExt, Irp);
passIrpDown = FALSE;
break;
case IRP_MJ_DEVICE_CONTROL:
DbgPrint(“######### IRP_MJ_DEVICE_CONTROL #########”);
break;
case IRP_MJ_CREATE:
DbgPrint(“######### IRP_MJ_CREATE #########”);
testread(DeviceObject,Irp);
break;
case IRP_MJ_CLOSE:
DbgPrint(“######### IRP_MJ_CLOSE #########”);
break;
case IRP_MJ_SYSTEM_CONTROL:
DbgPrint(“######### IRP_MJ_SYSTEM_CONTROL #########”);
break;
case IRP_MJ_INTERNAL_DEVICE_CONTROL:
DbgPrint(“######### IRP_MJ_INTERNAL_DEVICE_CONTROL #########”);
break;
case IRP_MJ_CLEANUP:
DbgPrint(“######### IRP_MJ_CLEANUP #########”);
break;
case IRP_MJ_FLUSH_BUFFERS:
DbgPrint(“######### IRP_MJ_FLUSH_BUFFERS #########”);
break;
case IRP_MJ_QUERY_INFORMATION:
DbgPrint(“######### IRP_MJ_QUERY_INFORMATION #########”);
break;
case IRP_MJ_SET_INFORMATION:
DbgPrint(“######### IRP_MJ_SET_INFORMATION #########”);
break;
case IRP_MJ_SHUTDOWN:
DbgPrint(“######### IRP_MJ_SHUTDOWN #########”);
break;
default:
break;
}
}
if (passIrpDown){
IoCopyCurrentIrpStackLocationToNext(Irp);
status = IoCallDriver(devExt->topDevObj, Irp);
}
if (!((majorFunc == IRP_MJ_PNP) && (minorFunc ==
IRP_MN_REMOVE_DEVICE))){
DecrementPendingActionCount(devExt);
}
return status;
}</stdio.h></wdm.h>

You are filtering the wrong layer. IRP_MJ_CREATE IRP is sent only during
file system mount. The storage device itself knows nothing about files, so
it doesn’t get any create requests. File system handles all create request
and it reads and writes raw data to from/to storage device.

–htfv

“Shuo-Da Huang(¶ÀºÓ¹F)” wrote in message
news:xxxxx@ntfsd…
> Hi All:
> I have a problem of writing a usb storage device filter driver
> I wrote a filter driver , now I can see the IRP_MJ_READ and
> IRP_MJ_WRITE
> when I open a file in the usb storage device, but now I want to get the
> file name
> of the file when file open or file write happened…
> what should I do?
> I got
> PIO_STACK_LOCATION Current = IoGetCurrentIrpStackLocation(Irp);
> PFILE_OBJECT pFileObject = Current->FileObject;
> if(!pFileObject){
> DbgPrint(“this is null”);
> }else{
> DbgPrint(“this is not null”);
> }
> I always got this is null when IRP_MJ_READ and IRP_MJ_WRITE happened…
> only “this is not null” when IRP_MJ_CREATE happened , but I found that
> IRP_MJ_CREATE only apears when the usb device insert into myPC
> here is my filter driver below…
>
> Need your help …thanx alot…
>
> /++
>
> Copyright (c) 1996 Microsoft Corporation
>
> Module Name:
>
> filter.c
>
> Abstract: NULL filter driver – boilerplate code
>
> Author:
>
> ervinp
>
> Environment:
>
> Kernel mode
>
> Revision History:
>
>
> –
/
>
> #include <wdm.h>
> #include <stdio.h>
> #include “filter.h”
>
> #ifdef ALLOC_PRAGMA
> #pragma alloc_text(INIT, DriverEntry)
> #pragma alloc_text(PAGE, VA_AddDevice)
> #pragma alloc_text(PAGE, VA_DriverUnload)
> #endif
>
>
> NTSTATUS DriverEntry(
> IN PDRIVER_OBJECT DriverObject,
> IN PUNICODE_STRING RegistryPath
> )
> /++
>
> Routine Description:
>
> Installable driver initialization entry point.
> This entry point is called directly by the I/O system.
>
> Arguments:
>
> DriverObject - pointer to the driver object
>
> RegistryPath - pointer to a unicode string representing the path,
> to driver-specific key in the registry.
>
> Return Value:
>
> STATUS_SUCCESS if successful,
> STATUS_UNSUCCESSFUL otherwise
>
> –
/
> {
>
> ULONG i;
>
> PAGED_CODE();
>
> UNREFERENCED_PARAMETER(RegistryPath);
>
> DBGOUT((“DriverEntry”));
> DbgPrint(“DriverEntry==================”);
> for (i = 0; i <= IRP_MJ_MAXIMUM_FUNCTION; i++){
> DriverObject->MajorFunction[i] = VA_Dispatch;
> }
>
> DriverObject->DriverExtension->AddDevice = VA_AddDevice;
> DriverObject->DriverUnload = VA_DriverUnload;
>
> return STATUS_SUCCESS;
> }
>
>
> NTSTATUS VA_AddDevice(
> IN PDRIVER_OBJECT driverObj,
> IN PDEVICE_OBJECT physicalDevObj
> )
> /++
>
> Routine Description:
>
> The PlugPlay subsystem is handing us a brand new
> PDO (Physical Device Object), for which we
> (by means of INF registration) have been asked to filter.
>
> We need to determine if we should attach or not.
> Create a filter device object to attach to the stack
> Initialize that device object
> Return status success.
>
> Remember: we can NOT actually send ANY non pnp IRPS to the given driver
> stack, UNTIL we have received an IRP_MN_START_DEVICE.
>
> Arguments:
>
> driverObj - pointer to a device object.
>
> physicalDevObj - pointer to a physical device object pointer
> created by the underlying bus driver.
>
> Return Value:
>
> NT status code.
>
> –
/
>
> {
>
> NTSTATUS status;
> PDEVICE_OBJECT filterDevObj = NULL;
>
> PAGED_CODE();
>
> DBGOUT((“VA_AddDevice: drvObj=%ph, pdo=%ph”, driverObj,
> physicalDevObj));
> DbgPrint(“######### —Add_Device— #########”);
> status = IoCreateDevice( driverObj,
> sizeof(struct DEVICE_EXTENSION),
> NULL,
> FILE_DEVICE_FILE_SYSTEM,
> FILE_REMOVABLE_MEDIA,
> FALSE, // not exclusive
> &filterDevObj); // our device object
> if (NT_SUCCESS(status)){
> struct DEVICE_EXTENSION devExt;
>
> ASSERT(filterDevObj);
> devExt = (struct DEVICE_EXTENSION )filterDevObj->DeviceExtension;
> RtlZeroMemory(devExt, sizeof(struct DEVICE_EXTENSION));
> devExt->signature = DEVICE_EXTENSION_SIGNATURE;
> devExt->state = STATE_INITIALIZED;
> devExt->filterDevObj = filterDevObj;
> devExt->physicalDevObj = physicalDevObj;
>
> devExt->pendingActionCount = 0;
> KeInitializeEvent(&devExt->removeEvent, NotificationEvent, FALSE);
> #ifdef HANDLE_DEVICE_USAGE
> KeInitializeEvent(&devExt->deviceUsageNotificationEvent,
> SynchronizationEvent, TRUE);
> #endif // HANDLE_DEVICE_USAGE
> devExt->topDevObj = IoAttachDeviceToDeviceStack(filterDevObj,
> physicalDevObj);
> ASSERT(devExt->topDevObj);
> DBGOUT((“created filterDevObj %ph attached to %ph.”, filterDevObj,
> devExt->topDevObj));
> filterDevObj->Flags |=
> (devExt->topDevObj->Flags & (DO_BUFFERED_IO | DO_DIRECT_IO));
> filterDevObj->Flags |= (devExt->topDevObj->Flags &
> (DO_POWER_INRUSH | DO_POWER_PAGABLE /
| DO_POWER_NOOP
/));
>
> #ifdef HANDLE_DEVICE_USAGE
> if ((devExt->topDevObj->Flags & DO_POWER_PAGABLE)
> /|| (devExt->topDevObj->Flags & DO_POWER_NOOP)/)
> {
> }
> else
> {
> DBGOUT(( “LOCKing some driver code (non-pageable) (b/c init
> conditions)” ));
> devExt->initUnlockHandle = MmLockPagableCodeSection(
> VA_Power );
> // some func that’s inside the code section that we want to lock
> ASSERT( NULL != devExt->initUnlockHandle );
> }
> devExt->initialFlags = filterDevObj->Flags &
> ~DO_DEVICE_INITIALIZING;
> #endif // HANDLE_DEVICE_USAGE
> filterDevObj->Flags &= ~DO_DEVICE_INITIALIZING;
> RegistryAccessSample(devExt, devExt->physicalDevObj);
> }
> ASSERT(NT_SUCCESS(status));
> return status;
> }
> VOID VA_DriverUnload(IN PDRIVER_OBJECT DriverObject)
> /++
>
> Routine Description:
>
> Free all the allocated resources, etc.
>
> Note: Although the DriverUnload function often does nothing,
> the driver must set a DriverUnload function in
> DriverEntry; otherwise, the kernel will never unload
> the driver.
>
> Arguments:
>
> DriverObject - pointer to a driver object.
>
> Return Value:
>
> VOID.
>
> –
/
> {
> PAGED_CODE();
> DBGOUT((“VA_DriverUnload”));
> }
> void testread(IN PDEVICE_OBJECT DeviceObject,IN PIRP Irp){
> PIO_STACK_LOCATION Current = IoGetCurrentIrpStackLocation(Irp);
> PFILE_OBJECT pFileObject = Current->FileObject;
>
> if(!pFileObject){
> DbgPrint(“this is null”);
> }else{
> DbgPrint(“this is not null”);
> }
> }
>
> NTSTATUS VA_Dispatch(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
> /++
>
> Routine Description:
>
> Common entrypoint for all Io Request Packets
>
> Arguments:
>
> DeviceObject - pointer to a device object.
> Irp - Io Request Packet
>
> Return Value:
>
> NT status code.
>
> –
/
>
> {
> struct DEVICE_EXTENSION *devExt;
> PIO_STACK_LOCATION irpSp;
> BOOLEAN passIrpDown = TRUE;
> UCHAR majorFunc, minorFunc;
> NTSTATUS status;
>
> devExt = DeviceObject->DeviceExtension;
> ASSERT(devExt->signature == DEVICE_EXTENSION_SIGNATURE);
>
> irpSp = IoGetCurrentIrpStackLocation(Irp);
> majorFunc = irpSp->MajorFunction;
> minorFunc = irpSp->MinorFunction;
> DBGOUT((“VA_Dispatch: majorFunc=%d, minorFunc=%d”,
> (ULONG)majorFunc, (ULONG)minorFunc));
> if (!((majorFunc == IRP_MJ_PNP) && (minorFunc ==
> IRP_MN_REMOVE_DEVICE))){
> IncrementPendingActionCount(devExt);
> }
>
> if ((majorFunc != IRP_MJ_PNP) &&
> (majorFunc != IRP_MJ_CLOSE) &&
> ((devExt->state == STATE_REMOVING) ||
> (devExt->state == STATE_REMOVED))){
> status = Irp->IoStatus.Status = STATUS_DELETE_PENDING;
> IoCompleteRequest(Irp, IO_NO_INCREMENT);
> passIrpDown = FALSE;
> }
> else {
> switch (majorFunc){
> case IRP_MJ_READ:
> DbgPrint(“######### IRP_MJ_READ #########”);
> testread(DeviceObject,Irp);
> break;
> case IRP_MJ_WRITE:
> DbgPrint(“######### IRP_MJ_WRITE #########”);
> testread(DeviceObject,Irp);
> break;
> case IRP_MJ_PNP:
> status = VA_PnP(devExt, Irp);
> passIrpDown = FALSE;
> break;
> case IRP_MJ_POWER:
> status = VA_Power(devExt, Irp);
> passIrpDown = FALSE;
> break;
> case IRP_MJ_DEVICE_CONTROL:
> DbgPrint(“######### IRP_MJ_DEVICE_CONTROL #########”);
> break;
> case IRP_MJ_CREATE:
> DbgPrint(“######### IRP_MJ_CREATE #########”);
> testread(DeviceObject,Irp);
> break;
> case IRP_MJ_CLOSE:
> DbgPrint(“######### IRP_MJ_CLOSE #########”);
> break;
> case IRP_MJ_SYSTEM_CONTROL:
> DbgPrint(“######### IRP_MJ_SYSTEM_CONTROL #########”);
> break;
> case IRP_MJ_INTERNAL_DEVICE_CONTROL:
> DbgPrint(“######### IRP_MJ_INTERNAL_DEVICE_CONTROL #########”);
> break;
> case IRP_MJ_CLEANUP:
> DbgPrint(“######### IRP_MJ_CLEANUP #########”);
> break;
> case IRP_MJ_FLUSH_BUFFERS:
> DbgPrint(“######### IRP_MJ_FLUSH_BUFFERS #########”);
> break;
> case IRP_MJ_QUERY_INFORMATION:
> DbgPrint(“######### IRP_MJ_QUERY_INFORMATION #########”);
> break;
> case IRP_MJ_SET_INFORMATION:
> DbgPrint(“######### IRP_MJ_SET_INFORMATION #########”);
> break;
> case IRP_MJ_SHUTDOWN:
> DbgPrint(“######### IRP_MJ_SHUTDOWN #########”);
> break;
> default:
> break;
> }
> }
> if (passIrpDown){
> IoCopyCurrentIrpStackLocationToNext(Irp);
> status = IoCallDriver(devExt->topDevObj, Irp);
> }
> if (!((majorFunc == IRP_MJ_PNP) && (minorFunc ==
> IRP_MN_REMOVE_DEVICE))){
> DecrementPendingActionCount(devExt);
> }
> return status;
> }
>
>
></stdio.h></wdm.h>