⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 specialiofunction.cpp

📁 一个过滤层文件系统驱动的完整代码,实现了文件的加密,操作截获等
💻 CPP
📖 第 1 页 / 共 4 页
字号:

#include "FsTPM.h"

// Used to set Object's flag
#ifndef SetFlag
#define SetFlag(x,f)    ((x) |= (f))
#endif

// Used to clear Object's flag
#ifndef ClearFlag
#define ClearFlag(x,f)  ((x) &= ~(f))
#endif

BOOL IsSomeSpecialFile( PWCHAR WideSource, PFILE_OBJECT pFileObject, PIO_STACK_LOCATION pCurrentIrpStack)
{
	if ( /*(0==pFileObject->FileName.Length)			||*/
		(wcsstr(WideSource,L"SYSTEM32\\CONFIG")!=0) ||
		(wcsstr(WideSource,L"NTUSER.DAT.LOG")!=0)	||
		(wcsstr(WideSource,L"PAGEFILE.SYS")!=0)		||
		(wcsstr(WideSource,L"NTUSER.DAT")!=0)		||
		(wcsstr(WideSource,L"SECURITY.LOG")!=0)		||
		(wcsstr(WideSource,L"SOFTWARE.LOG")!=0)		||
		(wcsstr(WideSource,L"SYSTEM.LOG")!=0)		||
		(wcsstr(WideSource,L"DEFAULT.LOG")!=0)		||
		(Is_Directory_File(pCurrentIrpStack->Parameters.Create.Options))
		)
	{
		return TRUE;
	}
	return FALSE;
}



VOID 
FsTPMGetFileStandardInformation(
								  PFILE_OBJECT FileObject,
								  PFILE_STANDARD_INFORMATION StandardInformation,
								  PIO_STATUS_BLOCK IoStatusBlock,
								  PDEVICE_OBJECT pDeviceObject
								  )
								  //++
								  // Function:	FsTPMGetFileStandardInformation
								  //
								  // Description:
								  //		Get a file's standard information 
								  //
								  // Arguments:
								  //		IN  FileObject			- Target file object 
								  //		OUT StandardInformation - Standard information pointer
								  //		OUT IoStatusBlock		- Point out whether this request is success.
								  //		IN  pDeviceObject       - the Device below me
								  // Return value:
								  //		None
								  //
								  // Notice :
								  //		This function is provided by OSR
								  //--
{
	PIRP irp;
	KEVENT event;
	PIO_STACK_LOCATION ioStackLocation;
	PDEVICE_OBJECT fsdDevice=pDeviceObject;

	//
	// Start off on the right foot - zero the information block.
	//

	RtlZeroMemory(StandardInformation, sizeof(FILE_STANDARD_INFORMATION));

	//
	// Allocate an irp for this request.  This could also come from a 
	// private pool, for instance.
	//

	irp = IoAllocateIrp(fsdDevice->StackSize, FALSE);

	if (!irp) {
		//
		// Failure!
		//

		return;
	}

	irp->AssociatedIrp.SystemBuffer = StandardInformation;

	irp->UserEvent = &event;

	irp->UserIosb = IoStatusBlock;

	irp->Tail.Overlay.Thread = PsGetCurrentThread();

	irp->Tail.Overlay.OriginalFileObject = FileObject;

	irp->RequestorMode = KernelMode;

	//
	// Initialize the event
	//

	KeInitializeEvent(&event, SynchronizationEvent, FALSE);

	//
	// Set up the I/O stack location.
	//

	ioStackLocation = IoGetNextIrpStackLocation(irp);

	ioStackLocation->MajorFunction = IRP_MJ_QUERY_INFORMATION;

	ioStackLocation->DeviceObject = fsdDevice;

	ioStackLocation->FileObject = FileObject;

	ioStackLocation->Parameters.QueryFile.Length = sizeof(FILE_STANDARD_INFORMATION);

	ioStackLocation->Parameters.QueryFile.FileInformationClass = FileStandardInformation;

	//
	// Set the completion routine.
	//

	IoSetCompletionRoutine(irp, KfcIoCompletion, 0, TRUE, TRUE, TRUE);

	//
	// Send it to the FSD
	//

	(void) IoCallDriver(fsdDevice, irp);

	//
	// Wait for the I/O
	//

	KeWaitForSingleObject(&event, Executive, KernelMode, TRUE, 0);

	//
	// Done!
	//

	return;

}


