您的位置:首页 > 其它

枚举移除LoadImageNotifyRoutine

2016-11-11 19:02 561 查看
#include <ntddk.h>
#include <Ntstrsafe.h>

#ifdef _WIN64
#define PSP_MAX_LOAD_IMAGE_NOTIFY 64
#else
#define PSP_MAX_LOAD_IMAGE_NOTIFY 8
#endif
ULONG_PTR PspLoadImageNotifyRoutine;
ULONG_PTR PspLoadImageNotifyRoutineCount;

DWORD                   g_OsVersion;                                            //系统版本
//操作系统版本
#define WINXP                   51
#define WIN7                    61
#define WIN8                    62
#define WIN81                   63
#define WIN10                   100

//获取系统版本
BOOLEAN GetOsVer(void);

//获取PspLoadImageNotifyRoutineCount
ULONG_PTR GetPspLoadImageNotifyRoutineCount(void);

//获取PspLoadImageNotifyRoutine
ULONG_PTR GetPspLoadImageNotifyRoutine(void);

//枚举移除LoadImageNotifyRoutine
NTSTATUS EnumRemoveLoadImageNotifyRoutine(void);

VOID loadImageNotifyRoutine(PUNICODE_STRING  FullImageName, HANDLE  ProcessId, PIMAGE_INFO  ImageInfo);

VOID DriverUnload(IN PDRIVER_OBJECT DriverObject)
{
PsRemoveLoadImageNotifyRoutine(loadImageNotifyRoutine);
return;
}

NTSTATUS DriverEntry(IN PDRIVER_OBJECT DriverObject, IN PUNICODE_STRING RegistryPath)
{
DriverObject->DriverUnload = DriverUnload;
PsSetLoadImageNotifyRoutine(loadImageNotifyRoutine);

DbgBreakPoint();

//枚举移除LoadImageNotifyRoutine
EnumRemoveLoadImageNotifyRoutine();
return STATUS_SUCCESS;
}

VOID loadImageNotifyRoutine( PUNICODE_STRING  FullImageName,  HANDLE  ProcessId,  PIMAGE_INFO  ImageInfo)
{

return;
}

//枚举移除LoadImageNotifyRoutine
NTSTATUS EnumRemoveLoadImageNotifyRoutine(void)
{
ULONG i;
PVOID MagicPtr, NotifyAddr;

//获取系统版本
if (GetOsVer() == FALSE)return STATUS_UNSUCCESSFUL;

//获取PspLoadImageNotifyRoutineCount
PspLoadImageNotifyRoutineCount=GetPspLoadImageNotifyRoutineCount();
if (PspLoadImageNotifyRoutineCount <= 0 || PspLoadImageNotifyRoutineCount>PSP_MAX_LOAD_IMAGE_NOTIFY)return STATUS_UNSUCCESSFUL;

//获取PspLoadImageNotifyRoutine
PspLoadImageNotifyRoutine=GetPspLoadImageNotifyRoutine();
if (PspLoadImageNotifyRoutine == NULL)return STATUS_UNSUCCESSFUL;

#ifdef _WIN64
for (i = 0; i < PspLoadImageNotifyRoutineCount; i++)
{
MagicPtr = (PVOID)((PUCHAR)PspLoadImageNotifyRoutine + i * sizeof(ULONG_PTR));
if (MagicPtr==NULL)continue;

NotifyAddr = *(PULONG_PTR)(MagicPtr);
if (NotifyAddr==NULL)continue;

if (MmIsAddressValid(NotifyAddr) && NotifyAddr != 0)
{
NotifyAddr = *(PULONG_PTR)(((ULONG_PTR)NotifyAddr & 0xfffffffffffffff0ui64) + sizeof(EX_RUNDOWN_REF));

DbgPrint("LoadImageNotify at %llx", NotifyAddr);
PsRemoveLoadImageNotifyRoutine(NotifyAddr);
}
}

#else
for (i = 0; i < PspLoadImageNotifyRoutineCount; i++)
{
//PEX_CALLBACK_ROUTINE_BLOCK Point = (PEX_CALLBACK_ROUTINE_BLOCK)((Ref->Value >> 3) << 3);
MagicPtr = (PVOID)((PUCHAR)PspLoadImageNotifyRoutine + i * sizeof(ULONG_PTR));
if (MagicPtr == NULL)continue;

NotifyAddr = *(PULONG_PTR)(MagicPtr);
if (NotifyAddr == NULL)continue;

if (MmIsAddressValid(NotifyAddr) && NotifyAddr != 0)
{
//NotifyAddr = (ULONG)(Point->Function)
NotifyAddr = *(PULONG_PTR)(((ULONG_PTR)NotifyAddr & 0xfffffff8) + sizeof(EX_RUNDOWN_REF));
DbgPrint("LoadImageNotify at %x", NotifyAddr);
PsRemoveLoadImageNotifyRoutine(NotifyAddr);
}
}

#endif

return STATUS_SUCCESS;
}

