how to get the source path of IRP _CREATE on File Copying operation (in a Minifilter)

I am getting the file name from File object on IRP create. In fact, I am trying to find the source path.
is there any way to find source path

I am assuming you are filtering below the file system. If so, there is no
100% reliable way to get the filename, but you can backtrack and get the
filename most of the time:

PFILE_OBJECT GetIrpFileObject(IN PIRP Irp)
{
PFILE_OBJECT file_object = IoGetCurrentIrpStackLocation(Irp)->FileObject;
if (file_object == NULL) {
// Check previous stack location.
file_object = ((PIO_STACK_LOCATION)(Irp->Tail.Overlay.CurrentStackLocation

  • 1))->FileObject;
    if (file_object == NULL) {
    file_object = Irp->Tail.Overlay.OriginalFileObject;
    if (file_object == NULL) {
    if (Irp->Flags & IRP_ASSOCIATED_IRP) {
    file_object = Irp->AssociatedIrp.MasterIrp->Tail.Overlay.OriginalFileObject;
    }
    }
    }
    }
    return file_object;
    }

From the file object, you can extract the name.

On Wed, Nov 14, 2018 at 9:32 AM Nikhil_V_S
wrote:

> OSR https://community.osr.com/
> Nikhil_V_S started a new discussion: how to get the source path of IRP
> _CREATE on File Copying operation
>
> I am getting the file name from File object on IRP create. In fact, I am
> trying to find the source path.
>
> is there any way to find source path
>
> –
> Reply to this email directly or follow the link below to check it out:
>
> https://community.osr.com/discussion/290779/how-to-get-the-source-path-of-irp-create-on-file-copying-operation
>
> Check it out:
> https://community.osr.com/discussion/290779/how-to-get-the-source-path-of-irp-create-on-file-copying-operation
>

Irp->Tail.Overlay.CurrentStackLocation+ 1))->FileObject

I’m afraid I can’t recommend that approach…

Before you do that, I’d recommend Irp->Tail->Overlay->OriginalFileObject, with the caveats shown in WDM.H:

                //
                // Original file object - pointer to the original file object
                // that was used to open the file.  This field is owned by the
                // I/O system and should not be used by any other drivers.
                //
               PFILE_OBJECT OriginalFileObject;

Peter

Peter,

Please move this thread to the correct section, this is A&A and makes mess in my mails :slight_smile:

Michal

I don’t recommend doing this at all. I’ve used it in debug code, but not in
production code. The function is def. not safe :slight_smile:

On Wed, Nov 14, 2018 at 11:17 AM Peter_Viscarola_(OSR)
wrote:

> OSR https://community.osr.com/
> Peter_Viscarola_(OSR) commented on how to get the source path of IRP
> _CREATE on File Copying operation
>
> > Irp->Tail.Overlay.CurrentStackLocation+ 1))->FileObject
>
>
>
> I’m afraid I can’t recommend that approach…
>
>
>
> Before you do that, I’d recommend Irp->Tail->Overlay->OriginalFileObject,
> with the caveats shown in WDM.H:
>
> // // Original file object - pointer to
> the original file object // that was used to open the
> file. This field is owned by the // I/O system and should
> not be used by any other drivers. //
> PFILE_OBJECT OriginalFileObject;
>
> Peter
>
> –
> Reply to this email directly or follow the link below to check it out:
> https://community.osr.com/discussion/comment/291445#Comment_291445
>
> Check it out:
> https://community.osr.com/discussion/comment/291445#Comment_291445
>

@Michal_Vodicka said:
Peter,

Please move this thread to the correct section, this is A&A and makes mess in my mails :slight_smile:

Michal

Thank you, Mr. Vodicka! In my haste this morning, I didn’t even notice it was in the wrong section.

Many thanks,

Peter

The function is def. not safe

I’m not sure what “function” you mean, but the OriginalFileObject field definitely is safe when it’s present… We’ve used it in some (limited release) production code, and have never seen it fail. In fact, I recall that we very carefully researched it at the time, and became convinced it was safe when we determined that something in the storage stack relied on its being present and correct (though, regrettably, I can’t recall what it was).

Peter

