win10 1909逆向----通过全局句柄PspCidTable,枚举所有进程【目前只考虑句柄表为两层结构的解析,因为懒】。
程序员文章站
2022-03-30 10:42:28
...
先看效果图:
再放代码:
#include <ntddk.h>
#include "Handle.h"
VOID Unload(PDRIVER_OBJECT pDriverObject)
{
KdPrint(("end\n"));
}
NTSTATUS DriverEntry(PDRIVER_OBJECT pDriverObject, PUNICODE_STRING pRegPath)
{
NTSTATUS status = STATUS_SUCCESS;
KdPrint(("start\n"));
pDriverObject->DriverUnload = Unload;
HANDLE hThread;
PUCHAR System = (PUCHAR)PsInitialSystemProcess;
//第一步得到全局句柄表
PHANDLE_TABLE PspCidTable=0;
PUCHAR var = (PUCHAR)PsLookupThreadByThreadId;
for (int i = 0; i < 100; i++)
{
if (*var == 0xf7 && *(var + 1) == 0xc1)
{
PspCidTable = *(PLONG32)(var - 4) & 0xFFFFFFFF;
PspCidTable = *(PUINT64)(var + (LONG32)PspCidTable);
}
var++;
}
//第二步,得到进程的INDEX
pObjectType = ObGetObjectType(PsInitialSystemProcess);
TypeIndex = pObjectType->Index;
//第二步解析
AnalyticHandle(PspCidTable);
return status;
}
PVOID NTAPI AnalyticHandle(IN PHANDLE_TABLE HandleTable)
{
INT64 TableBase = 0;
INT64 TableLevel = 0;
PUINT64 varTableEntry = 0;
PHANDLE_TABLE varHandleTable = HandleTable;
TableBase = varHandleTable->TableCode;
TableLevel = TableBase & 3;
TableBase = TableBase & 0xFFFFFFFFFFFFFFFC;
int var_i = 0;
int var_j = 0;
PUCHAR Object = 0;
UCHAR Index = 0;
if (TableLevel == 1)
{
for (; *(PUINT64)TableBase && ((var_i++)<0x200); TableBase += 8)
{
varTableEntry = *(PUINT64)TableBase;
//因为第一个和最后一个不用
varTableEntry += 2;
var_j = 0;
while((var_j++) < 0xFF)
{
if (*varTableEntry)
{
//全局句柄表得到的是Object 内核句柄表得到的是Object_Header
Object=(((INT64)*varTableEntry) >> 0x10) & 0xFFFFFFFFFFFFFFF0;
//解析Index
pObjectType = ObGetObjectType(Object);
if (pObjectType->Index == TypeIndex)
{
KdPrint(("%s\n", PsGetProcessImageFileName(Object)));
}
//不让系统卡死
KSleep(10);
}
varTableEntry += 2;
}
}
}
return 0;
}
VOID KSleep(LONG MilliSecond)
{
LARGE_INTEGER Interval = { 0 };
Interval.QuadPart = DELAY_ONE_MILLISECOND;
Interval.QuadPart *= MilliSecond;
KeDelayExecutionThread(KernelMode, 0, &Interval);
}
再放头文件:
#include <ntddk.h>
#define DELAY_ONE_MICROSECOND (-10)
#define DELAY_ONE_MILLISECOND (DELAY_ONE_MICROSECOND*1000)
typedef struct _HANDLE_TABLE
{
ULONG NextHandleNeedingPool;
LONG ExtraInfoPages;
ULONG64 TableCode;
PEPROCESS QuotaProcess;
LIST_ENTRY HandleTableList;
ULONG UniqueProcessId;
ULONG Flags;
ULONG64 HandleContentionEvent;
}HANDLE_TABLE, *PHANDLE_TABLE;
typedef struct _OBJECT_TYPE
{
LIST_ENTRY TypeList;
UNICODE_STRING Name;
PVOID DefaultObject;
UCHAR Index;
ULONG TotalNumberOfObjects;
ULONG TotalNumberOfHandles;
ULONG HighWaterNumberOfObjects;
ULONG HighWaterNumberOfHandles;
//后面暂时用不到,省略
}OBJECT_TYPE, *POBJECT_TYPE;
PVOID NTAPI AnalyticHandle(IN PHANDLE_TABLE HandleTable);
NTKERNELAPI PVOID NTAPI ObGetObjectType(IN PVOID pObject);
NTKERNELAPI NTSTATUS NTAPI PsLookupThreadByThreadId(IN HANDLE ThreadId, OUT PETHREAD *Thread);
NTKERNELAPI LPSTR NTAPI PsGetProcessImageFileName(PEPROCESS Process);
PSHORT ObHeaderCookie = 0;
PINT64 ObTypeIndexTable = 0;
UCHAR TypeIndex;
NTKERNELAPI PEPROCESS PsInitialSystemProcess;
PVOID Object;
POBJECT_TYPE pObjectType;
VOID KSleep(LONG MilliSecond);
UCHAR SystemProcessType;
UCHAR TypeIndex;
上一篇: 前端 —— SVG
下一篇: 第十章 内核同步方法