NTSTATUS 
KfcIoCompletion(
				PDEVICE_OBJECT DeviceObject,
				PIRP Irp,
				PVOID Context
				)
				//++
				// Function:	KfcIoCompletion
				//
				// Description:
				//		This routine is used to handle I/O (read OR write) completion
				//
				// Arguments:
				//		DeviceObject - not used
				//		Irp - the I/O operation being completed
				//		Context - not used
				//
				// Return value:
				//		STATUS_MORE_PROCESSING_REQUIRED
				//	
				// Notice :
				//		This function is provided by OSR
				//
				// Notes:
				//		The purpose of this routine is to do "cleanup" on I/O operations
				//  so we don't constantly throw away perfectly good MDLs as part of
				//  completion processing.
				//
{
	//
	// Copy the status information back into the "user" IOSB.
	//

	*Irp->UserIosb = Irp->IoStatus;

	//
	// Set the user event - wakes up the mainline code doing this.
	// So that we can jump out of KeWaitForSingleObject() in my routine
	//

	KeSetEvent(Irp->UserEvent, 0, FALSE);


	//
	// Free the IRP now that we are done with it.
	//

	IoFreeIrp(Irp);

	//
	// We return STATUS_MORE_PROCESSING_REQUIRED because this "magic" return value
	// tells the I/O Manager that additional processing will be done by this driver
	// to the IRP - in fact, it might (as it is in this case) already BE done - and
	// the IRP cannot be completed.
	//

	return STATUS_MORE_PROCESSING_REQUIRED;
}

VOID 
FsTPMRead(
			PFILE_OBJECT FileObject,
			PLARGE_INTEGER Offset,
			ULONG Length,
			PMDL Mdl,
			PIO_STATUS_BLOCK IoStatusBlock,
			PDEVICE_OBJECT pDevice
			)
			//++
			// Function:	FsTPMRead
			//
			// Description:
			//		This routine is used to read the file object to memory discribed by MDL
			//
			// Arguments:
			//		PFILE_OBJECT FileObject,
			//		PLARGE_INTEGER Offset,
			//		ULONG Length,
			//		PMDL Mdl,
			//		PIO_STATUS_BLOCK IoStatusBlock
			//
			// Return value:
			//		None
			//	
			// Notice :
			//		This function is provided by OSR
			//
{
	PIRP irp;
	KEVENT event;
	PIO_STACK_LOCATION ioStackLocation;
	PDEVICE_OBJECT fsdDevice=pDevice;
	//
	// Set up the event we'll use.
	//

	KeInitializeEvent(&event, SynchronizationEvent, FALSE);


	//
	// Allocate and build the IRP we'll be sending to the FSD.
	//

	irp = IoAllocateIrp(fsdDevice->StackSize, FALSE);

	if (!irp) {

		//
		// Allocation failed, presumably due to memory allocation failure.
		//

		IoStatusBlock->Status = STATUS_INSUFFICIENT_RESOURCES;

		IoStatusBlock->Information = 0;

	}

	irp->MdlAddress = Mdl;

	irp->UserEvent = &event;

	irp->UserIosb = IoStatusBlock;

	irp->Tail.Overlay.Thread = PsGetCurrentThread();

	irp->Tail.Overlay.OriginalFileObject= FileObject;

	irp->RequestorMode = KernelMode;


	//
	// Indicate that this is a READ operation.
	//

	irp->Flags = IRP_READ_OPERATION;


	//
	// Set up the next I/O stack location.  These are the parameters
	// that will be passed to the underlying driver.
	//

	ioStackLocation = IoGetNextIrpStackLocation(irp);

	ioStackLocation->MajorFunction = IRP_MJ_READ;

	ioStackLocation->MinorFunction = 0;

	ioStackLocation->DeviceObject = fsdDevice;

	ioStackLocation->FileObject = FileObject;


	//
	// We use a completion routine to keep the I/O Manager from doing
	// "cleanup" on our IRP - like freeing our MDL.
	//

	IoSetCompletionRoutine(irp, KfcIoCompletion, 0, TRUE, TRUE, TRUE);

	ioStackLocation->Parameters.Read.Length = Length;

	ioStackLocation->Parameters.Read.ByteOffset = *Offset;


	//
	// Send it on.  Ignore the return code.
	//

	(void) IoCallDriver(fsdDevice, irp);


	//
	// Wait for the I/O to complete.
	//

	KeWaitForSingleObject(&event, Executive, KernelMode, TRUE, 0);


	//
	// Done.  Return results are in the io status block.
	//

	return;
}