//获取PspLoadImageNotifyRoutineCount
ULONG_PTR GetPspLoadImageNotifyRoutineCount(void)
{
//定义变量
ULONG_PTR i = 0;
LONG OffsetAddr64 = 0;
ULONG_PTR OffsetAddr = 0;
ULONG_PTR RoutineCount = 0;
PULONG_PTR pRoutineCountAdd = NULL;
ULONG_PTR pRemoveLoadImageNotifyRoutine = NULL;
UNICODE_STRING unstrFunc;
RtlInitUnicodeString(&unstrFunc, L"PsRemoveLoadImageNotifyRoutine");

//获取函数地址
pRemoveLoadImageNotifyRoutine = (ULONG_PTR)MmGetSystemRoutineAddress(&unstrFunc);
if (pRemoveLoadImageNotifyRoutine == NULL)return 0;

#ifdef _WIN64
switch (g_OsVersion)
{
case WIN7:
{
//fffff800`040cb000 c3              ret
//fffff800`040cb001 f044013d3795d6ff lock add dword ptr[nt!PspLoadImageNotifyRoutineCount(fffff800`03e34540)], r15d
// ffd69537+7+fffff800040cb001
// fffff80003e34540-7-fffff800040cb001=ffd69537
for (i = pRemoveLoadImageNotifyRoutine; i < pRemoveLoadImageNotifyRoutine + 0xff; i++)
{
if (*(PUCHAR)i == 0xc3 && *(PUCHAR)(i + 1) == 0xf0 && *(PUCHAR)(i + 2) == 0x44 && *(PUCHAR)(i + 3) == 0x01 && *(PUCHAR)(i + 4) == 0x3d)
{
RtlCopyMemory(&OffsetAddr64, (PUCHAR)(i + 5), sizeof(DWORD));
OffsetAddr = OffsetAddr64 + 9 + i;
break;
}
}
}
break;
case WIN8:
case WIN81:
case WIN10:
{
//fffff802`d0807275 c3              ret
//fffff802`d0807276 f044012d8207d1ff lock add dword ptr[nt!PspLoadImageNotifyRoutineCount(fffff802`d0517a00)], r13d
for (i = pRemoveLoadImageNotifyRoutine; i < pRemoveLoadImageNotifyRoutine + 0xff; i++)
{
if (*(PUCHAR)i == 0xc3 && *(PUCHAR)(i + 1) == 0xf0 && *(PUCHAR)(i + 2) == 0x44 && *(PUCHAR)(i + 3) == 0x01 && *(PUCHAR)(i + 4) == 0x2d)
{
RtlCopyMemory(&OffsetAddr64, (PUCHAR)(i + 5), sizeof(DWORD));
OffsetAddr = OffsetAddr64 + 9 + i;
break;
}
}
}
break;
default:
break;
}

#else
switch (g_OsVersion)
{
case WINXP:
{
//805c7247 b8ffffffff      mov     eax,0FFFFFFFFh
//805c724c b968b25580      mov     ecx, offset nt!PspLoadImageNotifyRoutineCount(8055b268)
for (i = pRemoveLoadImageNotifyRoutine; i < pRemoveLoadImageNotifyRoutine + 0xff; i++)
{
if (*(PUCHAR)i == 0xb8 && *(PUCHAR)(i + 1) == 0xff && *(PUCHAR)(i + 2) == 0xff && *(PUCHAR)(i + 3) == 0xff && *(PUCHAR)(i + 4) == 0xff && *(PUCHAR)(i + 5) == 0xb9)
{
RtlCopyMemory(&OffsetAddr,(PUCHAR)(i + 6),sizeof(ULONG_PTR));
break;
}
}
}
break;
case WIN7:
{
//83f236a9 c20400          ret     4
//83f236ac b8a06bd883      mov     eax, offset nt!PspLoadImageNotifyRoutineCount(83d86ba0)
for (i = pRemoveLoadImageNotifyRoutine; i < pRemoveLoadImageNotifyRoutine + 0xff; i++)
{
if (*(PUCHAR)i == 0xc2 && *(PUCHAR)(i + 1) == 0x04 && *(PUCHAR)(i + 2) == 0x00 && *(PUCHAR)(i + 3) == 0xb8)
{
RtlCopyMemory(&OffsetAddr, (PUCHAR)(i + 4), sizeof(ULONG_PTR));
break;
}
}

}
break;
case WIN8:
case WIN81:
{
//817dccba c20400          ret     4
//817dccbd b960c95f81      mov     ecx, offset nt!PspLoadImageNotifyRoutineCount(815fc960)
for (i = pRemoveLoadImageNotifyRoutine; i < pRemoveLoadImageNotifyRoutine + 0xff; i++)
{
if (*(PUCHAR)i == 0xc2 && *(PUCHAR)(i + 1) == 0x04 && *(PUCHAR)(i + 2) == 0x00 && *(PUCHAR)(i + 3) == 0xb9)
{
RtlCopyMemory(&OffsetAddr, (PUCHAR)(i + 4), sizeof(ULONG_PTR));
break;
}
}

}
break;
case WIN10:
{
//81af7c5a c20400          ret     4
//81af7c5d f0ff0dc82dba81  lock dec dword ptr[nt!PspLoadImageNotifyRoutineCount(81ba2dc8)]
for (i = pRemoveLoadImageNotifyRoutine; i < pRemoveLoadImageNotifyRoutine + 0xff; i++)
{
if (*(PUCHAR)i == 0xc2 && *(PUCHAR)(i + 1) == 0x04 && *(PUCHAR)(i + 2) == 0x00 && *(PUCHAR)(i + 3) == 0xf0 && *(PUCHAR)(i + 4) == 0xff && *(PUCHAR)(i + 5) == 0x0d)
{
RtlCopyMemory(&OffsetAddr, (PUCHAR)(i + 6), sizeof(ULONG_PTR));
break;
}
}

}
break;
default:
return 0;
}
#endif

if (OffsetAddr && MmIsAddressValid(OffsetAddr))
{
RoutineCount = *(PULONG)(OffsetAddr);
//RoutineCount = *(PULONG_PTR)(OffsetAddr);
}
return RoutineCount;
}

