mirror of
https://github.com/ufrisk/pcileech.git
synced 2026-05-22 13:24:22 +08:00
128 lines
4.8 KiB
C
128 lines
4.8 KiB
C
// wx64_pslist.c : kernel code to list running processes (name and PID).
|
|
// Compatible with Windows x64.
|
|
//
|
|
// (c) Ulf Frisk, 2016
|
|
// Author: Ulf Frisk, pcileech@frizk.net
|
|
//
|
|
// compile with:
|
|
// cl.exe /O1 /Os /Oy /FD /MT /GS- /J /GR- /FAcs /W4 /Zl /c /TC /kernel wx64_common.c
|
|
// cl.exe /O1 /Os /Oy /FD /MT /GS- /J /GR- /FAcs /W4 /Zl /c /TC /kernel wx64_pslist.c
|
|
// ml64 wx64_common_a.asm /Fewx64_pslist.exe /link /NODEFAULTLIB /RELEASE /MACHINE:X64 /entry:main wx64_pslist.obj wx64_common.obj
|
|
// shellcode64.exe -o wx64_pslist.exe "ACTIVE PROCESS LIST \n===========================================================================\nNTSTATUS: %s0x%08x \nIN TOTAL %i ENTRIES EXISTS, SEE BELOW FOR MORE INFORMATION \n===========================================================================\n"
|
|
//
|
|
#include "wx64_common.h"
|
|
|
|
typedef struct tdKERNEL_FUNCTIONS2 {
|
|
LPSTR(*PsGetProcessImageFileName)(
|
|
_In_ PEPROCESS Process
|
|
);
|
|
NTSTATUS(*PsLookupProcessByProcessId)(
|
|
_In_ HANDLE ProcessId,
|
|
_Out_ PEPROCESS *Process
|
|
);
|
|
size_t(*strnlen)(
|
|
const char *str,
|
|
size_t numberOfElements
|
|
);
|
|
} KERNEL_FUNCTIONS2, *PKERNEL_FUNCTIONS2;
|
|
|
|
VOID InitializeKernelFunctions2(_In_ QWORD qwNtosBase, _Out_ PKERNEL_FUNCTIONS2 fnk2)
|
|
{
|
|
QWORD FUNC2[][2] = {
|
|
{ &fnk2->PsGetProcessImageFileName, H_PsGetProcessImageFileName },
|
|
{ &fnk2->PsLookupProcessByProcessId, H_PsLookupProcessByProcessId },
|
|
{ &fnk2->strnlen, H_strnlen }
|
|
};
|
|
for(QWORD j = 0; j < (sizeof(FUNC2) / sizeof(QWORD[2])); j++) {
|
|
*(PQWORD)FUNC2[j][0] = PEGetProcAddressH(qwNtosBase, (DWORD)FUNC2[j][1]);
|
|
}
|
|
}
|
|
|
|
typedef struct _SYSTEM_PROCESS_INFORMATION {
|
|
ULONG NextEntryOffset;
|
|
ULONG NumberOfThreads;
|
|
BYTE Reserved1[68];
|
|
LONG BasePriority;
|
|
HANDLE UniqueProcessId;
|
|
PVOID Reserved3;
|
|
ULONG HandleCount;
|
|
BYTE Reserved4[4];
|
|
PVOID Reserved5[11];
|
|
SIZE_T PeakPagefileUsage;
|
|
SIZE_T PrivatePageCount;
|
|
LARGE_INTEGER Reserved6[6];
|
|
} SYSTEM_PROCESS_INFORMATION, *PSYSTEM_PROCESS_INFORMATION;
|
|
|
|
NTSTATUS GetProcessNameFromPid(_In_ PKERNEL_FUNCTIONS fnk, _In_ PKERNEL_FUNCTIONS2 fnk2, _In_ HANDLE pid, _In_ SIZE_T cb, _Out_ PBYTE pb)
|
|
{
|
|
PEPROCESS Process;
|
|
LPSTR sz;
|
|
SIZE_T csz;
|
|
NTSTATUS nt = fnk2->PsLookupProcessByProcessId(pid, &Process);
|
|
if(NT_SUCCESS(nt)) {
|
|
sz = fnk2->PsGetProcessImageFileName(Process);
|
|
csz = fnk2->strnlen(sz, cb);
|
|
fnk->RtlCopyMemory(pb, sz, csz);
|
|
}
|
|
return nt;
|
|
}
|
|
|
|
NTSTATUS ActionDefault(_In_ PKMDDATA pk, _In_ PKERNEL_FUNCTIONS fnk, _In_ PKERNEL_FUNCTIONS2 fnk2)
|
|
{
|
|
CHAR ABET_HEX[] = { '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'a', 'b', 'c', 'd', 'e', 'f' };
|
|
NTSTATUS nt;
|
|
PBYTE pbSPIBuffer;
|
|
ULONG cbSPIBuffer;
|
|
PSYSTEM_PROCESS_INFORMATION pPI;
|
|
QWORD qwAddrOut, qwPID;
|
|
nt = fnk->ZwQuerySystemInformation(SystemProcessInformation, NULL, 0, &cbSPIBuffer);
|
|
if(nt != 0xC0000004 || !cbSPIBuffer) {
|
|
return nt;
|
|
}
|
|
pbSPIBuffer = (PBYTE)fnk->ExAllocatePool(0, cbSPIBuffer);
|
|
if(!pbSPIBuffer) {
|
|
return E_OUTOFMEMORY;
|
|
}
|
|
nt = fnk->ZwQuerySystemInformation(SystemProcessInformation, pbSPIBuffer, cbSPIBuffer, &cbSPIBuffer);
|
|
if(NT_SUCCESS(nt)) {
|
|
pPI = (PSYSTEM_PROCESS_INFORMATION)pbSPIBuffer;
|
|
qwAddrOut = pk->DMAAddrVirtual + pk->dataOutExtraOffset + pk->dataOutExtraLength;
|
|
do {
|
|
pk->dataOut[1]++;
|
|
qwAddrOut = pk->DMAAddrVirtual + pk->dataOutExtraOffset + pk->dataOutExtraLength;
|
|
*(PQWORD)(qwAddrOut + 0x00) = 0x2020202020202020;
|
|
*(PQWORD)(qwAddrOut + 0x08) = 0x2020202020202020;
|
|
pk->dataOutExtraLength += 0x20;
|
|
qwPID = pPI->UniqueProcessId;
|
|
GetProcessNameFromPid(fnk, fnk2, (HANDLE)qwPID, 0x10, (PBYTE)qwAddrOut);
|
|
*(PDWORD)(qwAddrOut + 0x10) = 0x3D444950;
|
|
*(PBYTE)(qwAddrOut + 0x1f) = '\n';
|
|
*(PBYTE)(qwAddrOut + 0x1e) = '\r';
|
|
*(PBYTE)(qwAddrOut + 0x1d) = '0' + (qwPID % 10);
|
|
*(PBYTE)(qwAddrOut + 0x1c) = '0' + ((qwPID / 10) % 10);
|
|
*(PBYTE)(qwAddrOut + 0x1b) = '0' + ((qwPID / 100) % 10);
|
|
*(PBYTE)(qwAddrOut + 0x1a) = '0' + ((qwPID / 1000) % 10);
|
|
*(PBYTE)(qwAddrOut + 0x19) = '0' + ((qwPID / 10000) % 10);
|
|
*(PBYTE)(qwAddrOut + 0x18) = '|';
|
|
*(PBYTE)(qwAddrOut + 0x17) = ABET_HEX[qwPID & 0xf];
|
|
*(PBYTE)(qwAddrOut + 0x16) = ABET_HEX[(qwPID >> 4) & 0xf];
|
|
*(PBYTE)(qwAddrOut + 0x15) = ABET_HEX[(qwPID >> 8) & 0xf];
|
|
*(PBYTE)(qwAddrOut + 0x14) = ABET_HEX[(qwPID >> 12) & 0xf];
|
|
if(!pPI->NextEntryOffset) {
|
|
break;
|
|
}
|
|
pPI = (PSYSTEM_PROCESS_INFORMATION)((QWORD)pPI + pPI->NextEntryOffset);
|
|
} while(((QWORD)pPI >= (QWORD)pbSPIBuffer) && ((QWORD)pPI < (QWORD)pbSPIBuffer + cbSPIBuffer));
|
|
}
|
|
if(pbSPIBuffer) { fnk->ExFreePool(pbSPIBuffer); }
|
|
return nt;
|
|
}
|
|
|
|
VOID c_EntryPoint(_In_ PKMDDATA pk)
|
|
{
|
|
KERNEL_FUNCTIONS fnk;
|
|
KERNEL_FUNCTIONS2 fnk2;
|
|
InitializeKernelFunctions(pk->AddrKernelBase, &fnk);
|
|
InitializeKernelFunctions2(pk->AddrKernelBase, &fnk2);
|
|
pk->dataOut[0] = ActionDefault(pk, &fnk, &fnk2);
|
|
} |