I’ve not seen if fail either, but I have seen it not get the filename; for
obvious reasons. I don’t like doing things this way. The stack below the
file system should not know the file, is not obligated to know the file,
and it probably not a good practice. Maybe practical would have been a
better word to use than safe :slight_smile:

On Wed, Nov 14, 2018 at 2:31 PM Peter_Viscarola_(OSR)
wrote:

> OSR https://community.osr.com/
> Peter_Viscarola_(OSR) commented on how to get the source path of IRP
> _CREATE on File Copying operation
>
> > The function is def. not safe
>
> I’m not sure what “function” you mean, but the OriginalFileObject field
> definitely is safe when it’s present… We’ve used it in some (limited
> release) production code, and have never seen it fail. In fact, I recall
> that we very carefully researched it at the time, and became convinced it
> was safe when we determined that something in the storage stack relied on
> its being present and correct (though, regrettably, I can’t recall what it
> was).
>
> Peter
>
> –
> Reply to this email directly or follow the link below to check it out:
> https://community.osr.com/discussion/comment/291450#Comment_291450
>
> Check it out:
> https://community.osr.com/discussion/comment/291450#Comment_291450
>

but I have seen it not get the filename; for obvious reasons

Agreed.

The stack below the file system should not know the file

That is the traditional view, yes.

However, in the new world order, there are many reasons to want to know the file at the lowest levels of the storage stack. The most common being storage optimization based on the file’s type (extension). And I can’t think of anything this harms.

So, I say… go for it.

OTOH, I wouldn’t on my worst day grovel through random IRP Stack Locations interpreting the FIleObject field. These are architecturally supposed to be opaque to your driver. There are reasons that there are no function called “IoGetPreviousIoStackLocation” … it’s not like they just forgot to write it.

Peter

thank you all

But I am using minifilter
following code, section is used for getting file name
FLT_PREOP_CALLBACK_STATUS MiniPreCreate(PFLT_CALLBACK_DATA Data,PCFLT_RELATED_OBJECTS FltObjects , PVOID * CompletionContext)
{
PFLT_FILE_NAME_INFORMATION FileNameInfos;
NTSTATUS status;
WCHAR Name[200] = {0};
status=FltGetFileNameInformation(Data,FLT_FILE_NAME_NORMALIZED|FLT_FILE_NAME_QUERY_DEFAULT,&FileNameInfos);
if(NT_SUCCESS(status))
{
status = FltParseFileNameInformation(FileNameInfos);
if(NT_SUCCESS(status))
{
if(FileNameInfos->Name.MaximumLength<260)
{
RtlCopyMemory(Name,FileNameInfos->Name.Buffer,FileNameInfos->Name.MaximumLength);
KdPrint(“NVS ::File Name %ws \n”,Name);
}
}
FltReleaseFileNameInformation(FileNameInfos);
}
return FLT_PREOP_SUCCESS_WITH_CALLBACK;
}

how can I get the source path of the file copied on pre/post create in minifilter?

But I am using minifilter

Oh, well! That’s entirely different!

You need to say so in your original post… AND your question belongs in the NTFSD section, not NTDEV!

I’ll move it for you…

Peter

Thank you @“Peter_Viscarola_(OSR)”

If you meant you need to find the source file name behind a CopyFile win32 API call from a minifilter you’re not in luck.
The minifilter, you need to realize has no clue to what higher API call the the create came from and secondly in a create there is only ONE file not a source and destination or anything like that ( well could be a related file object, but you get the idea).
At that level in your filter you should process the request more or less on its own. Keep in mind that CopyFile could be implemented in many ways, and there is no need for someone to use the Win32 api at all. I can create my own CustomCopyFileFunction that:

  1. Open source file and create a file map.
  2. Map the entire file and Close the handle
  3. Open the destination file.
  4. read from the in-memory map and use WriteFile to the destination.

Your filter will see 1 create and one acquire for section sync on one file followed by paging reads. Then it will see another create on the other file followed by writes.
What I am trying to say is that there is no link between a win32 api and a minifilter so then the question arises, what do you want to do ?

Gabriel

@Gabriel_Bercea
thank you

I am trying create a file operation tracking application
I done the create and and delete file operation tracking by IOCompletion port .But I need to track the file copying operation with its source path.how it possible

Have you read my reply ?