VOID 
FsTPMSetFileAllocation(
						 PFILE_OBJECT FileObject,
						 PLARGE_INTEGER AllocationSize,
						 PIO_STATUS_BLOCK IoStatusBlock,
						 PDEVICE_OBJECT   pDevice
						 )
						 //++
						 // Function:	FsTPMSetFileAllocation
						 //
						 // Description:
						 //		This routine sets a file's ALLOCATION size to the specified value.
						 //  Note that this DOES NOT extend the file's EOF.
						 //
						 // Arguments:
						 //		FileObject - the file on which to set the allocation size
						 //		AllocationSize - the new allocation size
						 //	    IoStatusBlock - the results of this operation
						 //
						 // Return value:
						 //		None
						 //	
						 // Notice :
						 //		This function is provided by OSR
						 //--
{
	PIRP irp;
	KEVENT event;
	PIO_STACK_LOCATION ioStackLocation;
	PDEVICE_OBJECT fsdDevice=pDevice;

	//
	// Allocate an irp for this request.  This could also come from a 
	// private pool, for instance.
	//

	irp = IoAllocateIrp(fsdDevice->StackSize, FALSE);

	if (!irp) {
		//
		// Failure!
		//

		return;
	}

	irp->AssociatedIrp.SystemBuffer = AllocationSize;

	irp->UserEvent = &event;

	irp->UserIosb = IoStatusBlock;

	irp->Tail.Overlay.Thread = PsGetCurrentThread();

	irp->Tail.Overlay.OriginalFileObject = FileObject;

	irp->RequestorMode = KernelMode;


	//
	// Initialize the event
	//

	KeInitializeEvent(&event, SynchronizationEvent, FALSE);


	//
	// Set up the I/O stack location.
	//

	ioStackLocation = IoGetNextIrpStackLocation(irp);

	ioStackLocation->MajorFunction = IRP_MJ_SET_INFORMATION;

	ioStackLocation->DeviceObject = fsdDevice;

	ioStackLocation->FileObject = FileObject;

	ioStackLocation->Parameters.SetFile.Length = sizeof(LARGE_INTEGER);

	ioStackLocation->Parameters.SetFile.FileInformationClass = FileAllocationInformation;

	ioStackLocation->Parameters.SetFile.FileObject = 0; // not used for allocation

	ioStackLocation->Parameters.SetFile.AdvanceOnly = FALSE;

	//
	// Set the completion routine.
	//

	IoSetCompletionRoutine(irp, KfcIoCompletion, 0, TRUE, TRUE, TRUE);

	//
	// Send it to the FSD
	//

	(void) IoCallDriver(fsdDevice, irp);

	//
	// Wait for the I/O
	//

	KeWaitForSingleObject(&event, Executive, KernelMode, TRUE, 0);

	//
	// Done!
	//

	return;
}

VOID 
FsTPMWrite(
			 PFILE_OBJECT FileObject,
			 PLARGE_INTEGER Offset,
			 ULONG Length,
			 PMDL Mdl,
			 PIO_STATUS_BLOCK IoStatusBlock,
			 PDEVICE_OBJECT   pDevice
			 )
			 //++
			 // Function:	FsTPMWrite
			 //
			 // Description:
			 //		This routine is used to write to the file object from memory discribed by MDL
			 //
			 // Arguments:
			 //		PFILE_OBJECT FileObject,
			 //		PLARGE_INTEGER Offset,
			 //		ULONG Length,
			 //		PMDL Mdl,
			 //		PIO_STATUS_BLOCK IoStatusBlock
			 //
			 // Return value:
			 //		None
			 //	
			 // Notice :
			 //		This function is provided by OSR
			 //
{
	PIRP irp;
	KEVENT event;
	PIO_STACK_LOCATION ioStackLocation;
	PDEVICE_OBJECT fsdDevice =pDevice;

	//
	// Set up the event we'll use.
	//

	KeInitializeEvent(&event, SynchronizationEvent, FALSE);


	//
	// Allocate and build the IRP we'll be sending to the FSD.
	//

	irp = IoAllocateIrp(fsdDevice->StackSize, FALSE);

	if (!irp) {

		//
		// Allocation failed, presumably due to memory allocation failure.
		//

		IoStatusBlock->Status = STATUS_INSUFFICIENT_RESOURCES;

		IoStatusBlock->Information = 0;

	}

	irp->MdlAddress = Mdl;

	irp->UserEvent = &event;

	irp->UserIosb = IoStatusBlock;

	irp->Tail.Overlay.Thread = PsGetCurrentThread();

	irp->Tail.Overlay.OriginalFileObject= FileObject;

	irp->RequestorMode = KernelMode;


	//
	// Indicate that this is a WRITE operation.
	//

	irp->Flags = IRP_WRITE_OPERATION;


	//
	// Set up the next I/O stack location.  These are the parameters
	// that will be passed to the underlying driver.
	//

	ioStackLocation = IoGetNextIrpStackLocation(irp);

	ioStackLocation->MajorFunction = IRP_MJ_WRITE;

	ioStackLocation->MinorFunction = 0;

	ioStackLocation->DeviceObject = fsdDevice;

	ioStackLocation->FileObject = FileObject;


	//
	// We use a completion routine to keep the I/O Manager from doing
	// "cleanup" on our IRP - like freeing our MDL.
	//

	IoSetCompletionRoutine(irp, KfcIoCompletion, 0, TRUE, TRUE, TRUE);

	ioStackLocation->Parameters.Write.Length = Length;

	ioStackLocation->Parameters.Write.ByteOffset = *Offset;


	//
	// Send it on.  Ignore the return code.
	//

	(void) IoCallDriver(fsdDevice, irp);


	//
	// Wait for the I/O to complete.
	//

	KeWaitForSingleObject(&event, Executive, KernelMode, TRUE, 0);


	//
	// Done.  Return results are in the io status block.
	//

	return;

}


//-----------------------------------------------------------------------------
/*++
The following functions

Abstract:
This module implements routines to support synchronous API calls to
the next lower file system driver.

Revision History:

02-01-2002 : created

Note:
Thank OSR and Mr. Paul for providing some useful information
--*/


VOID FsTPMReferenceDeviceAndVpb(IN PFILE_OBJECT FileObject)
{
	//	NTSTATUS Status;
	PDEVICE_OBJECT RealDevice;
	PVPB Vpb;

	//
	// Copy RealDevice and Vpb into local variables to make things easier.
	//

	RealDevice =  FileObject->DeviceObject;
	Vpb =  FileObject->Vpb;

	//ASSERT(Vpb !=  NULL ? RealDevice->Vpb !=  NULL : RealDevice->Vpb ==  NULL);

	//
	// Increment RealDevice's reference count.
	//

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -