Tuesday, January 5, 2016

On importance of FileObject->Vpb pointer

 An easily overlooked issue in FS(file systems) and FS filters development for Windows is Vpb pointer in FILE_OBJECT structure, i.e. Volume Parameters Block ( struct VPB ). It is responsibility of FS or FS filter ( in case of stacked FS, i.e. FSD-over-FSD ) to initialize this pointer to a correct value. It is especially important in case of FSD over FSD implementations as some underlying FSs check the VPB->ReferenceCount pointer on their PnP path and both upper FSD and lower FSD share the same VPB pointer. The kernel references Vpb in IopParseDevice routine that calls IRP_MJ_CREATE dispatch routine, but doesn't set Vpb pointer for FileObject sent with create Irp, and dereferences Vpb in IopDeleteFile just after IRP_MJ_CLOSE completes but IopDeleteFile fetches the pointer from FileObject->Vpb that is set by FS when processing IRP_MJ_CREATE. If FS or FS filter fails to set Vpb pointer PnP safe remove for some file systems would be impossible as Vpb->ReferenceCount never drops below a checked value.

 I encountered this problem when working on my own implementation for FSD-over-FSD FS filter. The problem manifested itself on FAT32 , NTFS was clean from this issue.

 Below are two call stacks for 32 bit Windows 8, the first is for a case when Vpb->ReferenceCount is bumped and the second for a case when it is decremented.


nt!IopCheckVpbMounted+0x81
nt!IopParseDevice+0x48b
nt!ObpLookupObjectName+0x6ef
nt!ObOpenObjectByName+0x1e3
nt!IopCreateFile+0x372
nt!NtCreateFile+0x78
nt!KiSystemServiceCopyEnd+0x13
ntdll!NtCreateFile+0xa


nt!IopDecrementVpbRefCount+0x5b
nt!IopDeleteFile+0xf5
nt!ObpRemoveObjectRoutine+0x64
nt!ObfDereferenceObjectWithTag+0x8f
nt!NtClose+0x210
nt!KiSystemServiceCopyEnd+0x13


No comments:

Post a Comment