//获取PspLoadImageNotifyRoutine
ULONG_PTR GetPspLoadImageNotifyRoutine(void)
{
//定义变量
ULONG_PTR i = 0;
LONG OffsetAddr64 = 0;
ULONG_PTR OffsetAddr = 0;
ULONG_PTR NotifyRoutine = 0;
ULONG_PTR pRemoveLoadImageNotifyRoutine = NULL;
UNICODE_STRING unstrFunc;
RtlInitUnicodeString(&unstrFunc, L"PsRemoveLoadImageNotifyRoutine");

//获取函数地址
pRemoveLoadImageNotifyRoutine = (ULONG_PTR)MmGetSystemRoutineAddress(&unstrFunc);
if (pRemoveLoadImageNotifyRoutine == NULL)return 0;

#ifdef _WIN64

switch (g_OsVersion)
{
case WIN7:
case WIN8:
case WIN81:
case WIN10:
{
//fffff800`040caf6e 488d0d8b95d6ff  lea     rcx, [nt!PspLoadImageNotifyRoutine(fffff800`03e34500)]
//fffff800`03e34500=ffd6958b+7+ fffff800040caf6e
for (i = pRemoveLoadImageNotifyRoutine; i < pRemoveLoadImageNotifyRoutine + 0xff; i++)
{
if (*(PUCHAR)i == 0x48 && *(PUCHAR)(i + 1) == 0x8d && *(PUCHAR)(i + 2) == 0x0d)
{
RtlCopyMemory(&OffsetAddr64, (PUCHAR)(i + 3), sizeof(DWORD));
OffsetAddr = OffsetAddr64 + 7 + i;
break;
}
}

}
break;
default:
break;
}

#else

switch (g_OsVersion)
{
case WINXP:
{
//805c7200 33db            xor     ebx, ebx
//805c7202 bf80b25580      mov     edi, offset nt!PspLoadImageNotifyRoutine(8055b280)
for (i = pRemoveLoadImageNotifyRoutine; i < pRemoveLoadImageNotifyRoutine + 0xff; i++)
{
if (*(PUCHAR)i == 0x33 && *(PUCHAR)(i + 1) == 0xdb && *(PUCHAR)(i + 2) == 0xbf)
{
RtlCopyMemory(&OffsetAddr, (PUCHAR)(i + 3), sizeof(ULONG_PTR));
break;
}
}

}
break;
case WIN7:
{

//83f23633 33db            xor     ebx, ebx
//83f23635 c745fc806bd883  mov     dword ptr[ebp - 4], offset nt!PspLoadImageNotifyRoutine(83d86b80)
for (i = pRemoveLoadImageNotifyRoutine; i < pRemoveLoadImageNotifyRoutine + 0xff; i++)
{
if (*(PUCHAR)i == 0x33 && *(PUCHAR)(i + 1) == 0xdb && *(PUCHAR)(i + 2) == 0xc7 && *(PUCHAR)(i + 3) == 0x45 && *(PUCHAR)(i + 4) == 0xfc)
{
RtlCopyMemory(&OffsetAddr, (PUCHAR)(i + 5), sizeof(ULONG_PTR));
break;
}
}
}
break;
case WIN8:
{

//817dcc48 8945fc          mov     dword ptr[ebp - 4], eax
//817dcc4b be80c95f81      mov     esi, offset nt!PspLoadImageNotifyRoutine(815fc980)
for (i = pRemoveLoadImageNotifyRoutine; i < pRemoveLoadImageNotifyRoutine + 0xff; i++)
{
if (*(PUCHAR)i == 0x89 && *(PUCHAR)(i + 1) == 0x45 && *(PUCHAR)(i + 2) == 0xfc && *(PUCHAR)(i + 3) == 0xbe)
{
RtlCopyMemory(&OffsetAddr, (PUCHAR)(i + 4), sizeof(ULONG_PTR));
break;
}
}

}
break;
case WIN81:
{
//8185f7c2 33c0            xor     eax, eax
//8185f7c4 bbe8d16081      mov     ebx, offset nt!PspLoadImageNotifyRoutine(8160d1e8)
for (i = pRemoveLoadImageNotifyRoutine; i < pRemoveLoadImageNotifyRoutine + 0xff; i++)
{
if (*(PUCHAR)i == 0x33 && *(PUCHAR)(i + 1) == 0xc0 && *(PUCHAR)(i + 2) == 0xbb)
{
RtlCopyMemory(&OffsetAddr, (PUCHAR)(i + 3), sizeof(ULONG_PTR));
break;
}
}

}
break;
case WIN10:
{
//81af7bdb 33c0            xor     eax, eax
//81af7bdd bb304a8681      mov     ebx, offset nt!PspLoadImageNotifyRoutine(81864a30)
for (i = pRemoveLoadImageNotifyRoutine; i < pRemoveLoadImageNotifyRoutine + 0xff; i++)
{
if (*(PUCHAR)i == 0x33 && *(PUCHAR)(i + 1) == 0xc0 && *(PUCHAR)(i + 2) == 0xbb)
{
RtlCopyMemory(&OffsetAddr, (PUCHAR)(i + 3), sizeof(ULONG_PTR));
break;
}
}

}
break;
default:
break;
}
#endif

if (OffsetAddr && MmIsAddressValid(OffsetAddr))
{
NotifyRoutine = OffsetAddr;
}
return NotifyRoutine;
}

//获取系统版本
BOOLEAN GetOsVer(void)
{

ULONG    dwMajorVersion = 0;
ULONG    dwMinorVersion = 0;
PsGetVersion(&dwMajorVersion, &dwMinorVersion, NULL, NULL);
if (dwMajorVersion == 5 && dwMinorVersion == 1)
g_OsVersion = WINXP;
else if (dwMajorVersion == 6 && dwMinorVersion == 1)
g_OsVersion = WIN7;
else if (dwMajorVersion == 6 && dwMinorVersion == 2)
g_OsVersion = WIN8;
else if (dwMajorVersion == 6 && dwMinorVersion == 3)
g_OsVersion = WIN81;
else if (dwMajorVersion == 10 && dwMinorVersion == 0)
g_OsVersion = WIN10;
else
{
g_OsVersion = 0;
KdPrint(("未知版本"));
return FALSE;
}

return TRUE;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: