注册表回调整体框架

注册表回调整体框架

这个就不多说了,想详细了解的可以自行百度,网上有很多相关内容

NTSTATUS DriverEntry(IN PDRIVER_OBJECT DriverObject, IN PUNICODE_STRING RegistryPath)
{
 	NTSTATUS ntStatus;
	ntStatus = CmRegisterCallback(MyRegistryCallback, NULL,  &pCookie);
	
	return ntStatus;
}
//see demo:
//7eightl-minifilter\Demo\REG-hips






NTSTATUS HOOK_PreNtDeleteKey(PREG_DELETE_KEY_INFORMATION Data)
{
	NTSTATUS status = 0;
	PUNICODE_STRING keyName;
	UNICODE_STRING uTarget;




	return STATUS_SUCCESS;
}


NTSTATUS MyRegistryCallback(__in PVOID CallbackContext,__in_opt PVOID Argument1,            / / REG_NOTIFY_CLASS  __in_opt PVOID Argument2            //  KEY_INFORMATION ){
            switch( (REG_NOTIFY_CLASS) Argument1)
{
         case RegNtPreDeleteKey :
return HOOK_PreNtDeleteKey((PREG_DELETE_KEY_INFORMATION) Argument2);
          case RegNtPreRenameKey:
return HOOK_PreNtRenameKey((PREG_RENAME_KEY_INFORMATION) Argument2);
          case RegNtPreCreateKeyEx:	 // pre 操作
 return HOOK_PreNtCreateKeyEx((PREG_CREATE_KEY_INFORMATION) Argument2);
          case RegNtPostCreateKeyEx :    // post 操作
return HOOK_PostNtCreateKeyEx((PRGG_POST_OPERATION_INFORMATION )}
   }      
}                                                                                                                                  }




main.c
#include "precomp.h"


#define		DEVICE_NAME					L"\\device\\HipsRegDrv"
#define		LINK_NAME					L"\\dosDevices\\HipsRegDrv"




// function to dispatch the IRPs
NTSTATUS DispatchOK(PDEVICE_OBJECT DeviceObject, PIRP Irp)
{
   Irp->IoStatus.Status = STATUS_SUCCESS;
   IoCompleteRequest(Irp,IO_NO_INCREMENT);
   return STATUS_SUCCESS;
}


VOID DriverUnload (
    IN PDRIVER_OBJECT	pDriverObject) 
{
	UNICODE_STRING strLink;
	RtlInitUnicodeString(&strLink, LINK_NAME);
	stopRegMon();


	IoDeleteSymbolicLink(&strLink);
	IoDeleteDevice(pDriverObject->DeviceObject);


	DbgPrint(" Unloaded\n"); 
}




NTSTATUS DriverEntry(IN PDRIVER_OBJECT pDriverObject, IN PUNICODE_STRING pRegistryPath)
{
    UNICODE_STRING 	DeviceName;
    UNICODE_STRING 	LinkName;  
    NTSTATUS 		status; 
    PDEVICE_OBJECT 	pDriverDeviceObject;  
	ULONG i;
    
    //DbgPrint("Driver loaded.");
    pDriverObject->DriverUnload = DriverUnload;   
    
    // init strings
    RtlInitUnicodeString(&DeviceName, DEVICE_NAME);
    RtlInitUnicodeString(&LinkName, LINK_NAME);
    
    // to communicate with usermode, we need a device
    status = IoCreateDevice(
           pDriverObject,        // ptr to caller object
           0,  // extension device allocated byte number
           &DeviceName,         // device name 
           FILE_DEVICE_UNKNOWN, 
           0,                   // no special caracteristics
           FALSE,               // we can open many handles in same time
           &pDriverDeviceObject); // [OUT] ptr to the created object
           
    if ( !NT_SUCCESS(status) ) 
       return STATUS_NO_SUCH_DEVICE;
    
	pDriverDeviceObject-> Flags |= DO_BUFFERED_IO;


    // we also need a symbolic link
    status = IoCreateSymbolicLink(&LinkName,&DeviceName);
    if( !NT_SUCCESS(status) ) 
    {
		IoDeleteDevice( pDriverDeviceObject );
        return STATUS_NO_SUCH_DEVICE;
    }  


    for (i = 0; i < IRP_MJ_MAXIMUM_FUNCTION; i++)
		pDriverObject->MajorFunction[i] = DispatchOK; 
    


    startRegMon(pDriverObject);
    //Do other things...   
    
    return STATUS_SUCCESS;
}


precomp.h
#ifndef _PRECOMP_H_
#define _PRECOMP_H_
#include <ntifs.h>
#include <ntddk.h>
#include <windef.h>
#include "regmon.h"
#endif


regmon.c
#include "precomp.h"


GENERIC_MAPPING g_KeyMapping = {KEY_READ, KEY_WRITE, KEY_EXECUTE, KEY_ALL_ACCESS};
static WCHAR g_wszAltitude[] = L"370020";


PGENERIC_MAPPING IoGetKeyGenericMapping( )
{
	return &g_KeyMapping;
}


BOOL MyObQueryObjectName(HANDLE hObjHandle, PUNICODE_STRING ustrObjectName, BOOL bNeedAllocateName)
{
	PVOID			pQueryBuffer		= NULL;
	DWORD			dwReqSize			= 0;
	NTSTATUS		ntStatus			= 0;
	__try
	{
		dwReqSize = sizeof(OBJECT_NAME_INFORMATION) + (MAX_PATH + 32)*sizeof(WCHAR);
		
		pQueryBuffer = ExAllocatePoolWithTag(PagedPool, dwReqSize, 'RFLM');
		
		if(pQueryBuffer == NULL)
			return FALSE;
		
		ntStatus = ZwQueryObject(hObjHandle, 
			ObjectNameInfo,
			pQueryBuffer,
			dwReqSize,
			&dwReqSize);
		
		if((ntStatus == STATUS_INFO_LENGTH_MISMATCH) ||
			(ntStatus == STATUS_BUFFER_OVERFLOW) ||
			(ntStatus == STATUS_BUFFER_TOO_SMALL))
		{
			ExFreePool(pQueryBuffer);
			pQueryBuffer = NULL;
			
			pQueryBuffer = ExAllocatePoolWithTag(PagedPool, dwReqSize, 'RFLM');
			
			if(pQueryBuffer == NULL)
			{
				return FALSE;
			}
			
			ntStatus = ZwQueryObject(hObjHandle, 
				ObjectNameInfo,
				pQueryBuffer,
				dwReqSize,
				&dwReqSize);
			
		}
		
		if(NT_SUCCESS(ntStatus))
		{ 
			OBJECT_NAME_INFORMATION * pNameInfo = (OBJECT_NAME_INFORMATION *)pQueryBuffer;
			
			if(bNeedAllocateName)
			{
				ustrObjectName->Buffer = ExAllocatePoolWithTag(PagedPool, pNameInfo->Name.Length + sizeof(WCHAR), 'RFLM');
				
				if(ustrObjectName->Buffer)
				{
					RtlZeroMemory(ustrObjectName->Buffer, pNameInfo->Name.Length + sizeof(WCHAR));
					ustrObjectName->Length = 0;
					ustrObjectName->MaximumLength = pNameInfo->Name.Length;
					RtlCopyUnicodeString(ustrObjectName, &pNameInfo->Name);
				}
				else
					ntStatus = STATUS_INSUFFICIENT_RESOURCES;
				
			}
			else
				RtlCopyUnicodeString(ustrObjectName, &pNameInfo->Name);
		}
	}
	__except(EXCEPTION_EXECUTE_HANDLER)
	{
		ntStatus = GetExceptionCode();
	}
	
	if(pQueryBuffer)
	{
		ExFreePool(pQueryBuffer);
		pQueryBuffer = NULL;
	}
	
	return NT_SUCCESS(ntStatus);
}




LARGE_INTEGER g_RegCookie;


#if (NTDDI_VERSION >= NTDDI_VISTA)
NTSTATUS TlGetObjectNameOnVistaAndLater(PVOID Object, PUNICODE_STRING Name)
{
	PUNICODE_STRING			pKeyName = NULL;
	NTSTATUS				ntStatus = 0;


	if(Object == NULL || Name == NULL)
		return STATUS_INVALID_PARAMETER;


	ntStatus = CmCallbackGetKeyObjectID(&g_RegCookie,
									  Object,
									  NULL,
									 &pKeyName);


	if(NT_SUCCESS(ntStatus) == FALSE)
	{
		return ntStatus;
	}


	Name->Buffer = ( PWCHAR )ExAllocatePoolWithTag( 
							PagedPool, 
							pKeyName->Length,
							'RFLM'
							);


	if(Name->Buffer == NULL)
	{
		return STATUS_INSUFFICIENT_RESOURCES;
	}


	RtlZeroMemory(Name->Buffer, pKeyName->Length);


	Name->Length = 0;
	Name->MaximumLength = pKeyName->Length;


	RtlCopyUnicodeString(Name, pKeyName);
	return STATUS_SUCCESS;
}
#endif


NTSTATUS TlGetObjectNameOnXP(PVOID Object, PUNICODE_STRING Name)
{
	UNICODE_STRING				ustrKeyName				= {0};
	HANDLE						ObjectHandle			= NULL;
	NTSTATUS					ntStatus				= 0;


	if(Object == NULL || Name == NULL)
		return STATUS_INVALID_PARAMETER;


	ntStatus = ObOpenObjectByPointer(Object,
							  OBJ_KERNEL_HANDLE ,
							  0,
							  0,
							  NULL,
							  KernelMode,
							  &ObjectHandle);


	if(NT_SUCCESS(ntStatus) == FALSE)
	{
		return ntStatus;
	}


	if(MyObQueryObjectName(ObjectHandle, &ustrKeyName, TRUE) == FALSE)
	{
		ZwClose(ObjectHandle);
		return STATUS_INSUFFICIENT_RESOURCES;
	}
	
	ZwClose(ObjectHandle);


	Name->Buffer = ( PWCHAR )ExAllocatePoolWithTag( 
							PagedPool, 
							ustrKeyName.Length,
							'RFLM'
							);


	if(Name->Buffer == NULL)
	{
		return STATUS_INSUFFICIENT_RESOURCES;
	}


	RtlZeroMemory(Name->Buffer, ustrKeyName.Length);


	Name->Length = 0;
	Name->MaximumLength = ustrKeyName.Length;


	RtlCopyUnicodeString(Name, &ustrKeyName);
	ExFreePool(ustrKeyName.Buffer);


	return STATUS_SUCCESS;
}


NTSTATUS TlGetObjectFullName(PVOID Object, PUNICODE_STRING Name)
{
#if (NTDDI_VERSION >= NTDDI_LONGHORN)
	return TlGetObjectNameOnVistaAndLater(Object, Name);
#else
	return TlGetObjectNameOnXP(Object, Name);
#endif
}




NTSTATUS MyDeleteKey(PREG_DELETE_KEY_INFORMATION Data)
{
	NTSTATUS			ntStatus		= 0;
	UNICODE_STRING		ustrKeyName		= {0};


	__try
	{


		if((ExGetPreviousMode() == KernelMode))
		{
			return STATUS_SUCCESS;
		}


		if(NT_SUCCESS(TlGetObjectFullName(Data->Object, &ustrKeyName)) == FALSE)
		{
			return STATUS_SUCCESS;
		}
		DbgPrint("DeleteKey Key:%wZ\n", &ustrKeyName);


		ExFreePool(ustrKeyName.Buffer);


	}
	__except(EXCEPTION_EXECUTE_HANDLER)
	{
	}


	return STATUS_SUCCESS;
}


NTSTATUS MySetValueKey(PREG_SET_VALUE_KEY_INFORMATION Data)
{
	NTSTATUS				ntStatus				= 0;
	UNICODE_STRING			ustrKeyName				= {0};
	UNICODE_STRING			ustrTarget				= {0};
	WCHAR					wszKeyPath[MAX_PATH]	= {0};


	__try
	{
		
		if((ExGetPreviousMode() == KernelMode))
		{
			return STATUS_SUCCESS;
		}


		if(NT_SUCCESS(TlGetObjectFullName(Data->Object, &ustrKeyName)) == FALSE)
		{


			return STATUS_SUCCESS;
		}


		ustrTarget.Buffer = wszKeyPath;
		ustrTarget.MaximumLength = MAX_PATH * sizeof(WCHAR);
		
		RtlCopyUnicodeString(&ustrTarget, &ustrKeyName);




		ExFreePool(ustrKeyName.Buffer);


		if (ustrTarget.Buffer[ustrTarget.Length/sizeof(WCHAR) - 1] != L'\\' )
			RtlAppendUnicodeToString(&ustrTarget, L"\\");


		RtlAppendUnicodeStringToString(&ustrTarget, Data->ValueName);
		DbgPrint("SetValueKey Key:%wZ\n", &ustrTarget);


	}
	__except(EXCEPTION_EXECUTE_HANDLER)
	{


	}


	return STATUS_SUCCESS;
}


NTSTATUS MyDeleteValueKey(PREG_DELETE_VALUE_KEY_INFORMATION Data)
{
	NTSTATUS				ntStatus				= 0;
	UNICODE_STRING			ustrKeyName				= {0};
	UNICODE_STRING			ustrTarget				= {0};
	WCHAR					wszKeyPath[MAX_PATH]	= {0};




	__try
	{


		if((ExGetPreviousMode() == KernelMode))
		{
			return STATUS_SUCCESS;
		}


		if(NT_SUCCESS(TlGetObjectFullName(Data->Object, &ustrKeyName)) == FALSE)
		{
			return STATUS_SUCCESS;
		}


		ustrTarget.Buffer = wszKeyPath;
		ustrTarget.MaximumLength = MAX_PATH * sizeof(WCHAR);
		
		RtlCopyUnicodeString(&ustrTarget, &ustrKeyName);


		ExFreePool(ustrKeyName.Buffer);


		if (ustrTarget.Buffer[ustrTarget.Length/sizeof(WCHAR) - 1]!=L'\\' )
			RtlAppendUnicodeToString(&ustrTarget, L"\\");


		RtlAppendUnicodeStringToString(&ustrTarget, Data->ValueName);
		DbgPrint("DeleteValueKey Key:%wZ\n", &ustrTarget);


	}
	__except(EXCEPTION_EXECUTE_HANDLER)
	{


	}


	return STATUS_SUCCESS;
}


NTSTATUS MyRenameKey(PREG_RENAME_KEY_INFORMATION Data)
{
	NTSTATUS				ntStatus	= 0;
	UNICODE_STRING			ustrKeyName = {0};
	
	__try
	{
		if((ExGetPreviousMode() == KernelMode))
		{
			return STATUS_SUCCESS;
		}


		if(NT_SUCCESS(TlGetObjectFullName(Data->Object, &ustrKeyName)) == FALSE)
		{
			return STATUS_SUCCESS;
		}


		DbgPrint("RenameKey Key:%wZ\n", &ustrKeyName);


		ExFreePool(ustrKeyName.Buffer);




	}
	__except(EXCEPTION_EXECUTE_HANDLER)
	{


	}


	return STATUS_SUCCESS;
}


NTSTATUS MyCreateKey(PREG_PRE_CREATE_KEY_INFORMATION Data)
{
	NTSTATUS			ntStatus				= 0;
	UNICODE_STRING		ustrTarget				= {0};
	WCHAR				wszKeyName[MAX_PATH]	= {0};


	__try
	{
		if((ExGetPreviousMode() == KernelMode))
		{
			return STATUS_SUCCESS;
		}
		
		ustrTarget.Buffer = wszKeyName;
		ustrTarget.MaximumLength = MAX_PATH * sizeof(WCHAR);
		
		RtlCopyUnicodeString(&ustrTarget, Data->CompleteName);
		DbgPrint("CreateKey Key:%wZ\n", &ustrTarget);
	}
	__except(EXCEPTION_EXECUTE_HANDLER)
	{
	}


	return STATUS_SUCCESS;
}


NTSTATUS MyCreateKeyEx(PREG_CREATE_KEY_INFORMATION Data)
{
	NTSTATUS			ntStatus	= 0;
	UNICODE_STRING		ustrKeyName	= {0};
	UNICODE_STRING		ustrTarget	= {0};


	__try
	{
		if((ExGetPreviousMode() == KernelMode))
		{


			return STATUS_SUCCESS;
		}


		if(NT_SUCCESS(TlGetObjectFullName(Data->RootObject, &ustrKeyName)) == FALSE)
		{


			return STATUS_SUCCESS;
		}


		ustrTarget.MaximumLength = MAX_PATH * sizeof(WCHAR);
		
		RtlCopyUnicodeString(&ustrTarget, &ustrKeyName);


		ExFreePool(ustrKeyName.Buffer);
		
		if(Data->CompleteName)
		{
			RtlAppendUnicodeToString(&ustrTarget, L"\\");
			RtlAppendUnicodeStringToString(&ustrTarget, Data->CompleteName);
		}


		DbgPrint("CreateKeyEx :%wZ\n", ustrTarget);


	}
	__except(EXCEPTION_EXECUTE_HANDLER)
	{


	}


	return STATUS_SUCCESS;
}




NTSTATUS MyRegCallback
(
	PVOID CallbackContext, 
	PVOID Argument1, 
	PVOID Argument2
)
{
	switch( (REG_NOTIFY_CLASS) Argument1)
	{
	case RegNtPreDeleteKey :
		return MyDeleteKey((PREG_DELETE_KEY_INFORMATION) Argument2);
	case RegNtPreSetValueKey:
		return MySetValueKey((PREG_SET_VALUE_KEY_INFORMATION) Argument2);
	case RegNtPreDeleteValueKey:
		return MyDeleteValueKey((PREG_DELETE_VALUE_KEY_INFORMATION) Argument2);
	case RegNtPreRenameKey:
		return MyRenameKey((PREG_RENAME_KEY_INFORMATION) Argument2);
	case RegNtPreCreateKey:
		return MyCreateKey((PREG_PRE_CREATE_KEY_INFORMATION) Argument2);	
	case RegNtPreCreateKeyEx:
		return MyCreateKeyEx((PREG_CREATE_KEY_INFORMATION) Argument2);


	}


	return STATUS_SUCCESS;
}


NTSTATUS startRegMon(PDRIVER_OBJECT driverObject)
{
#if (NTDDI_VERSION >= NTDDI_VISTA)
	UNICODE_STRING uAltitude;


	RtlInitUnicodeString(&uAltitude, g_wszAltitude);
	return CmRegisterCallbackEx(MyRegCallback,
						  &uAltitude,
						  driverObject,
						  NULL,
						  &g_RegCookie,
						  NULL);	
#else
	return CmRegisterCallback(MyRegCallback,
							  NULL,
							 &g_RegCookie);


#endif
						  
}


VOID stopRegMon( )
{
	CmUnRegisterCallback(g_RegCookie);
}






regmon.c
#ifndef __REGMON_H__
#define __REGMON_H__


typedef enum _OBJECT_INFO_CLASS {
    ObjectBasicInfo,
		ObjectNameInfo,
		ObjectTypeInfo,
		ObjectAllTypesInfo,
		ObjectProtectionInfo
} OBJECT_INFO_CLASS;




PGENERIC_MAPPING IoGetKeyGenericMapping( );


NTSTATUS 
MyRegCallback
(
	PVOID CallbackContext, 
	PVOID Argument1, 
	PVOID Argument2
);




NTSTATUS startRegMon(PDRIVER_OBJECT driverObject);
VOID stopRegMon( );




#endif







可以参考TA的教程
  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值