├── VT_demo ├── dbgkm.asm ├── EptHideDebugPort.c ├── dbgk.c ├── dbgk.h ├── DBGTOOL.c ├── Driver.c ├── VMH │ ├── mem.c │ ├── mem.h │ ├── vmx.h │ ├── common.h │ ├── amd64 │ │ ├── common-asm.asm │ │ ├── vmx-asm.asm │ │ └── regs.asm │ ├── regs.h │ ├── hvm.h │ ├── common.c │ └── vmcs.h ├── dpg.asm ├── eptcomm.h ├── newbp.c ├── DisablePG.c ├── EptHeader.h ├── dbgk1to2.c ├── KernelStruct.h ├── initMiniHook.c ├── HOOKfunctions.c ├── ProtectWindow.c ├── R3EptHieMemPage.c ├── VMProtectDDK32.lib ├── VMProtectDDK64.lib ├── AntiHookSwapContext.c ├── initSsdtInlineHook.c ├── Arch │ └── Intel │ │ ├── VmxExitHandlers.c │ │ ├── VMXa.asm │ │ ├── VmxEvent.h │ │ ├── EPT.h │ │ └── VMCS.h ├── Test │ ├── Tests.h │ └── Tests.c ├── VMMprocessList.h ├── R3EptHideMem.h ├── vstruct.h ├── snprintf.h ├── driver.h ├── VT_demo.inf ├── dbgtool.h ├── Core │ ├── HVM.h │ └── HVM.c ├── ActiveProcessDbgList.h ├── Hooks │ ├── SyscallHook.h │ ├── PageHook.h │ ├── SyscallHook.c │ ├── Syscall.asm │ └── PageHook.c ├── Util │ ├── LDasm.h │ ├── Utils.h │ └── Utils.c ├── WindowKrnlHwbreak.asm ├── DRRWE.h ├── dbgfunc.asm ├── SwapContext.asm ├── DbgIsMyProcess.c ├── Txoo.h ├── ActiveProcessDbgList.c ├── VMProtectDDK.h ├── common.c ├── hvm.c ├── DRRWE.c ├── ept.h ├── Include │ ├── Common.h │ ├── CPU.h │ └── PE.h ├── syscalhook.c ├── VT_demo.vcxproj.filters ├── gobalConter.h └── vmxdebug.c ├── README.md ├── VT_demo Package └── VT_demo Package.vcxproj.filters ├── .gitattributes ├── .gitignore └── VT_demo.sln /VT_demo/dbgkm.asm: -------------------------------------------------------------------------------- 1 | 2 | .CODE 3 | 4 | END -------------------------------------------------------------------------------- /VT_demo/EptHideDebugPort.c: -------------------------------------------------------------------------------- 1 | #include "ntddk.h" -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # VTbasedDebuggerWin7 2 | Nothing to be placed... 3 | -------------------------------------------------------------------------------- /VT_demo/dbgk.c: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/OkazakiNagisa/VTbasedDebuggerWin7/HEAD/VT_demo/dbgk.c -------------------------------------------------------------------------------- /VT_demo/dbgk.h: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/OkazakiNagisa/VTbasedDebuggerWin7/HEAD/VT_demo/dbgk.h -------------------------------------------------------------------------------- /VT_demo/DBGTOOL.c: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/OkazakiNagisa/VTbasedDebuggerWin7/HEAD/VT_demo/DBGTOOL.c -------------------------------------------------------------------------------- /VT_demo/Driver.c: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/OkazakiNagisa/VTbasedDebuggerWin7/HEAD/VT_demo/Driver.c -------------------------------------------------------------------------------- /VT_demo/VMH/mem.c: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/OkazakiNagisa/VTbasedDebuggerWin7/HEAD/VT_demo/VMH/mem.c -------------------------------------------------------------------------------- /VT_demo/VMH/mem.h: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/OkazakiNagisa/VTbasedDebuggerWin7/HEAD/VT_demo/VMH/mem.h -------------------------------------------------------------------------------- /VT_demo/VMH/vmx.h: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/OkazakiNagisa/VTbasedDebuggerWin7/HEAD/VT_demo/VMH/vmx.h -------------------------------------------------------------------------------- /VT_demo/dpg.asm: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/OkazakiNagisa/VTbasedDebuggerWin7/HEAD/VT_demo/dpg.asm -------------------------------------------------------------------------------- /VT_demo/eptcomm.h: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/OkazakiNagisa/VTbasedDebuggerWin7/HEAD/VT_demo/eptcomm.h -------------------------------------------------------------------------------- /VT_demo/newbp.c: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/OkazakiNagisa/VTbasedDebuggerWin7/HEAD/VT_demo/newbp.c -------------------------------------------------------------------------------- /VT_demo/DisablePG.c: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/OkazakiNagisa/VTbasedDebuggerWin7/HEAD/VT_demo/DisablePG.c -------------------------------------------------------------------------------- /VT_demo/EptHeader.h: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/OkazakiNagisa/VTbasedDebuggerWin7/HEAD/VT_demo/EptHeader.h -------------------------------------------------------------------------------- /VT_demo/dbgk1to2.c: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/OkazakiNagisa/VTbasedDebuggerWin7/HEAD/VT_demo/dbgk1to2.c -------------------------------------------------------------------------------- /VT_demo/KernelStruct.h: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/OkazakiNagisa/VTbasedDebuggerWin7/HEAD/VT_demo/KernelStruct.h -------------------------------------------------------------------------------- /VT_demo/VMH/common.h: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/OkazakiNagisa/VTbasedDebuggerWin7/HEAD/VT_demo/VMH/common.h -------------------------------------------------------------------------------- /VT_demo/initMiniHook.c: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/OkazakiNagisa/VTbasedDebuggerWin7/HEAD/VT_demo/initMiniHook.c -------------------------------------------------------------------------------- /VT_demo/HOOKfunctions.c: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/OkazakiNagisa/VTbasedDebuggerWin7/HEAD/VT_demo/HOOKfunctions.c -------------------------------------------------------------------------------- /VT_demo/ProtectWindow.c: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/OkazakiNagisa/VTbasedDebuggerWin7/HEAD/VT_demo/ProtectWindow.c -------------------------------------------------------------------------------- /VT_demo/R3EptHieMemPage.c: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/OkazakiNagisa/VTbasedDebuggerWin7/HEAD/VT_demo/R3EptHieMemPage.c -------------------------------------------------------------------------------- /VT_demo/VMProtectDDK32.lib: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/OkazakiNagisa/VTbasedDebuggerWin7/HEAD/VT_demo/VMProtectDDK32.lib -------------------------------------------------------------------------------- /VT_demo/VMProtectDDK64.lib: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/OkazakiNagisa/VTbasedDebuggerWin7/HEAD/VT_demo/VMProtectDDK64.lib -------------------------------------------------------------------------------- /VT_demo/AntiHookSwapContext.c: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/OkazakiNagisa/VTbasedDebuggerWin7/HEAD/VT_demo/AntiHookSwapContext.c -------------------------------------------------------------------------------- /VT_demo/initSsdtInlineHook.c: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/OkazakiNagisa/VTbasedDebuggerWin7/HEAD/VT_demo/initSsdtInlineHook.c -------------------------------------------------------------------------------- /VT_demo/VMH/amd64/common-asm.asm: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/OkazakiNagisa/VTbasedDebuggerWin7/HEAD/VT_demo/VMH/amd64/common-asm.asm -------------------------------------------------------------------------------- /VT_demo/Arch/Intel/VmxExitHandlers.c: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/OkazakiNagisa/VTbasedDebuggerWin7/HEAD/VT_demo/Arch/Intel/VmxExitHandlers.c -------------------------------------------------------------------------------- /VT_demo/Test/Tests.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | #include 3 | 4 | VOID TestStart( IN BOOLEAN SyscallHook, IN BOOLEAN PageHook1, IN IN BOOLEAN PageHook2 ); 5 | VOID TestStop(); 6 | VOID TestPrintResults(); -------------------------------------------------------------------------------- /VT_demo/VMMprocessList.h: -------------------------------------------------------------------------------- 1 | #include "ntddk.h" 2 | 3 | typedef struct{ 4 | 5 | struct ProcessList * up; 6 | HANDLE processID; 7 | 8 | struct ProcessList * dw; 9 | 10 | }ProcessList, *PProcessList; -------------------------------------------------------------------------------- /VT_demo/R3EptHideMem.h: -------------------------------------------------------------------------------- 1 | #include "ntddk.h" 2 | BOOLEAN R3_HideMem(PEPROCESS Process, ULONG64 Address, PVOID Code, ULONG Size); 3 | BOOLEAN R3_UnHideMem(ULONG64 Address,ULONG64 Eprocess); 4 | VOID InitialzeR3EPTHOOK(); 5 | -------------------------------------------------------------------------------- /VT_demo/vstruct.h: -------------------------------------------------------------------------------- 1 | #include "ntddk.h" 2 | typedef struct _StackFrame{ 3 | ULONG64 ERRORCODE; 4 | ULONG64 rip; 5 | ULONG64 cs; 6 | ULONG64 rflags; 7 | ULONG64 rsp; 8 | ULONG64 ss; 9 | 10 | }StackFrame, *PStackFrame; -------------------------------------------------------------------------------- /VT_demo/snprintf.h: -------------------------------------------------------------------------------- 1 | #ifndef _PORTABLE_SNPRINTF_H_ 2 | # define _PORTABLE_SNPRINTF_H_ 3 | 4 | extern int snprintf ( 5 | char *, 6 | size_t, 7 | const char *, /*args */ 8 | ... 9 | ); 10 | extern int vsnprintf ( 11 | char *, 12 | size_t, 13 | const char *, 14 | va_list 15 | ); 16 | 17 | #endif 18 | -------------------------------------------------------------------------------- /VT_demo/driver.h: -------------------------------------------------------------------------------- 1 | // This file is part of Virtdbg 2 | // Copyright (C) 2010-2011 Damien AUMAITRE 3 | 4 | // Licence is GPLv3, see LICENCE.txt in the top-level directory 5 | 6 | 7 | #include 8 | 9 | 10 | 11 | NTSTATUS PsLookupProcessByProcessId( 12 | _In_ HANDLE ProcessId, 13 | _Out_ PEPROCESS *Process); 14 | 15 | 16 | 17 | 18 | -------------------------------------------------------------------------------- /VT_demo Package/VT_demo Package.vcxproj.filters: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | {8E41214B-6785-4CFE-B992-037D68949A14} 6 | inf;inv;inx;mof;mc; 7 | 8 | 9 | -------------------------------------------------------------------------------- /VT_demo/VT_demo.inf: -------------------------------------------------------------------------------- 1 | ; 2 | ; VT_demo.inf 3 | ; 4 | 5 | [Version] 6 | Signature="$WINDOWS NT$" 7 | Class= 8 | ClassGuid= 9 | Provider= 10 | DriverVer= 11 | CatalogFile= 12 | 13 | [DestinationDirs] 14 | DefaultDestDir = 12 15 | 16 | 17 | [SourceDisksNames] 18 | 1 = %DiskName%,,,"" 19 | 20 | [SourceDisksFiles] 21 | 22 | 23 | [Manufacturer] 24 | %ManufacturerName%=Standard,NT$ARCH$ 25 | 26 | [Standard.NT$ARCH$] 27 | 28 | 29 | [Strings] 30 | ManufacturerName="" 31 | ClassName="" 32 | DiskName="VT_demo Source Disk" 33 | -------------------------------------------------------------------------------- /VT_demo/dbgtool.h: -------------------------------------------------------------------------------- 1 | #include "ntddk.h" 2 | typedef struct _save_handlentry{ 3 | struct _save_handlentry*head; 4 | HANDLE dbgProcessId; 5 | PEPROCESS dbgProcessStruct; 6 | 7 | struct _save_handlentry*next; 8 | 9 | }_save_handlentry, *p_save_handlentry; 10 | 11 | p_save_handlentry createlist(); 12 | p_save_handlentry insertlist(HANDLE dbgProcessId, 13 | PEPROCESS dbgProcessStruct, p_save_handlentry phead); 14 | p_save_handlentry querylist(p_save_handlentry phead, HANDLE dbgProcessId, PEPROCESS dbgProcessStruct); 15 | void deletelist(p_save_handlentry pclid); 16 | -------------------------------------------------------------------------------- /VT_demo/Core/HVM.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | #include 3 | 4 | /// 5 | /// Check if VT-x/AMD-V is supported 6 | /// 7 | /// TRUE if supported 8 | BOOLEAN HvmIsHVSupported(); 9 | 10 | /// 11 | /// CPU virtualization features 12 | /// 13 | VOID HvmCheckFeatures(); 14 | 15 | /// 16 | /// Virtualize each CPU 17 | /// 18 | /// Status code 19 | NTSTATUS StartHV(); 20 | 21 | /// 22 | /// Devirtualize each CPU 23 | /// 24 | /// Status code 25 | NTSTATUS StopHV(); 26 | -------------------------------------------------------------------------------- /VT_demo/ActiveProcessDbgList.h: -------------------------------------------------------------------------------- 1 | #include "ntddk.h" 2 | typedef struct _DbgPortList{ 3 | LIST_ENTRY PortList; 4 | ULONG64 DbgPort; 5 | UINT8 markdbg; 6 | PEPROCESS Process; 7 | }DbgPortList, *PDbgPortList; 8 | VOID InitDbgPortList(); 9 | PDbgPortList Port_FindProcessList(PEPROCESS Process, ULONG64 DbgPort); 10 | PDbgPortList Port_AddProcessToList(PEPROCESS Process, ULONG64 DbgPort); 11 | VOID NTAPI Port_ExFreeItem(PDbgPortList Item); 12 | BOOLEAN Port_SetPort(PEPROCESS Process, ULONG64 DbgPort); 13 | BOOLEAN Port_IsPort(PEPROCESS Process); 14 | ULONG64 Port_GetPort(PEPROCESS Process); 15 | BOOLEAN Port_RemoveDbgItem(PEPROCESS Process, ULONG64 DbgPort); -------------------------------------------------------------------------------- /VT_demo/VMH/regs.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright holder: Invisible Things Lab 3 | */ 4 | 5 | #pragma once 6 | #include 7 | 8 | USHORT RegGetCs (); 9 | USHORT RegGetDs (); 10 | USHORT RegGetEs (); 11 | USHORT RegGetSs (); 12 | USHORT RegGetFs (); 13 | USHORT RegGetGs (); 14 | 15 | ULONG64 RegGetRflags (); 16 | ULONG64 RegGetRsp (); 17 | 18 | ULONG64 GetIdtBase (); 19 | USHORT GetIdtLimit (); 20 | ULONG64 GetGdtBase (); 21 | USHORT GetGdtLimit (); 22 | 23 | USHORT GetTrSelector (); 24 | USHORT GetLdtr (); 25 | 26 | ULONG64 RegGetDr0 (); 27 | ULONG64 RegGetDr1 (); 28 | ULONG64 RegGetDr2 (); 29 | ULONG64 RegGetDr3 (); 30 | // 31 | ULONG64 RegSetDr0 (); 32 | ULONG64 RegSetDr1 (); 33 | ULONG64 RegSetDr2 (); 34 | ULONG64 RegSetDr3 (); -------------------------------------------------------------------------------- /VT_demo/Hooks/SyscallHook.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | #include 3 | 4 | /// 5 | /// Perform LSTAR hooking 6 | /// 7 | /// Status code 8 | NTSTATUS SHInitHook(); 9 | 10 | /// 11 | /// Hook specific SSDT entry 12 | /// 13 | /// SSDT index 14 | /// Hook address 15 | /// Number of function arguments 16 | /// Status code 17 | NTSTATUS SHHookSyscall( IN ULONG index, IN PVOID hookPtr, IN CHAR argCount ); 18 | 19 | /// 20 | /// Restore original SSDT entry 21 | /// 22 | /// SSDT index 23 | /// Status code 24 | NTSTATUS SHRestoreSyscall( IN ULONG index ); 25 | 26 | /// 27 | /// Unhook LSTAR 28 | /// 29 | /// Status code 30 | NTSTATUS SHDestroyHook(); 31 | -------------------------------------------------------------------------------- /VT_demo/Util/LDasm.h: -------------------------------------------------------------------------------- 1 | #ifndef _LDASM_ 2 | #define _LDASM_ 3 | 4 | #include 5 | 6 | #ifdef __cplusplus 7 | extern "C" 8 | { 9 | #endif 10 | 11 | #define F_INVALID 0x01 12 | #define F_PREFIX 0x02 13 | #define F_REX 0x04 14 | #define F_MODRM 0x08 15 | #define F_SIB 0x10 16 | #define F_DISP 0x20 17 | #define F_IMM 0x40 18 | #define F_RELATIVE 0x80 19 | 20 | typedef struct _ldasm_data 21 | { 22 | UCHAR flags; 23 | UCHAR rex; 24 | UCHAR modrm; 25 | UCHAR sib; 26 | UCHAR opcd_offset; 27 | UCHAR opcd_size; 28 | UCHAR disp_offset; 29 | UCHAR disp_size; 30 | UCHAR imm_offset; 31 | UCHAR imm_size; 32 | } ldasm_data; 33 | 34 | unsigned int __fastcall ldasm( void *code, ldasm_data *ld, ULONG is64 ); 35 | unsigned long __fastcall SizeOfProc( void *Proc ); 36 | void* __fastcall ResolveJmp( void *Proc ); 37 | 38 | #ifdef __cplusplus 39 | } 40 | #endif 41 | 42 | #endif//_LDASM_ -------------------------------------------------------------------------------- /VT_demo/WindowKrnlHwbreak.asm: -------------------------------------------------------------------------------- 1 | 2 | .CODE 3 | myKiSaveDebugRegisterState PROC 4 | 5 | mov r9,qword ptr gs:[18h] 6 | mov rax,dr0 7 | mov rdx,dr1 8 | mov qword ptr [rbp+58h],rax 9 | mov qword ptr [rbp+60h],rdx 10 | mov rax,dr2 11 | mov rdx,dr3 12 | mov qword ptr [rbp+68h],rax 13 | mov qword ptr [rbp+70h],rdx 14 | mov rax,dr6 15 | mov rdx,dr7 16 | mov qword ptr [rbp+78h],rax 17 | mov qword ptr [rbp+80h],rdx 18 | xor eax,eax 19 | mov dr7,rax 20 | ret 0 21 | myKiSaveDebugRegisterState ENDP 22 | 23 | 24 | 25 | 26 | myKiRestoreDebugRegisterState PROC 27 | xor edx,edx 28 | mov dr7,rdx 29 | mov rax,qword ptr [rbp+58h] 30 | mov rdx,qword ptr [rbp+60h] 31 | mov dr0,rax 32 | mov dr1,rdx 33 | mov rax,qword ptr [rbp+68h] 34 | mov rdx,qword ptr [rbp+70h] 35 | mov dr2,rax 36 | mov dr3,rdx 37 | mov rdx,qword ptr [rbp+80h] 38 | xor eax,eax 39 | mov dr6,rax 40 | mov dr7,rdx 41 | ret 0 42 | myKiRestoreDebugRegisterState ENDP 43 | 44 | END -------------------------------------------------------------------------------- /VT_demo/DRRWE.h: -------------------------------------------------------------------------------- 1 | #include "ntddk.h" 2 | typedef LONG DWORD; 3 | typedef struct _THREAD_dr_List{ 4 | LIST_ENTRY TList; 5 | DWORD Dr0; 6 | DWORD Dr1; 7 | DWORD Dr2; 8 | DWORD Dr3; 9 | DWORD Dr6; 10 | DWORD Dr7; 11 | DWORD eflag; 12 | PETHREAD Thread; 13 | 14 | }THREAD_dr_List, *PTHREAD_dr_List; 15 | 16 | #define HIDWORD(a) ((DWORD)((UINT64)(a) >> 32)) 17 | #define LODWORD(a) ((DWORD)((UINT64)(a)& 0x0000ffff)) 18 | typedef struct _PROCESS_List{ 19 | LIST_ENTRY PorcessList; 20 | PEPROCESS Process; 21 | KSPIN_LOCK loacl_lock; 22 | LIST_ENTRY ThreadList; 23 | }PROCESS_List, *PPROCESS_List; 24 | VOID InitListAndLock(); 25 | PPROCESS_List Dr_FindProcessList(PEPROCESS Process); 26 | PPROCESS_List Dr_AddProcessToList(PEPROCESS Process); 27 | VOID NTAPI Dr_ExFreeItem(PPROCESS_List Item); 28 | PTHREAD_dr_List Dr_AddThreadStructToList(PPROCESS_List DrRwListItem, PTHREAD_dr_List Struct); 29 | VOID NTAPI Dr_ExFreeTheadListItem(PPROCESS_List DrRwListItem, PTHREAD_dr_List Struct); 30 | PTHREAD_dr_List Dr_FindThreadContextByThreadList(PPROCESS_List DrRwListItem, PETHREAD Thread); 31 | PTHREAD_dr_List Dr_UpdataThreadContextByThreadList(PPROCESS_List DrRwListItem, PETHREAD Thread, PTHREAD_dr_List UpData); 32 | -------------------------------------------------------------------------------- /VT_demo/VMH/hvm.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright holder: Invisible Things Lab 3 | */ 4 | 5 | #pragma once 6 | 7 | #include 8 | #include "common.h" 9 | #include "vmx.h" 10 | #include "regs.h" 11 | 12 | // ntamd64_x.h 13 | #define KGDT64_NULL (0 * 16) // NULL descriptor 14 | #define KGDT64_R0_CODE (1 * 16) // kernel mode 64-bit code 15 | #define KGDT64_R0_DATA (1 * 16) + 8 // kernel mode 64-bit data (stack) 16 | #define KGDT64_R3_CMCODE (2 * 16) // user mode 32-bit code 17 | #define KGDT64_R3_DATA (2 * 16) + 8 // user mode 32-bit data 18 | #define KGDT64_R3_CODE (3 * 16) // user mode 64-bit code 19 | #define KGDT64_SYS_TSS (4 * 16) // kernel mode system task state 20 | #define KGDT64_R3_CMTEB (5 * 16) // user mode 32-bit TEB 21 | #define KGDT64_R0_CMCODE (6 * 16) // kernel mode 32-bit code 22 | 23 | // this must be synchronized with CmSetBluepillSelectors() (common-asm.asm) 24 | #define BP_GDT64_CODE KGDT64_R0_CODE // cs 25 | #define BP_GDT64_DATA KGDT64_R0_DATA // ds, es, ss 26 | #define BP_GDT64_SYS_TSS KGDT64_SYS_TSS // tr 27 | #define BP_GDT64_PCR KGDT64_R0_DATA // gs 28 | 29 | NTSTATUS HvmSwallowBluepill (); 30 | 31 | NTSTATUS HvmSpitOutBluepill (); 32 | -------------------------------------------------------------------------------- /VT_demo/dbgfunc.asm: -------------------------------------------------------------------------------- 1 | EXTERN ObfDereferenceObject:PROC 2 | EXTERN ObfReferenceObjectWithTag:PROC 3 | EXTERN MmUserProbeAddress:QWORD 4 | .CODE 5 | 6 | ObFastDereferenceObject PROC 7 | prefetchw byte ptr [rcx] 8 | mov rax, [rcx] 9 | mov r8, rax 10 | xor r8, rdx 11 | cmp r8, 0Fh 12 | jnb a 13 | mov r9, rcx 14 | loc_1400921A5: 15 | lea r8, [rax+1] 16 | lock cmpxchg [r9], r8 17 | jnz short loc_1400921B9 18 | ret 19 | loc_1400921B9: 20 | mov rcx, rax 21 | xor rcx, rdx 22 | cmp rcx, 0Fh 23 | jb short loc_1400921A5 24 | mov rcx, rdx ; Object 25 | jmp ObfDereferenceObject 26 | 27 | 28 | 29 | 30 | 31 | a: ; Object 32 | mov rcx, rdx 33 | jmp ObfDereferenceObject 34 | 35 | ObFastDereferenceObject ENDP 36 | 37 | ObFastReferenceObjectLocked PROC 38 | 39 | push rbx 40 | sub rsp, 20h 41 | mov rbx, [rcx] 42 | and rbx, 0FFFFFFFFFFFFFFF0h 43 | jz short loc_1400B6B7C 44 | mov edx, 746C6644h 45 | mov rcx, rbx 46 | call ObfReferenceObjectWithTag 47 | 48 | loc_1400B6B7C: 49 | mov rax, rbx 50 | add rsp, 20h 51 | pop rbx 52 | ret 53 | ObFastReferenceObjectLocked ENDP 54 | 55 | ProbeWrite PROC 56 | 57 | mov rax, qword ptr [MmUserProbeAddress] 58 | cmp rcx, rax 59 | cmovnb rcx, rax 60 | mov rax, [rcx] 61 | mov [rcx], rax 62 | 63 | ProbeWrite ENDP 64 | END -------------------------------------------------------------------------------- /VT_demo/SwapContext.asm: -------------------------------------------------------------------------------- 1 | .CODE 2 | HVM_SAVE_ALL_NOSEGREGS MACRO 3 | push r15 4 | push r14 5 | push r13 6 | push r12 7 | push r11 8 | push r10 9 | push r9 10 | push r8 11 | push rdi 12 | push rsi 13 | push rbp 14 | push rbp ; rsp 15 | push rbx 16 | push rdx 17 | push rcx 18 | push rax 19 | ENDM 20 | 21 | HVM_RESTORE_ALL_NOSEGREGS MACRO 22 | pop rax 23 | pop rcx 24 | pop rdx 25 | pop rbx 26 | pop rbp ; rsp 27 | pop rbp 28 | pop rsi 29 | pop rdi 30 | pop r8 31 | pop r9 32 | pop r10 33 | pop r11 34 | pop r12 35 | pop r13 36 | pop r14 37 | pop r15 38 | ENDM 39 | 40 | extern jmp_SwapContext_PatchXRstor:QWORD 41 | extern jmp_SwapContext:QWORD 42 | extern jmp_SwapContextTp:QWORD 43 | extern IstThreadStub:PROC 44 | MySwapContext PROC 45 | 46 | 47 | 48 | sub rsp,38h 49 | mov qword ptr [rsp+30h],rbp 50 | prefetchw [rsi+49h] 51 | mov byte ptr [rsp+28h],cl 52 | 53 | cmp byte ptr [rsi+49h],0 54 | 55 | je jmp_patch 56 | jmp qword ptr [jmp_SwapContext_PatchXRstor] 57 | 58 | jmp_patch: 59 | 60 | 61 | ;;;;;;;;;;;;;;;;;;;;;;;;;;;; 62 | HVM_SAVE_ALL_NOSEGREGS 63 | mov rcx,rdi 64 | mov rdx,rsi 65 | call IstThreadStub 66 | cmp rax,1 67 | je jmptp 68 | HVM_RESTORE_ALL_NOSEGREGS 69 | ;;;;;;;;;;;;;;;;;;;;;;;;;;;; 70 | 71 | mov byte ptr [rsi+49h],1 72 | cli 73 | rdtsc 74 | shl rdx,20h 75 | or rax,rdx 76 | 77 | push qword ptr [jmp_SwapContext] 78 | ret 79 | 80 | jmptp: 81 | HVM_RESTORE_ALL_NOSEGREGS 82 | push qword ptr [jmp_SwapContextTp] 83 | ret 84 | MySwapContext ENDP 85 | END -------------------------------------------------------------------------------- /VT_demo/Arch/Intel/VMXa.asm: -------------------------------------------------------------------------------- 1 | ;++ 2 | ; 3 | ; Copyright (c) Alex Ionescu. All rights reserved. 4 | ; 5 | ; Module: 6 | ; 7 | ; VMXa.asm 8 | ; 9 | ; Abstract: 10 | ; 11 | ; This module implements AMD64-specific routines for the Simple Hyper Visor. 12 | ; 13 | ; Author: 14 | ; 15 | ; Alex Ionescu (@aionescu) 16-Mar-2016 - Initial version 16 | ; 17 | ; Environment: 18 | ; 19 | ; Kernel mode only. 20 | ; 21 | ;-- 22 | extern VmxpExitHandler:proc 23 | extern RtlCaptureContext:proc 24 | 25 | .CODE 26 | 27 | VmxVMEntry PROC 28 | push rcx ; save RCX, as we will need to orverride it 29 | lea rcx, [rsp+8h] ; store the context in the stack, bias for 30 | ; the return address and the push we just did. 31 | call RtlCaptureContext ; save the current register state. 32 | ; note that this is a specially written function 33 | ; which has the following key characteristics: 34 | ; 1) it does not taint the value of RCX 35 | ; 2) it does not spill any registers, nor 36 | ; expect home space to be allocated for it 37 | 38 | jmp VmxpExitHandler ; jump to the C code handler. we assume that it 39 | ; compiled with optimizations and does not use 40 | ; home space, which is true of release builds. 41 | VmxVMEntry ENDP 42 | 43 | VmxVMCleanup PROC 44 | mov ds, cx ; set DS to parameter 1 45 | mov es, cx ; set ES to parameter 1 46 | mov fs, dx ; set FS to parameter 2 47 | ret ; return 48 | VmxVMCleanup ENDP 49 | 50 | VmxpResume PROC 51 | vmresume 52 | ret 53 | VmxpResume ENDP 54 | 55 | __vmx_vmcall PROC 56 | vmcall 57 | ret 58 | __vmx_vmcall ENDP 59 | 60 | __invept PROC 61 | invept rcx, OWORD PTR [rdx] 62 | ret 63 | __invept ENDP 64 | 65 | __invvpid PROC 66 | invvpid rcx, OWORD PTR [rdx] 67 | ret 68 | __invvpid ENDP 69 | 70 | END -------------------------------------------------------------------------------- /VT_demo/VMH/amd64/vmx-asm.asm: -------------------------------------------------------------------------------- 1 | ; 2 | ; Copyright holder: Invisible Things Lab 3 | ; 4 | 5 | EXTERN VmExitHandler:PROC 6 | 7 | HVM_SAVE_ALL_NOSEGREGS MACRO 8 | push r15 9 | push r14 10 | push r13 11 | push r12 12 | push r11 13 | push r10 14 | push r9 15 | push r8 16 | push rdi 17 | push rsi 18 | push rbp 19 | push rbp ; rsp 20 | push rbx 21 | push rdx 22 | push rcx 23 | push rax 24 | ENDM 25 | 26 | HVM_RESTORE_ALL_NOSEGREGS MACRO 27 | pop rax 28 | pop rcx 29 | pop rdx 30 | pop rbx 31 | pop rbp ; rsp 32 | pop rbp 33 | pop rsi 34 | pop rdi 35 | pop r8 36 | pop r9 37 | pop r10 38 | pop r11 39 | pop r12 40 | pop r13 41 | pop r14 42 | pop r15 43 | ENDM 44 | 45 | .CODE 46 | GuestHookExitPoint Proc 47 | 48 | HVM_RESTORE_ALL_NOSEGREGS 49 | ret 50 | GuestHookExitPoint Endp 51 | set_in_cr4 PROC 52 | mov rax,cr4 53 | or rcx,rax 54 | mov cr4,rcx 55 | ret 56 | set_in_cr4 ENDP 57 | 58 | clear_in_cr4 PROC 59 | mov rax,cr4 60 | not rcx 61 | and rcx,rax 62 | mov cr4,rcx 63 | ret 64 | clear_in_cr4 ENDP 65 | 66 | 67 | VmxRead PROC 68 | vmread rax, rcx 69 | ret 70 | VmxRead ENDP 71 | 72 | VmxVmCall PROC 73 | vmcall 74 | ret 75 | VmxVmCall ENDP 76 | 77 | 78 | ; Stack layout for vmxLaunch() call: 79 | ; 80 | ; ^ ^ 81 | ; | | 82 | ; | lots of pages for host stack | 83 | ; | | 84 | ; |------------------------------| <- HostStackBottom(rcx) points here 85 | ; | struct CPU | 86 | ; -------------------------------- 87 | 88 | ;====== VmxVMexitHandler ====== 89 | 90 | VmxVmexitHandler PROC 91 | 92 | HVM_SAVE_ALL_NOSEGREGS 93 | 94 | mov rcx, rsp ;GuestRegs 95 | 96 | sub rsp, 28h 97 | call VmExitHandler 98 | add rsp, 28h 99 | 100 | HVM_RESTORE_ALL_NOSEGREGS 101 | vmresume 102 | ret 103 | 104 | VmxVmexitHandler ENDP 105 | 106 | END 107 | -------------------------------------------------------------------------------- /VT_demo/VMH/amd64/regs.asm: -------------------------------------------------------------------------------- 1 | 2 | .CODE 3 | 4 | RegGetCs PROC 5 | mov rax, cs 6 | ret 7 | RegGetCs ENDP 8 | 9 | RegGetDs PROC 10 | mov rax, ds 11 | ret 12 | RegGetDs ENDP 13 | 14 | RegGetEs PROC 15 | mov rax, es 16 | ret 17 | RegGetEs ENDP 18 | 19 | RegGetSs PROC 20 | mov rax, ss 21 | ret 22 | RegGetSs ENDP 23 | 24 | RegGetFs PROC 25 | mov rax, fs 26 | ret 27 | RegGetFs ENDP 28 | 29 | RegGetGs PROC 30 | mov rax, gs 31 | ret 32 | RegGetGs ENDP 33 | 34 | 35 | RegGetDr0 PROC 36 | mov rax, dr0 37 | ret 38 | RegGetDr0 ENDP 39 | 40 | RegGetDr1 PROC 41 | mov rax, dr1 42 | ret 43 | RegGetDr1 ENDP 44 | 45 | RegGetDr2 PROC 46 | mov rax, dr2 47 | ret 48 | RegGetDr2 ENDP 49 | 50 | RegGetDr3 PROC 51 | mov rax, dr3 52 | ret 53 | RegGetDr3 ENDP 54 | 55 | RegSetDr0 PROC 56 | mov dr0, rcx 57 | ret 58 | RegSetDr0 ENDP 59 | 60 | RegSetDr1 PROC 61 | mov dr1, rcx 62 | ret 63 | RegSetDr1 ENDP 64 | 65 | RegSetDr2 PROC 66 | mov dr2, rcx 67 | ret 68 | RegSetDr2 ENDP 69 | 70 | _SetDr6 PROC 71 | mov dr6, rcx 72 | ret 73 | _SetDr6 ENDP 74 | 75 | CallRetAddr PROC 76 | call rcx 77 | ret 78 | CallRetAddr ENDP 79 | RegSetDr3 PROC 80 | mov dr3, rcx 81 | ret 82 | RegSetDr3 ENDP 83 | 84 | 85 | RegGetRflags PROC 86 | pushfq 87 | pop rax 88 | ret 89 | RegGetRflags ENDP 90 | 91 | RegGetRsp PROC 92 | mov rax, rsp 93 | add rax, 8 94 | ret 95 | RegGetRsp ENDP 96 | 97 | GetIdtBase PROC 98 | LOCAL idtr[10]:BYTE 99 | 100 | sidt idtr 101 | mov rax, QWORD PTR idtr[2] 102 | ret 103 | GetIdtBase ENDP 104 | 105 | GetIdtLimit PROC 106 | LOCAL idtr[10]:BYTE 107 | 108 | sidt idtr 109 | mov ax, WORD PTR idtr[0] 110 | ret 111 | GetIdtLimit ENDP 112 | 113 | GetGdtBase PROC 114 | LOCAL gdtr[10]:BYTE 115 | 116 | sgdt gdtr 117 | mov rax, QWORD PTR gdtr[2] 118 | ret 119 | GetGdtBase ENDP 120 | 121 | GetGdtLimit PROC 122 | LOCAL gdtr[10]:BYTE 123 | 124 | sgdt gdtr 125 | mov ax, WORD PTR gdtr[0] 126 | ret 127 | GetGdtLimit ENDP 128 | 129 | 130 | GetLdtr PROC 131 | sldt rax 132 | ret 133 | GetLdtr ENDP 134 | 135 | GetTrSelector PROC 136 | str rax 137 | ret 138 | GetTrSelector ENDP 139 | 140 | 141 | END 142 | -------------------------------------------------------------------------------- /VT_demo/Hooks/PageHook.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | #include "ntddk.h" 3 | 4 | typedef enum _PAGE_TYPE 5 | { 6 | DATA_PAGE = 0, 7 | CODE_PAGE = 1, 8 | } PAGE_TYPE; 9 | 10 | typedef struct _PAGE_HOOK_ENTRY 11 | { 12 | LIST_ENTRY Link; 13 | PVOID OriginalPtr; // Original function VA 14 | PVOID DataPageVA; // Data page VA 15 | ULONG64 DataPagePFN; // Data page PFN 16 | PVOID CodePageVA; // Executable page VA 17 | ULONG64 CodePagePFN; // Executable page PFN 18 | ULONG OriginalSize; // Size of original data 19 | UCHAR OriginalData[80]; // Original bytes + jump 20 | } PAGE_HOOK_ENTRY, *PPAGE_HOOK_ENTRY; 21 | 22 | /// 23 | /// Hook function 24 | /// 25 | /// Function address 26 | /// Hook address 27 | /// /// Hook type 28 | /// Status code 29 | NTSTATUS PHHook( IN PVOID pFunc, IN PVOID pHook ); 30 | 31 | /// 32 | /// Restore hooked function 33 | /// 34 | /// Function address 35 | /// Status code 36 | NTSTATUS PHRestore( IN PVOID pFunc ); 37 | 38 | /// 39 | /// Get hook data by function pointer 40 | /// 41 | /// Function address 42 | /// Found entry or NULL 43 | PPAGE_HOOK_ENTRY PHGetHookEntry( IN PVOID ptr ); 44 | 45 | /// 46 | /// Get number of hooks in one page 47 | /// 48 | /// Function address 49 | /// Page type 50 | /// Number of hooks 51 | ULONG PHPageHookCount( IN PVOID ptr, IN PAGE_TYPE Type ); 52 | 53 | /// 54 | /// Get hook data by page address 55 | /// 56 | /// Function pointer 57 | /// Page type 58 | /// Found hook entry or NULL 59 | PPAGE_HOOK_ENTRY PHGetHookEntryByPage( IN PVOID ptr, IN PAGE_TYPE Type ); 60 | 61 | /// 62 | /// Get hook data by Physical page frame number 63 | /// 64 | /// PFN 65 | /// Page type 66 | /// Found hook entry or NULL 67 | PPAGE_HOOK_ENTRY PHGetHookEntryByPFN( IN ULONG64 pfn, IN PAGE_TYPE Type ); 68 | 69 | 70 | NTSTATUS PHHOOK2(IN PVOID pFunc, IN PVOID code, IN ULONG Size); -------------------------------------------------------------------------------- /VT_demo/DbgIsMyProcess.c: -------------------------------------------------------------------------------- 1 | #include "ntddk.h" 2 | 3 | typedef struct _DbgProcess 4 | { 5 | LIST_ENTRY64 DbgProcessList; 6 | PEPROCESS DebugProcess; 7 | PEPROCESS Process; 8 | POBJECT_TYPE DebugObject; 9 | HANDLE DbgHanle; 10 | }DbgProcess, *PDbgProcess; 11 | 12 | static LIST_ENTRY64 DbgList; 13 | static KSPIN_LOCK d_lock; 14 | 15 | VOID InitialzeDbgprocessList(){ 16 | 17 | KeInitializeSpinLock(&d_lock); 18 | InitializeListHead(&DbgList); 19 | } 20 | 21 | 22 | PDbgProcess Debug_AddStructToList(PDbgProcess DbgStruct){ 23 | PDbgProcess pstruct = NULL; 24 | if (MmIsAddressValid(DbgStruct)==TRUE) 25 | { 26 | pstruct = (PDbgProcess)ExAllocatePoolWithTag(NonPagedPool, sizeof(DbgProcess), "dbx"); 27 | 28 | if (!pstruct) 29 | { 30 | return FALSE; 31 | } 32 | RtlZeroMemory(pstruct, sizeof(DbgProcess)); 33 | 34 | pstruct->DbgHanle = DbgStruct->DbgHanle; 35 | pstruct->DebugObject = DbgStruct->DebugObject; 36 | pstruct->DebugProcess = DbgStruct->DebugProcess; 37 | pstruct->Process = DbgStruct->Process; 38 | ExInterlockedInsertTailList(&DbgList, &pstruct->DbgProcessList, &d_lock); 39 | return pstruct; 40 | } 41 | return FALSE; 42 | 43 | 44 | } 45 | 46 | VOID NTAPI Debug_ExFreeItem(PDbgProcess Item) 47 | { 48 | KIRQL OldIrql; 49 | KeAcquireSpinLock(&d_lock, &OldIrql); 50 | RemoveEntryList(&Item->DbgProcessList); 51 | KeReleaseSpinLock(&d_lock, OldIrql); 52 | ExFreePool(Item); 53 | return; 54 | 55 | 56 | } 57 | 58 | PDbgProcess Debug_FindMyNeedData(PDbgProcess DbgStruct){ 59 | DbgProcess*Temp = NULL; 60 | DbgProcess*RetFind = NULL; 61 | KIRQL irql; 62 | PLIST_ENTRY64 Entry = NULL; 63 | if (MmIsAddressValid(DbgStruct)==TRUE) 64 | { 65 | KeAcquireSpinLock(&d_lock, &irql); 66 | Entry = DbgList.Flink; 67 | while (Entry != &DbgList){ 68 | Temp = CONTAINING_RECORD(Entry, DbgProcess, DbgProcessList); 69 | Entry= Entry->Flink; 70 | if (Temp->DbgHanle==DbgStruct->DbgHanle) 71 | { 72 | RetFind = Temp; 73 | break; 74 | } 75 | if (Temp->DebugObject == DbgStruct->DebugObject) 76 | { 77 | RetFind = Temp; 78 | break; 79 | } 80 | if (Temp->DebugProcess == DbgStruct->DebugProcess) 81 | { 82 | RetFind = Temp; 83 | break; 84 | } 85 | if (Temp->Process == DbgStruct->Process) 86 | { 87 | RetFind = Temp; 88 | break; 89 | } 90 | 91 | } 92 | 93 | 94 | KeReleaseSpinLock(&d_lock, irql); 95 | } 96 | return RetFind; 97 | 98 | } -------------------------------------------------------------------------------- /VT_demo/Util/Utils.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | #include 3 | 4 | /// 5 | /// Get CPU vendor 6 | /// 7 | /// Intel or AMD. If failed - Other 8 | enum _CPU_VENDOR UtilCPUVendor(); 9 | 10 | /// 11 | /// Get ntoskrnl base address 12 | /// 13 | /// Size of module 14 | /// Found address, NULL if not found 15 | PVOID UtilKernelBase( OUT PULONG pSize ); 16 | 17 | /// 18 | /// Gets SSDT base - KiSystemServiceTable 19 | /// 20 | /// SSDT base, NULL if not found 21 | struct _SYSTEM_SERVICE_DESCRIPTOR_TABLE* UtilSSDTBase(); 22 | 23 | /// 24 | /// Gets the SSDT entry address by index. 25 | /// 26 | /// Service index 27 | /// Found service address, NULL if not found 28 | PVOID UtilSSDTEntry( IN ULONG index ); 29 | 30 | /// 31 | /// Gather info about used physical pages 32 | /// 33 | /// Status code 34 | NTSTATUS UtilQueryPhysicalMemory(); 35 | 36 | /// 37 | /// Change protection of nonpaged system address 38 | /// 39 | /// Address 40 | /// Size of region 41 | /// New protection flags 42 | /// Status code 43 | NTSTATUS UtilProtectNonpagedMemory( IN PVOID ptr, IN ULONG64 size, IN ULONG protection ); 44 | 45 | /// 46 | /// Search for pattern 47 | /// 48 | /// Pattern to search for 49 | /// Used wildcard 50 | /// Pattern length 51 | /// Base address for searching 52 | /// Address range to search in 53 | /// Found location 54 | /// Status code 55 | NTSTATUS UtilSearchPattern( IN PCUCHAR pattern, IN UCHAR wildcard, IN ULONG_PTR len, IN const VOID* base, IN ULONG_PTR size, OUT PVOID* ppFound ); 56 | 57 | /// 58 | /// Find pattern in kernel PE section 59 | /// 60 | /// Section name 61 | /// Pattern data 62 | /// Pattern wildcard symbol 63 | /// Pattern length 64 | /// Found address 65 | /// Status code 66 | NTSTATUS UtilScanSection( IN PCCHAR section, IN PCUCHAR pattern, IN UCHAR wildcard, IN ULONG_PTR len, OUT PVOID* ppFound ); -------------------------------------------------------------------------------- /VT_demo/Arch/Intel/VmxEvent.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | #include 3 | 4 | typedef union _INTERRUPT_INFO_FIELD 5 | { 6 | ULONG32 All; 7 | struct 8 | { 9 | ULONG32 Vector : 8; 10 | ULONG32 Type : 3; 11 | ULONG32 ErrorCodeValid : 1; 12 | ULONG32 NMIUnblocking : 1; 13 | ULONG32 Reserved : 18; 14 | ULONG32 Valid : 1; 15 | } Fields; 16 | } INTERRUPT_INFO_FIELD, *PINTERRUPT_INFO_FIELD; 17 | 18 | typedef union _INTERRUPT_INJECT_INFO_FIELD 19 | { 20 | ULONG32 All; 21 | struct 22 | { 23 | ULONG32 Vector : 8; 24 | ULONG32 Type : 3; 25 | ULONG32 DeliverErrorCode : 1; 26 | ULONG32 Reserved : 19; 27 | ULONG32 Valid : 1; 28 | } Fields; 29 | } INTERRUPT_INJECT_INFO_FIELD, *PINTERRUPT_INJECT_INFO_FIELD; 30 | 31 | typedef enum _INTERRUPT_TYPE 32 | { 33 | INTERRUPT_EXTERNAL = 0, 34 | INTERRUPT_NMI = 2, 35 | INTERRUPT_HARDWARE_EXCEPTION = 3, 36 | INTERRUPT_SOFTWARE = 4, 37 | INTERRUPT_PRIVILIGED_EXCEPTION = 5, 38 | INTERRUPT_SOFTWARE_EXCEPTION = 6, 39 | INTERRUPT_OTHER_EVENT = 7 40 | } INTERRUPT_TYPE; 41 | 42 | typedef enum _VECTOR_EXCEPTION 43 | { 44 | VECTOR_DIVIDE_ERROR_EXCEPTION = 0, 45 | VECTOR_DEBUG_EXCEPTION = 1, 46 | VECTOR_NMI_INTERRUPT = 2, 47 | VECTOR_BREAKPOINT_EXCEPTION = 3, 48 | VECTOR_OVERFLOW_EXCEPTION = 4, 49 | VECTOR_BOUND_EXCEPTION = 5, 50 | VECTOR_INVALID_OPCODE_EXCEPTION = 6, 51 | VECTOR_DEVICE_NOT_AVAILABLE_EXCEPTION = 7, 52 | VECTOR_DOUBLE_FAULT_EXCEPTION = 8, 53 | VECTOR_COPROCESSOR_SEGMENT_OVERRUN = 9, 54 | VECTOR_INVALID_TSS_EXCEPTION = 10, 55 | VECTOR_SEGMENT_NOT_PRESENT = 11, 56 | VECTOR_STACK_FAULT_EXCEPTION = 12, 57 | VECTOR_GENERAL_PROTECTION_EXCEPTION = 13, 58 | VECTOR_PAGE_FAULT_EXCEPTION = 14, 59 | VECTOR_X87_FLOATING_POINT_ERROR = 16, 60 | VECTOR_ALIGNMENT_CHECK_EXCEPTION = 17, 61 | VECTOR_MACHINE_CHECK_EXCEPTION = 18, 62 | VECTOR_SIMD_FLOATING_POINT_EXCEPTION = 19, 63 | VECTOR_VIRTUALIZATION_EXCEPTION = 20 64 | } VECTOR_EXCEPTION; 65 | 66 | /// 67 | /// Inject interrupt or exception into guest 68 | /// 69 | /// INterrupt type 70 | /// IDT index 71 | /// Intruction length skip 72 | VOID VmxInjectEvent( INTERRUPT_TYPE InterruptType, VECTOR_EXCEPTION Vector, ULONG WriteLength ); -------------------------------------------------------------------------------- /.gitattributes: -------------------------------------------------------------------------------- 1 | ############################################################################### 2 | # Set default behavior to automatically normalize line endings. 3 | ############################################################################### 4 | * text=auto 5 | 6 | ############################################################################### 7 | # Set default behavior for command prompt diff. 8 | # 9 | # This is need for earlier builds of msysgit that does not have it on by 10 | # default for csharp files. 11 | # Note: This is only used by command line 12 | ############################################################################### 13 | #*.cs diff=csharp 14 | 15 | ############################################################################### 16 | # Set the merge driver for project and solution files 17 | # 18 | # Merging from the command prompt will add diff markers to the files if there 19 | # are conflicts (Merging from VS is not affected by the settings below, in VS 20 | # the diff markers are never inserted). Diff markers may cause the following 21 | # file extensions to fail to load in VS. An alternative would be to treat 22 | # these files as binary and thus will always conflict and require user 23 | # intervention with every merge. To do so, just uncomment the entries below 24 | ############################################################################### 25 | #*.sln merge=binary 26 | #*.csproj merge=binary 27 | #*.vbproj merge=binary 28 | #*.vcxproj merge=binary 29 | #*.vcproj merge=binary 30 | #*.dbproj merge=binary 31 | #*.fsproj merge=binary 32 | #*.lsproj merge=binary 33 | #*.wixproj merge=binary 34 | #*.modelproj merge=binary 35 | #*.sqlproj merge=binary 36 | #*.wwaproj merge=binary 37 | 38 | ############################################################################### 39 | # behavior for image files 40 | # 41 | # image files are treated as binary by default. 42 | ############################################################################### 43 | #*.jpg binary 44 | #*.png binary 45 | #*.gif binary 46 | 47 | ############################################################################### 48 | # diff behavior for common document formats 49 | # 50 | # Convert binary document formats to text before diffing them. This feature 51 | # is only available from the command line. Turn it on by uncommenting the 52 | # entries below. 53 | ############################################################################### 54 | #*.doc diff=astextplain 55 | #*.DOC diff=astextplain 56 | #*.docx diff=astextplain 57 | #*.DOCX diff=astextplain 58 | #*.dot diff=astextplain 59 | #*.DOT diff=astextplain 60 | #*.pdf diff=astextplain 61 | #*.PDF diff=astextplain 62 | #*.rtf diff=astextplain 63 | #*.RTF diff=astextplain 64 | -------------------------------------------------------------------------------- /VT_demo/Txoo.h: -------------------------------------------------------------------------------- 1 | #include "ntddk.h" 2 | typedef struct _DbgProcess 3 | { 4 | LIST_ENTRY64 DbgProcessList; 5 | PEPROCESS DebugProcess; 6 | PEPROCESS Process; 7 | POBJECT_TYPE DebugObject; 8 | HANDLE DbgHanle; 9 | }DbgProcess, *PDbgProcess; 10 | 11 | typedef NTSTATUS(__fastcall *pfNtCreateDebugObject)( 12 | OUT PHANDLE DebugObjectHandle, 13 | IN ACCESS_MASK DesiredAccess, 14 | IN POBJECT_ATTRIBUTES ObjectAttributes, 15 | IN ULONG Flags 16 | ); 17 | 18 | typedef NTSTATUS( 19 | __fastcall* 20 | pfNtDebugActiveProcess)(IN HANDLE ProcessHandle, 21 | IN HANDLE DebugHandle); 22 | 23 | typedef 24 | NTSTATUS( 25 | __fastcall* pfNtWaitForDebugEvent)(IN HANDLE DebugHandle, 26 | IN BOOLEAN Alertable, 27 | IN PLARGE_INTEGER Timeout OPTIONAL, 28 | OUT ULONG64 StateChange); 29 | 30 | 31 | 32 | typedef 33 | NTSTATUS( 34 | __fastcall* 35 | pfNtDebugContinue)(IN HANDLE DebugHandle, 36 | IN PCLIENT_ID AppClientId, 37 | IN NTSTATUS ContinueStatus); 38 | typedef 39 | NTSTATUS 40 | (__fastcall* 41 | pfNtRemoveProcessDebug)(IN HANDLE ProcessHandle, 42 | IN HANDLE DebugHandle); 43 | typedef NTSTATUS (__fastcall *pfDbgkpQueueMessage)(IN PEPROCESS Process, IN PETHREAD Thread, IN OUT ULONG64 ApiMsg, IN ULONG Flags, IN ULONG64 TargetDebugObject); 44 | typedef VOID(__fastcall *pfDbgkMapViewOfSection)(IN PVOID Processs, 45 | IN PVOID Section, 46 | IN ULONG BaseAddress 47 | ); 48 | typedef VOID(__fastcall *pfDbgkUnMapViewOfSection)(IN PEPROCESS PROCESS, IN PVOID BaseAddress); 49 | typedef NTSTATUS (__fastcall *pfDbgkOpenProcessDebugPort)(IN PEPROCESS Process, IN KPROCESSOR_MODE PreviousMode, OUT HANDLE *DebugHandle); 50 | typedef VOID(__fastcall *pfDbgkCopyProcessDebugPort)(IN PEPROCESS Process, IN PEPROCESS Parent, IN ULONG64 unknow, IN ULONG64 unknow1); 51 | typedef BOOLEAN( __fastcall *pfDbgkForwardException)(IN PEXCEPTION_RECORD ExceptionRecord, IN BOOLEAN DebugPort, IN BOOLEAN SecondChance); 52 | extern pfNtCreateDebugObject ori_pslp40;//pfNtCreateDebugObject 53 | extern pfNtDebugActiveProcess ori_pslp43;//pfNtDebugActiveProcess 54 | extern pfNtWaitForDebugEvent ori_pslp41;//pfNtWaitForDebugEvent 55 | extern pfNtDebugContinue ori_pslp42;//pfNtDebugContinue 56 | extern pfNtRemoveProcessDebug ori_pslp44;//pfNtRemoveProcessDebug 57 | extern pfDbgkForwardException ori_pslp3;//pfDbgkForwardException 58 | extern pfDbgkCopyProcessDebugPort ori_pslp2;//pfDbgkCopyProcessDebugPort 59 | extern pfDbgkOpenProcessDebugPort ori_pslp4;//pfDbgkOpenProcessDebugPort 60 | extern pfDbgkUnMapViewOfSection ori_pslp5;//pfDbgkUnMapViewOfSection 61 | extern pfDbgkMapViewOfSection ori_pslp6; //pfDbgkMapViewOfSection 62 | extern pfDbgkpQueueMessage ori_pslp11;//pfDbgkpQueueMessage 63 | VOID NTAPI Debug_ExFreeItem(PDbgProcess Item); 64 | PDbgProcess Debug_FindMyNeedData(PDbgProcess DbgStruct); 65 | PDbgProcess Debug_AddStructToList(PDbgProcess DbgStruct); -------------------------------------------------------------------------------- /VT_demo/Test/Tests.c: -------------------------------------------------------------------------------- 1 | #include "Tests.h" 2 | #include "../Include/Common.h" 3 | #include "../Util/Utils.h" 4 | #include "../Hooks/PageHook.h" 5 | #include "../Hooks/SyscallHook.h" 6 | 7 | ULONG64 calls1 = 0, calls2 = 0; 8 | PVOID g_NtClose = NULL; 9 | typedef NTSTATUS( *pfnNtClose )(HANDLE); 10 | 11 | 12 | NTSTATUS hkNtClose( HANDLE handle ) 13 | { 14 | calls1++; 15 | 16 | return ((pfnNtClose)g_NtClose)(handle); 17 | } 18 | 19 | NTSTATUS hkNtClose2( HANDLE handle ) 20 | { 21 | PPAGE_HOOK_ENTRY pEntry = PHGetHookEntry( g_NtClose ); 22 | if (pEntry) 23 | { 24 | calls2++; 25 | DbgPrint("NTclose2"); 26 | return ((pfnNtClose)pEntry->OriginalData)(handle); 27 | } 28 | 29 | return STATUS_SUCCESS; 30 | } 31 | 32 | ULONG64 TestFn( ULONG64 in1, ULONG64 in2 ); 33 | #pragma alloc_text(".text0", TestFn) 34 | ULONG64 TestFn( ULONG64 in1, ULONG64 in2 ) 35 | { 36 | ULONG64 data1 = 0x500; 37 | data1 += in1; 38 | in2 -= 0x10; 39 | return in1 + in2 * 3 - in1 / in2 + data1; 40 | } 41 | 42 | ULONG64 hkTestFn( ULONG64 in1, ULONG64 in2 ); 43 | #pragma alloc_text(".text1", hkTestFn) 44 | ULONG64 hkTestFn( ULONG64 in1, ULONG64 in2 ) 45 | { 46 | // Call original 47 | PPAGE_HOOK_ENTRY pEntry = PHGetHookEntry( (PVOID)(ULONG_PTR)TestFn ); 48 | if (pEntry) 49 | ((ULONG64( *)(ULONG64, ULONG64))(ULONG_PTR)pEntry->OriginalData)(in1, in2); 50 | 51 | return 0xDEADBEEF; 52 | } 53 | 54 | VOID TestPageHook() 55 | { 56 | 57 | PVOID pFn = (PVOID)TestFn; 58 | 59 | PHHook( pFn, (PVOID)hkTestFn ); 60 | 61 | PHRestore( pFn ); 62 | 63 | 64 | } 65 | 66 | 67 | VOID TestStart( IN BOOLEAN SyscallHook, IN BOOLEAN PageHook1, IN IN BOOLEAN PageHook2 ) 68 | { 69 | if (PageHook1) 70 | { 71 | TestPageHook(); 72 | } 73 | 74 | g_NtClose = (PVOID)UtilSSDTEntry( SSDTIndex( &ZwClose ) ); 75 | if (g_NtClose) 76 | { 77 | if (SyscallHook) 78 | { 79 | if (NT_SUCCESS( SHInitHook() )) 80 | SHHookSyscall( SSDTIndex( &ZwClose ), (PVOID)hkNtClose, 1 ); 81 | else 82 | DPRINT( "HyperBone: CPU %d: %s: SHInitHook() failed\n", CPU_IDX, __FUNCTION__ ); 83 | } 84 | 85 | if (PageHook2) 86 | { 87 | if (g_NtClose) 88 | { 89 | if (!NT_SUCCESS( PHHook( g_NtClose, (PVOID)hkNtClose2 ) )) 90 | DPRINT( "HyperBone: CPU %d: %s: PHHook() failed\n", CPU_IDX, __FUNCTION__ ); 91 | } 92 | else 93 | DPRINT( "HyperBone: CPU %d: %s: NtClose not found\n", CPU_IDX, __FUNCTION__ ); 94 | } 95 | } 96 | else 97 | DPRINT( "HyperBone: CPU %d: %s: NtClose not found\n", CPU_IDX, __FUNCTION__ ); 98 | } 99 | 100 | VOID TestStop() 101 | { 102 | PVOID pFn = (PVOID)TestFn; 103 | PHRestore(pFn); 104 | } 105 | 106 | VOID TestPrintResults() 107 | { 108 | DPRINT( "HyperBone: CPU %d: %s: SyscallHook Calls made %d\n", CPU_IDX, __FUNCTION__, calls1 ); 109 | DPRINT( "HyperBone: CPU %d: %s: PageHook Calls made %d\n", CPU_IDX, __FUNCTION__, calls2 ); 110 | } -------------------------------------------------------------------------------- /VT_demo/ActiveProcessDbgList.c: -------------------------------------------------------------------------------- 1 | #include "ntddk.h" 2 | typedef struct _DbgPortList{ 3 | LIST_ENTRY PortList; 4 | ULONG64 DbgPort; 5 | UINT8 markdbg; 6 | PEPROCESS Process; 7 | }DbgPortList, *PDbgPortList; 8 | static LIST_ENTRY PortList ; 9 | static KSPIN_LOCK Port_lock = NULL; 10 | VOID InitDbgPortList(){ 11 | 12 | InitializeListHead(&PortList); 13 | KeInitializeSpinLock(&Port_lock); 14 | 15 | } 16 | PDbgPortList Port_FindProcessList(PEPROCESS Process ,ULONG64 DbgPort){ 17 | KIRQL OldIrql; 18 | PLIST_ENTRY Entry; 19 | DbgPortList *TempItem = NULL; 20 | DbgPortList* DFind = NULL; 21 | KeAcquireSpinLock(&Port_lock, &OldIrql); 22 | Entry = PortList.Flink; 23 | while (Entry != &PortList) 24 | { 25 | TempItem = CONTAINING_RECORD(Entry, DbgPortList, PortList); 26 | Entry = Entry->Flink; 27 | if (Process!=NULL) 28 | { 29 | 30 | if (TempItem->Process == Process) 31 | { 32 | DFind = TempItem; 33 | break; 34 | } 35 | } 36 | 37 | if (DbgPort != NULL) 38 | { 39 | if (TempItem->DbgPort == DbgPort) 40 | { 41 | DFind = TempItem; 42 | break; 43 | } 44 | } 45 | } 46 | KeReleaseSpinLock(&Port_lock, OldIrql); 47 | return DFind; 48 | } 49 | 50 | PDbgPortList Port_AddProcessToList(PEPROCESS Process,ULONG64 DbgPort){ 51 | PDbgPortList TempItem; 52 | TempItem = (PDbgPortList)ExAllocatePoolWithTag(NonPagedPool, sizeof(DbgPortList), 'prrp'); 53 | if (!TempItem) 54 | { 55 | return FALSE; 56 | } 57 | 58 | RtlZeroMemory(TempItem, sizeof(DbgPortList)); 59 | TempItem->Process = Process; 60 | TempItem->DbgPort = DbgPort; 61 | TempItem->markdbg = FALSE; 62 | ExInterlockedInsertTailList(&PortList, &TempItem->PortList, &Port_lock); 63 | if (TempItem != NULL) 64 | { 65 | 66 | return TempItem; 67 | } 68 | 69 | return FALSE; 70 | } 71 | BOOLEAN Port_SetPort(PEPROCESS Process, ULONG64 DbgPort){ 72 | PDbgPortList Temp = NULL; 73 | Temp=Port_AddProcessToList(Process, DbgPort); 74 | if (Temp != NULL){ 75 | 76 | 77 | return TRUE; 78 | } 79 | return FALSE; 80 | } 81 | BOOLEAN Port_IsPort(PEPROCESS Process){ 82 | PDbgPortList Temp = NULL; 83 | Temp=Port_FindProcessList(Process, NULL); 84 | if (Temp!=NULL) 85 | { 86 | if (Temp->DbgPort != NULL && Temp->Process == Process){ 87 | 88 | return TRUE; 89 | } 90 | } 91 | return FALSE; 92 | } 93 | ULONG64 Port_GetPort(PEPROCESS Process){ 94 | PDbgPortList Temp = NULL; 95 | Temp = Port_FindProcessList(Process, NULL); 96 | if (Temp != NULL) 97 | { 98 | if (Temp->DbgPort != NULL && Temp->Process == Process){ 99 | 100 | return Temp->DbgPort; 101 | } 102 | } 103 | return FALSE; 104 | } 105 | VOID NTAPI Port_ExFreeItem(PDbgPortList Item) 106 | { 107 | KIRQL OldIrql; 108 | KeAcquireSpinLock(&Port_lock, &OldIrql); 109 | RemoveEntryList(&Item->PortList); 110 | KeReleaseSpinLock(&Port_lock, OldIrql); 111 | ExFreePool(Item); 112 | return; 113 | 114 | 115 | } 116 | BOOLEAN Port_RemoveDbgItem(PEPROCESS Process, ULONG64 DbgPort){ 117 | 118 | PDbgPortList Temp = NULL; 119 | Temp = Port_FindProcessList(Process, DbgPort); 120 | if (Temp != NULL) 121 | { 122 | if (Process!=NULL) 123 | { 124 | if (Temp->Process == Process){ 125 | Port_ExFreeItem(Temp); 126 | return TRUE; 127 | } 128 | } 129 | 130 | if (DbgPort != NULL) 131 | { 132 | if (Temp->DbgPort == DbgPort){ 133 | Port_ExFreeItem(Temp); 134 | return TRUE; 135 | } 136 | } 137 | } 138 | return FALSE; 139 | 140 | } 141 | -------------------------------------------------------------------------------- /VT_demo/VMProtectDDK.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #define VMP_IMPORT __declspec(dllimport) 4 | #define VMP_API __stdcall 5 | #define VMP_WCHAR wchar_t 6 | #ifdef _WIN64 7 | #pragma comment(lib, "VMProtectDDK64.lib") 8 | #else 9 | #pragma comment(lib, "VMProtectDDK32.lib") 10 | #endif // _WIN64 11 | 12 | #ifdef __cplusplus 13 | extern "C" { 14 | #endif 15 | 16 | // protection 17 | VMP_IMPORT void VMP_API VMProtectBegin(const char *); 18 | VMP_IMPORT void VMP_API VMProtectBeginVirtualization(const char *); 19 | VMP_IMPORT void VMP_API VMProtectBeginMutation(const char *); 20 | VMP_IMPORT void VMP_API VMProtectBeginUltra(const char *); 21 | VMP_IMPORT void VMP_API VMProtectBeginVirtualizationLockByKey(const char *); 22 | VMP_IMPORT void VMP_API VMProtectBeginUltraLockByKey(const char *); 23 | VMP_IMPORT void VMP_API VMProtectEnd(void); 24 | 25 | // utils 26 | VMP_IMPORT int VMP_API VMProtectIsProtected(); 27 | VMP_IMPORT int VMP_API VMProtectIsDebuggerPresent(bool); 28 | VMP_IMPORT int VMP_API VMProtectIsVirtualMachinePresent(void); 29 | VMP_IMPORT int VMP_API VMProtectIsValidImageCRC(void); 30 | VMP_IMPORT const char * VMP_API VMProtectDecryptStringA(const char *value); 31 | VMP_IMPORT const VMP_WCHAR * VMP_API VMProtectDecryptStringW(const VMP_WCHAR *value); 32 | VMP_IMPORT int VMP_API VMProtectFreeString(const void *value); 33 | 34 | // licensing 35 | enum VMProtectSerialStateFlags 36 | { 37 | SERIAL_STATE_FLAG_CORRUPTED = 0x00000001, 38 | SERIAL_STATE_FLAG_INVALID = 0x00000002, 39 | SERIAL_STATE_FLAG_BLACKLISTED = 0x00000004, 40 | SERIAL_STATE_FLAG_DATE_EXPIRED = 0x00000008, 41 | SERIAL_STATE_FLAG_RUNNING_TIME_OVER = 0x00000010, 42 | SERIAL_STATE_FLAG_BAD_HWID = 0x00000020, 43 | SERIAL_STATE_FLAG_MAX_BUILD_EXPIRED = 0x00000040, 44 | }; 45 | 46 | #pragma pack(push, 1) 47 | typedef struct 48 | { 49 | unsigned short wYear; 50 | unsigned char bMonth; 51 | unsigned char bDay; 52 | } VMProtectDate; 53 | 54 | typedef struct 55 | { 56 | int nState; // VMProtectSerialStateFlags 57 | VMP_WCHAR wUserName[256]; // user name 58 | VMP_WCHAR wEMail[256]; // email 59 | VMProtectDate dtExpire; // date of serial number expiration 60 | VMProtectDate dtMaxBuild; // max date of build, that will accept this key 61 | int bRunningTime; // running time in minutes 62 | unsigned char nUserDataLength; // length of user data in bUserData 63 | unsigned char bUserData[255]; // up to 255 bytes of user data 64 | } VMProtectSerialNumberData; 65 | #pragma pack(pop) 66 | 67 | VMP_IMPORT int VMP_API VMProtectSetSerialNumber(const char *serial); 68 | VMP_IMPORT int VMP_API VMProtectGetSerialNumberState(); 69 | VMP_IMPORT int VMP_API VMProtectGetSerialNumberData(VMProtectSerialNumberData *data, int size); 70 | VMP_IMPORT int VMP_API VMProtectGetCurrentHWID(char *hwid, int size); 71 | 72 | // activation 73 | enum VMProtectActivationFlags 74 | { 75 | ACTIVATION_OK = 0, 76 | ACTIVATION_SMALL_BUFFER, 77 | ACTIVATION_NO_CONNECTION, 78 | ACTIVATION_BAD_REPLY, 79 | ACTIVATION_BANNED, 80 | ACTIVATION_CORRUPTED, 81 | ACTIVATION_BAD_CODE, 82 | ACTIVATION_ALREADY_USED, 83 | ACTIVATION_SERIAL_UNKNOWN, 84 | ACTIVATION_EXPIRED, 85 | ACTIVATION_NOT_AVAILABLE 86 | }; 87 | 88 | VMP_IMPORT int VMP_API VMProtectActivateLicense(const char *code, char *serial, int size); 89 | VMP_IMPORT int VMP_API VMProtectDeactivateLicense(const char *serial); 90 | VMP_IMPORT int VMP_API VMProtectGetOfflineActivationString(const char *code, char *buf, int size); 91 | VMP_IMPORT int VMP_API VMProtectGetOfflineDeactivationString(const char *serial, char *buf, int size); 92 | 93 | #ifdef __cplusplus 94 | } 95 | #endif -------------------------------------------------------------------------------- /VT_demo/Core/HVM.c: -------------------------------------------------------------------------------- 1 | #include "HVM.h" 2 | #include "../Arch/Intel/EPT.h" 3 | #include "../Arch/Intel/VMX.h" 4 | #include "../Util/Utils.h" 5 | 6 | /// 7 | /// Check if VT-x/AMD-V is supported 8 | /// 9 | /// TRUE if supported 10 | BOOLEAN HvmIsHVSupported() 11 | { 12 | CPU_VENDOR vendor = UtilCPUVendor(); 13 | if (vendor == CPU_Intel) 14 | return VmxHardSupported(); 15 | 16 | return TRUE; 17 | } 18 | 19 | /// 20 | /// CPU virtualization features 21 | /// 22 | VOID HvmCheckFeatures() 23 | { 24 | CPU_VENDOR vendor = UtilCPUVendor(); 25 | if (vendor == CPU_Intel) 26 | VmxCheckFeatures(); 27 | } 28 | 29 | // 30 | // Vendor-specific calls 31 | // 32 | VOID IntelSubvertCPU( IN PVCPU Vcpu, IN PVOID SystemDirectoryTableBase ) 33 | { 34 | VmxInitializeCPU( Vcpu, (ULONG64)SystemDirectoryTableBase ); 35 | } 36 | 37 | VOID IntelRestoreCPU( IN PVCPU Vcpu ) 38 | { 39 | // Prevent execution of VMCALL on non-vmx CPU 40 | if (Vcpu->VmxState > VMX_STATE_OFF) 41 | VmxShutdown( Vcpu ); 42 | } 43 | 44 | VOID AMDSubvertCPU( IN PVCPU Vcpu, IN PVOID arg ) 45 | { 46 | UNREFERENCED_PARAMETER( Vcpu ); 47 | UNREFERENCED_PARAMETER( arg ); 48 | //DPRINT( "HyperBone: CPU %d: %s: AMD-V not yet supported\n", CPU_IDX, __FUNCTION__ ); 49 | } 50 | 51 | VOID AMDRestoreCPU( IN PVCPU Vcpu ) 52 | { 53 | UNREFERENCED_PARAMETER( Vcpu ); 54 | // DPRINT( "HyperBone: CPU %d: %s: AMD-V not yet supported\n", CPU_IDX, __FUNCTION__ ); 55 | } 56 | 57 | VOID HvmpHVCallbackDPC( PRKDPC Dpc, PVOID Context, PVOID SystemArgument1, PVOID SystemArgument2 ) 58 | { 59 | UNREFERENCED_PARAMETER( Dpc ); 60 | PVCPU pVCPU = &g_Data->cpu_data[CPU_IDX]; 61 | 62 | // Check if we are loading, or unloading 63 | if (ARGUMENT_PRESENT( Context )) 64 | { 65 | // Initialize the virtual processor 66 | g_Data->CPUVendor == CPU_Intel ? IntelSubvertCPU( pVCPU, Context ) : AMDSubvertCPU( pVCPU, Context ); 67 | } 68 | else 69 | { 70 | // Tear down the virtual processor 71 | g_Data->CPUVendor == CPU_Intel ? IntelRestoreCPU( pVCPU ) : AMDRestoreCPU( pVCPU ); 72 | } 73 | 74 | // Wait for all DPCs to synchronize at this point 75 | KeSignalCallDpcSynchronize( SystemArgument2 ); 76 | 77 | // Mark the DPC as being complete 78 | KeSignalCallDpcDone( SystemArgument1 ); 79 | } 80 | 81 | 82 | /// 83 | /// Virtualize each CPU 84 | /// 85 | /// Status code 86 | NTSTATUS StartHV() 87 | { 88 | // Unknown CPU 89 | if (g_Data->CPUVendor == CPU_Other) 90 | return STATUS_NOT_SUPPORTED; 91 | 92 | KeGenericCallDpc( HvmpHVCallbackDPC, (PVOID)__readcr3() ); 93 | 94 | // Some CPU failed 95 | ULONG count = KeQueryActiveProcessorCountEx( ALL_PROCESSOR_GROUPS ); 96 | if (count != (ULONG)g_Data->vcpus) 97 | { 98 | // DPRINT( "HyperBone: CPU %d: %s: Some CPU failed to subvert\n", CPU_IDX, __FUNCTION__ ); 99 | StopHV(); 100 | return STATUS_UNSUCCESSFUL; 101 | } 102 | 103 | return STATUS_SUCCESS; 104 | } 105 | 106 | /// 107 | /// Devirtualize each CPU 108 | /// 109 | /// Status code 110 | NTSTATUS StopHV() 111 | { 112 | // Unknown CPU 113 | if (g_Data->CPUVendor == CPU_Other) 114 | return STATUS_NOT_SUPPORTED; 115 | 116 | KeGenericCallDpc( HvmpHVCallbackDPC, NULL ); 117 | 118 | return STATUS_SUCCESS; 119 | } 120 | 121 | -------------------------------------------------------------------------------- /VT_demo/common.c: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright holder: Invisible Things Lab 3 | */ 4 | 5 | #include "common.h" 6 | #include "hvm.h" 7 | 8 | NTSTATUS CmInitializeSegmentSelector ( 9 | SEGMENT_SELECTOR * SegmentSelector, 10 | USHORT Selector, 11 | PUCHAR GdtBase 12 | ) 13 | { 14 | PSEGMENT_DESCRIPTOR SegDesc; 15 | 16 | if (!SegmentSelector) 17 | return STATUS_INVALID_PARAMETER; 18 | 19 | if (Selector & 0x4) { 20 | KdPrint (("CmInitializeSegmentSelector(): Given selector (0x%X) points to LDT\n", Selector)); 21 | return STATUS_INVALID_PARAMETER; 22 | } 23 | 24 | SegDesc = (PSEGMENT_DESCRIPTOR) ((PUCHAR) GdtBase + (Selector & ~0x7)); 25 | 26 | SegmentSelector->sel = Selector; 27 | SegmentSelector->base = SegDesc->BaseLow | SegDesc->BaseMid << 16 | SegDesc->BaseHigh << 24; 28 | SegmentSelector->limit = SegDesc->LimitLow | SegDesc->LimitHigh << 16; 29 | SegmentSelector->attributes = SegDesc->AttributesLow | SegDesc->AttributesHigh << 8; 30 | 31 | if (!(SegDesc->AttributesLow & LA_STANDARD)) { 32 | // this is a TSS or callgate etc, save the base high part 33 | SegmentSelector->base |= (*(PULONG64) ((PUCHAR) SegDesc + 8)) << 32; 34 | } 35 | 36 | #define IS_GRANULARITY_4KB (1 << 0xB) 37 | 38 | if ( SegmentSelector->attributes & IS_GRANULARITY_4KB ) { 39 | // 4096-bit granularity is enabled for this segment, scale the limit 40 | SegmentSelector->limit = (SegmentSelector->limit << 12) | 0xfff; 41 | } 42 | 43 | return STATUS_SUCCESS; 44 | } 45 | 46 | 47 | NTSTATUS CmGenerateMovReg ( 48 | PUCHAR pCode, 49 | PULONG pGeneratedCodeLength, 50 | ULONG Register, 51 | ULONG64 Value 52 | ) 53 | { 54 | ULONG uCodeLength; 55 | 56 | if (!pCode || !pGeneratedCodeLength) 57 | return STATUS_INVALID_PARAMETER; 58 | 59 | switch (Register & ~REG_MASK) { 60 | case REG_GP: 61 | pCode[0] = 0x48; 62 | pCode[1] = 0xb8 | (UCHAR) (Register & REG_MASK); 63 | memcpy (&pCode[2], &Value, 8); 64 | uCodeLength = 10; 65 | break; 66 | 67 | case REG_GP_ADDITIONAL: 68 | pCode[0] = 0x49; 69 | pCode[1] = 0xb8 | (UCHAR) (Register & REG_MASK); 70 | memcpy (&pCode[2], &Value, 8); 71 | uCodeLength = 10; 72 | break; 73 | 74 | case REG_CONTROL: 75 | uCodeLength = *pGeneratedCodeLength; 76 | CmGenerateMovReg (pCode, pGeneratedCodeLength, REG_RAX, Value); 77 | // calc the size of the "mov rax, value" 78 | uCodeLength = *pGeneratedCodeLength - uCodeLength; 79 | pCode += uCodeLength; 80 | 81 | uCodeLength = 0; 82 | 83 | if (Register == (REG_CR8)) { 84 | // build 0x44 0x0f 0x22 0xc0 85 | pCode[0] = 0x44; 86 | uCodeLength = 1; 87 | pCode++; 88 | Register = 0; 89 | } 90 | // mov crX, rax 91 | 92 | pCode[0] = 0x0f; 93 | pCode[1] = 0x22; 94 | pCode[2] = 0xc0 | (UCHAR) ((Register & REG_MASK) << 3); 95 | 96 | // *pGeneratedCodeLength has already been adjusted to the length of the "mov rax" 97 | uCodeLength += 3; 98 | } 99 | 100 | if (pGeneratedCodeLength) 101 | *pGeneratedCodeLength += uCodeLength; 102 | 103 | return STATUS_SUCCESS; 104 | } 105 | 106 | 107 | NTSTATUS CmGenerateCallReg ( 108 | PUCHAR pCode, 109 | PULONG pGeneratedCodeLength, 110 | ULONG Register 111 | ) 112 | { 113 | ULONG uCodeLength; 114 | 115 | if (!pCode || !pGeneratedCodeLength) 116 | return STATUS_INVALID_PARAMETER; 117 | 118 | switch (Register & ~REG_MASK) { 119 | case REG_GP: 120 | pCode[0] = 0xff; 121 | pCode[1] = 0xd0 | (UCHAR) (Register & REG_MASK); 122 | uCodeLength = 2; 123 | break; 124 | 125 | case REG_GP_ADDITIONAL: 126 | pCode[0] = 0x41; 127 | pCode[1] = 0xff; 128 | pCode[1] = 0xd0 | (UCHAR) (Register & REG_MASK); 129 | uCodeLength = 3; 130 | break; 131 | } 132 | 133 | if (pGeneratedCodeLength) 134 | *pGeneratedCodeLength += uCodeLength; 135 | 136 | return STATUS_SUCCESS; 137 | } 138 | 139 | NTSTATUS CmGeneratePushReg ( 140 | PUCHAR pCode, 141 | PULONG pGeneratedCodeLength, 142 | ULONG Register 143 | ) 144 | { 145 | if (!pCode || !pGeneratedCodeLength) 146 | return STATUS_INVALID_PARAMETER; 147 | 148 | if ((Register & ~REG_MASK) != REG_GP) 149 | return STATUS_NOT_SUPPORTED; 150 | 151 | pCode[0] = 0x50 | (UCHAR) (Register & REG_MASK); 152 | *pGeneratedCodeLength += 1; 153 | 154 | return STATUS_SUCCESS; 155 | } 156 | 157 | 158 | NTSTATUS CmGenerateIretq ( 159 | PUCHAR pCode, 160 | PULONG pGeneratedCodeLength 161 | ) 162 | { 163 | if (!pCode || !pGeneratedCodeLength) 164 | return STATUS_INVALID_PARAMETER; 165 | 166 | pCode[0] = 0x48; 167 | pCode[1] = 0xcf; 168 | *pGeneratedCodeLength += 2; 169 | 170 | return STATUS_SUCCESS; 171 | } 172 | -------------------------------------------------------------------------------- /VT_demo/VMH/common.c: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright holder: Invisible Things Lab 3 | */ 4 | 5 | #include "common.h" 6 | #include "hvm.h" 7 | 8 | NTSTATUS CmInitializeSegmentSelector ( 9 | SEGMENT_SELECTOR * SegmentSelector, 10 | USHORT Selector, 11 | PUCHAR GdtBase 12 | ) 13 | { 14 | PSEGMENT_DESCRIPTOR SegDesc; 15 | 16 | if (!SegmentSelector) 17 | return STATUS_INVALID_PARAMETER; 18 | 19 | if (Selector & 0x4) { 20 | KdPrint (("CmInitializeSegmentSelector(): Given selector (0x%X) points to LDT\n", Selector)); 21 | return STATUS_INVALID_PARAMETER; 22 | } 23 | 24 | SegDesc = (PSEGMENT_DESCRIPTOR) ((PUCHAR) GdtBase + (Selector & ~0x7)); 25 | 26 | SegmentSelector->sel = Selector; 27 | SegmentSelector->base = SegDesc->BaseLow | SegDesc->BaseMid << 16 | SegDesc->BaseHigh << 24; 28 | SegmentSelector->limit = SegDesc->LimitLow | SegDesc->LimitHigh << 16; 29 | SegmentSelector->attributes = SegDesc->AttributesLow | SegDesc->AttributesHigh << 8; 30 | 31 | if (!(SegDesc->AttributesLow & LA_STANDARD)) { 32 | // this is a TSS or callgate etc, save the base high part 33 | SegmentSelector->base |= (*(PULONG64) ((PUCHAR) SegDesc + 8)) << 32; 34 | } 35 | 36 | #define IS_GRANULARITY_4KB (1 << 0xB) 37 | 38 | if ( SegmentSelector->attributes & IS_GRANULARITY_4KB ) { 39 | // 4096-bit granularity is enabled for this segment, scale the limit 40 | SegmentSelector->limit = (SegmentSelector->limit << 12) | 0xfff; 41 | } 42 | 43 | return STATUS_SUCCESS; 44 | } 45 | 46 | 47 | NTSTATUS CmGenerateMovReg ( 48 | PUCHAR pCode, 49 | PULONG pGeneratedCodeLength, 50 | ULONG Register, 51 | ULONG64 Value 52 | ) 53 | { 54 | ULONG uCodeLength; 55 | 56 | if (!pCode || !pGeneratedCodeLength) 57 | return STATUS_INVALID_PARAMETER; 58 | 59 | switch (Register & ~REG_MASK) { 60 | case REG_GP: 61 | pCode[0] = 0x48; 62 | pCode[1] = 0xb8 | (UCHAR) (Register & REG_MASK); 63 | memcpy (&pCode[2], &Value, 8); 64 | uCodeLength = 10; 65 | break; 66 | 67 | case REG_GP_ADDITIONAL: 68 | pCode[0] = 0x49; 69 | pCode[1] = 0xb8 | (UCHAR) (Register & REG_MASK); 70 | memcpy (&pCode[2], &Value, 8); 71 | uCodeLength = 10; 72 | break; 73 | 74 | case REG_CONTROL: 75 | uCodeLength = *pGeneratedCodeLength; 76 | CmGenerateMovReg (pCode, pGeneratedCodeLength, REG_RAX, Value); 77 | // calc the size of the "mov rax, value" 78 | uCodeLength = *pGeneratedCodeLength - uCodeLength; 79 | pCode += uCodeLength; 80 | 81 | uCodeLength = 0; 82 | 83 | if (Register == (REG_CR8)) { 84 | // build 0x44 0x0f 0x22 0xc0 85 | pCode[0] = 0x44; 86 | uCodeLength = 1; 87 | pCode++; 88 | Register = 0; 89 | } 90 | // mov crX, rax 91 | 92 | pCode[0] = 0x0f; 93 | pCode[1] = 0x22; 94 | pCode[2] = 0xc0 | (UCHAR) ((Register & REG_MASK) << 3); 95 | 96 | // *pGeneratedCodeLength has already been adjusted to the length of the "mov rax" 97 | uCodeLength += 3; 98 | } 99 | 100 | if (pGeneratedCodeLength) 101 | *pGeneratedCodeLength += uCodeLength; 102 | 103 | return STATUS_SUCCESS; 104 | } 105 | 106 | 107 | NTSTATUS CmGenerateCallReg ( 108 | PUCHAR pCode, 109 | PULONG pGeneratedCodeLength, 110 | ULONG Register 111 | ) 112 | { 113 | ULONG uCodeLength; 114 | 115 | if (!pCode || !pGeneratedCodeLength) 116 | return STATUS_INVALID_PARAMETER; 117 | 118 | switch (Register & ~REG_MASK) { 119 | case REG_GP: 120 | pCode[0] = 0xff; 121 | pCode[1] = 0xd0 | (UCHAR) (Register & REG_MASK); 122 | uCodeLength = 2; 123 | break; 124 | 125 | case REG_GP_ADDITIONAL: 126 | pCode[0] = 0x41; 127 | pCode[1] = 0xff; 128 | pCode[1] = 0xd0 | (UCHAR) (Register & REG_MASK); 129 | uCodeLength = 3; 130 | break; 131 | } 132 | 133 | if (pGeneratedCodeLength) 134 | *pGeneratedCodeLength += uCodeLength; 135 | 136 | return STATUS_SUCCESS; 137 | } 138 | 139 | NTSTATUS CmGeneratePushReg ( 140 | PUCHAR pCode, 141 | PULONG pGeneratedCodeLength, 142 | ULONG Register 143 | ) 144 | { 145 | if (!pCode || !pGeneratedCodeLength) 146 | return STATUS_INVALID_PARAMETER; 147 | 148 | if ((Register & ~REG_MASK) != REG_GP) 149 | return STATUS_NOT_SUPPORTED; 150 | 151 | pCode[0] = 0x50 | (UCHAR) (Register & REG_MASK); 152 | *pGeneratedCodeLength += 1; 153 | 154 | return STATUS_SUCCESS; 155 | } 156 | 157 | 158 | NTSTATUS CmGenerateIretq ( 159 | PUCHAR pCode, 160 | PULONG pGeneratedCodeLength 161 | ) 162 | { 163 | if (!pCode || !pGeneratedCodeLength) 164 | return STATUS_INVALID_PARAMETER; 165 | 166 | pCode[0] = 0x48; 167 | pCode[1] = 0xcf; 168 | *pGeneratedCodeLength += 2; 169 | 170 | return STATUS_SUCCESS; 171 | } 172 | -------------------------------------------------------------------------------- /VT_demo/Hooks/SyscallHook.c: -------------------------------------------------------------------------------- 1 | #include "SyscallHook.h" 2 | #include "../Include/CPU.h" 3 | #include "../Arch/Intel/VMX.h" 4 | #include "../Include/Common.h" 5 | #include "../Util/Utils.h" 6 | #include "../Include/Native.h" 7 | 8 | #define MAX_SYSCALL_INDEX 0x1000 9 | 10 | CHAR HookEnabled[MAX_SYSCALL_INDEX] = { 0 }; 11 | CHAR ArgTble[MAX_SYSCALL_INDEX] = { 0 }; 12 | PVOID HookTable[MAX_SYSCALL_INDEX] = { 0 }; 13 | 14 | ULONG64 KiSystemCall64Ptr = 0; // Original LSTAR value 15 | ULONG64 KiServiceCopyEndPtr = 0; // KiSystemServiceCopyEnd address 16 | 17 | // Implemented in Syscall.asm 18 | VOID SyscallEntryPoint(); 19 | 20 | /// 21 | /// Per-CPU LSTAR hook/unhook routine 22 | /// 23 | /// Unused 24 | /// New LASTAR value if hooking, 0 if unhooking 25 | /// Unused 26 | /// Unused 27 | VOID SHpHookCallbackDPC( PRKDPC Dpc, PVOID Context, PVOID SystemArgument1, PVOID SystemArgument2 ) 28 | { 29 | UNREFERENCED_PARAMETER( Dpc ); 30 | 31 | __vmx_vmcall( Context != NULL ? HYPERCALL_HOOK_LSTAR : HYPERCALL_UNHOOK_LSTAR, (ULONG64)Context, 0, 0 ); 32 | KeSignalCallDpcSynchronize( SystemArgument2 ); 33 | KeSignalCallDpcDone( SystemArgument1 ); 34 | } 35 | 36 | /// 37 | /// Perform LSTAR hooking 38 | /// 39 | /// Status code 40 | NTSTATUS SHInitHook() 41 | { 42 | NTSTATUS status = STATUS_SUCCESS; 43 | 44 | // No SSDT 45 | if (!UtilSSDTBase()) 46 | { 47 | DPRINT( "HyperBone: CPU %d: %s: SSDT base not found\n", CPU_IDX, __FUNCTION__ ); 48 | return STATUS_NOT_FOUND; 49 | } 50 | 51 | // KiSystemServiceCopyEnd 52 | // F7 05 ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 0F 85 ? ? ? ? ? ? ? ? 41 FF D2 53 | if (KiServiceCopyEndPtr == 0) 54 | { 55 | CHAR pattern[] = "\xF7\x05\xcc\xcc\xcc\xcc\xcc\xcc\xcc\xcc\x0F\x85\xcc\xcc\xcc\xcc\x41\xFF\xD2"; 56 | status = UtilScanSection( ".text", (PCUCHAR)pattern, 0xCC, sizeof( pattern ) - 1, (PVOID)&KiServiceCopyEndPtr ); 57 | if (!NT_SUCCESS( status )) 58 | { 59 | DPRINT( "HyperBone: CPU %d: %s: KiSystemServiceCopyEnd not found\n", CPU_IDX, __FUNCTION__ ); 60 | return status; 61 | } 62 | } 63 | 64 | // Hook LSTAR 65 | if (KiSystemCall64Ptr == 0) 66 | { 67 | KiSystemCall64Ptr = __readmsr( MSR_LSTAR ); 68 | 69 | // Something isn't right 70 | if (KiSystemCall64Ptr == 0) 71 | return STATUS_UNSUCCESSFUL; 72 | 73 | KeGenericCallDpc( SHpHookCallbackDPC, (PVOID)(ULONG_PTR)SyscallEntryPoint ); 74 | return STATUS_SUCCESS; 75 | } 76 | 77 | return STATUS_SUCCESS; 78 | } 79 | 80 | /// 81 | /// Unhook LSTAR 82 | /// 83 | /// Status code 84 | NTSTATUS SHDestroyHook() 85 | { 86 | NTSTATUS status = STATUS_SUCCESS; 87 | if (KiSystemCall64Ptr != 0) 88 | KeGenericCallDpc( SHpHookCallbackDPC, NULL ); 89 | 90 | if (NT_SUCCESS( status )) 91 | KiSystemCall64Ptr = 0; 92 | 93 | return status; 94 | } 95 | 96 | /// 97 | /// Hook specific SSDT entry 98 | /// 99 | /// SSDT index 100 | /// Hook address 101 | /// Number of function arguments 102 | /// Status code 103 | NTSTATUS SHHookSyscall( IN ULONG index, IN PVOID hookPtr, IN CHAR argCount ) 104 | { 105 | NTSTATUS status = STATUS_SUCCESS; 106 | if (index > MAX_SYSCALL_INDEX || hookPtr == NULL) 107 | return STATUS_INVALID_PARAMETER; 108 | 109 | KIRQL irql = KeGetCurrentIrql(); 110 | if (irql < DISPATCH_LEVEL) 111 | irql = KeRaiseIrqlToDpcLevel(); 112 | 113 | InterlockedExchange64( (PLONG64)&HookTable[index], (LONG64)hookPtr ); 114 | InterlockedExchange8( &ArgTble[index], argCount ); 115 | InterlockedExchange8( &HookEnabled[index], TRUE ); 116 | 117 | if (KeGetCurrentIrql() > irql) 118 | KeLowerIrql( irql ); 119 | 120 | return status; 121 | } 122 | 123 | /// 124 | /// Restore original SSDT entry 125 | /// 126 | /// SSDT index 127 | /// Status code 128 | NTSTATUS SHRestoreSyscall( IN ULONG index ) 129 | { 130 | if (index > MAX_SYSCALL_INDEX) 131 | return STATUS_INVALID_PARAMETER; 132 | 133 | KIRQL irql = KeGetCurrentIrql(); 134 | if (irql < DISPATCH_LEVEL) 135 | irql = KeRaiseIrqlToDpcLevel(); 136 | 137 | InterlockedExchange8( &HookEnabled[index], 0 ); 138 | InterlockedExchange8( &ArgTble[index], 0 ); 139 | InterlockedExchange64( (PLONG64)&HookTable[index], 0 ); 140 | 141 | if( KeGetCurrentIrql() > irql ) 142 | KeLowerIrql( irql ); 143 | 144 | return STATUS_SUCCESS; 145 | } 146 | 147 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | ## Ignore Visual Studio temporary files, build results, and 2 | ## files generated by popular Visual Studio add-ons. 3 | 4 | # User-specific files 5 | *.suo 6 | *.user 7 | *.userosscache 8 | *.sln.docstates 9 | 10 | # User-specific files (MonoDevelop/Xamarin Studio) 11 | *.userprefs 12 | 13 | # Build results 14 | [Dd]ebug/ 15 | [Dd]ebugPublic/ 16 | [Rr]elease/ 17 | [Rr]eleases/ 18 | [Xx]64/ 19 | [Xx]86/ 20 | [Bb]uild/ 21 | bld/ 22 | [Bb]in/ 23 | [Oo]bj/ 24 | 25 | # Visual Studio 2015 cache/options directory 26 | .vs/ 27 | # Uncomment if you have tasks that create the project's static files in wwwroot 28 | #wwwroot/ 29 | 30 | # MSTest test Results 31 | [Tt]est[Rr]esult*/ 32 | [Bb]uild[Ll]og.* 33 | 34 | # NUNIT 35 | *.VisualState.xml 36 | TestResult.xml 37 | 38 | # Build Results of an ATL Project 39 | [Dd]ebugPS/ 40 | [Rr]eleasePS/ 41 | dlldata.c 42 | 43 | # DNX 44 | project.lock.json 45 | artifacts/ 46 | 47 | *_i.c 48 | *_p.c 49 | *_i.h 50 | *.ilk 51 | *.meta 52 | *.obj 53 | *.pch 54 | *.pdb 55 | *.pgc 56 | *.pgd 57 | *.rsp 58 | *.sbr 59 | *.tlb 60 | *.tli 61 | *.tlh 62 | *.tmp 63 | *.tmp_proj 64 | *.log 65 | *.vspscc 66 | *.vssscc 67 | .builds 68 | *.pidb 69 | *.svclog 70 | *.scc 71 | 72 | # Chutzpah Test files 73 | _Chutzpah* 74 | 75 | # Visual C++ cache files 76 | ipch/ 77 | *.aps 78 | *.ncb 79 | *.opendb 80 | *.opensdf 81 | *.sdf 82 | *.cachefile 83 | *.VC.db 84 | 85 | # Visual Studio profiler 86 | *.psess 87 | *.vsp 88 | *.vspx 89 | *.sap 90 | 91 | # TFS 2012 Local Workspace 92 | $tf/ 93 | 94 | # Guidance Automation Toolkit 95 | *.gpState 96 | 97 | # ReSharper is a .NET coding add-in 98 | _ReSharper*/ 99 | *.[Rr]e[Ss]harper 100 | *.DotSettings.user 101 | 102 | # JustCode is a .NET coding add-in 103 | .JustCode 104 | 105 | # TeamCity is a build add-in 106 | _TeamCity* 107 | 108 | # DotCover is a Code Coverage Tool 109 | *.dotCover 110 | 111 | # NCrunch 112 | _NCrunch_* 113 | .*crunch*.local.xml 114 | nCrunchTemp_* 115 | 116 | # MightyMoose 117 | *.mm.* 118 | AutoTest.Net/ 119 | 120 | # Web workbench (sass) 121 | .sass-cache/ 122 | 123 | # Installshield output folder 124 | [Ee]xpress/ 125 | 126 | # DocProject is a documentation generator add-in 127 | DocProject/buildhelp/ 128 | DocProject/Help/*.HxT 129 | DocProject/Help/*.HxC 130 | DocProject/Help/*.hhc 131 | DocProject/Help/*.hhk 132 | DocProject/Help/*.hhp 133 | DocProject/Help/Html2 134 | DocProject/Help/html 135 | 136 | # Click-Once directory 137 | publish/ 138 | 139 | # Publish Web Output 140 | *.[Pp]ublish.xml 141 | *.azurePubxml 142 | 143 | # TODO: Un-comment the next line if you do not want to checkin 144 | # your web deploy settings because they may include unencrypted 145 | # passwords 146 | #*.pubxml 147 | *.publishproj 148 | 149 | # NuGet Packages 150 | *.nupkg 151 | # The packages folder can be ignored because of Package Restore 152 | **/packages/* 153 | # except build/, which is used as an MSBuild target. 154 | !**/packages/build/ 155 | # Uncomment if necessary however generally it will be regenerated when needed 156 | #!**/packages/repositories.config 157 | # NuGet v3's project.json files produces more ignoreable files 158 | *.nuget.props 159 | *.nuget.targets 160 | 161 | # Microsoft Azure Build Output 162 | csx/ 163 | *.build.csdef 164 | 165 | # Microsoft Azure Emulator 166 | ecf/ 167 | rcf/ 168 | 169 | # Windows Store app package directory 170 | AppPackages/ 171 | BundleArtifacts/ 172 | 173 | # Visual Studio cache files 174 | # files ending in .cache can be ignored 175 | *.[Cc]ache 176 | # but keep track of directories ending in .cache 177 | !*.[Cc]ache/ 178 | 179 | # Others 180 | ClientBin/ 181 | [Ss]tyle[Cc]op.* 182 | ~$* 183 | *~ 184 | *.dbmdl 185 | *.dbproj.schemaview 186 | *.pfx 187 | *.publishsettings 188 | node_modules/ 189 | orleans.codegen.cs 190 | 191 | # RIA/Silverlight projects 192 | Generated_Code/ 193 | 194 | # Backup & report files from converting an old project file 195 | # to a newer Visual Studio version. Backup files are not needed, 196 | # because we have git ;-) 197 | _UpgradeReport_Files/ 198 | Backup*/ 199 | UpgradeLog*.XML 200 | UpgradeLog*.htm 201 | 202 | # SQL Server files 203 | *.mdf 204 | *.ldf 205 | 206 | # Business Intelligence projects 207 | *.rdl.data 208 | *.bim.layout 209 | *.bim_*.settings 210 | 211 | # Microsoft Fakes 212 | FakesAssemblies/ 213 | 214 | # GhostDoc plugin setting file 215 | *.GhostDoc.xml 216 | 217 | # Node.js Tools for Visual Studio 218 | .ntvs_analysis.dat 219 | 220 | # Visual Studio 6 build log 221 | *.plg 222 | 223 | # Visual Studio 6 workspace options file 224 | *.opt 225 | 226 | # Visual Studio LightSwitch build output 227 | **/*.HTMLClient/GeneratedArtifacts 228 | **/*.DesktopClient/GeneratedArtifacts 229 | **/*.DesktopClient/ModelManifest.xml 230 | **/*.Server/GeneratedArtifacts 231 | **/*.Server/ModelManifest.xml 232 | _Pvt_Extensions 233 | 234 | # LightSwitch generated files 235 | GeneratedArtifacts/ 236 | ModelManifest.xml 237 | 238 | # Paket dependency manager 239 | .paket/paket.exe 240 | 241 | # FAKE - F# Make 242 | .fake/ 243 | -------------------------------------------------------------------------------- /VT_demo/hvm.c: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright holder: Invisible Things Lab 3 | */ 4 | 5 | #include "hvm.h" 6 | 7 | ULONG g_uSubvertedCPUs; 8 | CPU cpu[32]; 9 | 10 | NTSTATUS HvmSubvertCpu ( 11 | PVOID GuestRsp 12 | ) 13 | { 14 | PCPU pCpu = &cpu[KeGetCurrentProcessorNumber ()]; 15 | ULONG_PTR VMM_Stack; 16 | PHYSICAL_ADDRESS PhyAddr; 17 | 18 | KdPrint (("HvmSubvertCpu(): Running on processor #%d\n", KeGetCurrentProcessorNumber ())); 19 | 20 | // 检查IA32_FEATURE_CONTROL寄存器的Lock位 21 | if (!(__readmsr(MSR_IA32_FEATURE_CONTROL) & FEATURE_CONTROL_LOCKED)) 22 | { 23 | KdPrint(("VmxInitialize() IA32_FEATURE_CONTROL bit[0] = 0!\n")); 24 | return STATUS_UNSUCCESSFUL; 25 | } 26 | 27 | // 检查IA32_FEATURE_CONTROL寄存器的Enable VMX outside SMX位 28 | if (!(__readmsr(MSR_IA32_FEATURE_CONTROL) & FEATURE_CONTROL_VMXON_ENABLED)) 29 | { 30 | KdPrint(("VmxInitialize() IA32_FEATURE_CONTROL bit[2] = 0!\n")); 31 | return STATUS_UNSUCCESSFUL; 32 | } 33 | 34 | PhyAddr.QuadPart = -1; 35 | // 36 | // 为VMXON结构分配空间 (Allocate VMXON region) 37 | // 38 | pCpu->OriginaVmxonR = MmAllocateContiguousMemory(PAGE_SIZE, PhyAddr); 39 | if (!pCpu->OriginaVmxonR) 40 | { 41 | KdPrint (("VmxInitialize(): Failed to allocate memory for original VMXON\n")); 42 | return STATUS_INSUFFICIENT_RESOURCES; 43 | } 44 | RtlZeroMemory (pCpu->OriginaVmxonR, PAGE_SIZE); 45 | 46 | // 47 | // 为VMCS结构分配空间 (Allocate VMCS) 48 | // 49 | pCpu->OriginalVmcs = MmAllocateContiguousMemory(PAGE_SIZE, PhyAddr); 50 | if (!pCpu->OriginalVmcs) 51 | { 52 | KdPrint (("VmxInitialize(): Failed to allocate memory for original VMCS\n")); 53 | return STATUS_INSUFFICIENT_RESOURCES; 54 | } 55 | RtlZeroMemory (pCpu->OriginalVmcs, PAGE_SIZE); 56 | 57 | // 为Guest分配内核栈(按页分配), 大小与Host相同 58 | pCpu->VMM_Stack = ExAllocatePoolWithTag (NonPagedPool, 2 * PAGE_SIZE, MEM_TAG); 59 | if (!pCpu->VMM_Stack) 60 | { 61 | KdPrint (("HvmSubvertCpu(): Failed to allocate host stack!\n")); 62 | return STATUS_INSUFFICIENT_RESOURCES; 63 | } 64 | RtlZeroMemory (pCpu->VMM_Stack, 2 * PAGE_SIZE); 65 | 66 | // 67 | // 准备VM要用到的数据结构 (VMXON & VMCS ) 68 | // GuestRip和GuestRsp会被填进VMCS结构,代表Guest原本的代码位置和栈顶指针 69 | // 70 | 71 | set_in_cr4 (X86_CR4_VMXE); 72 | *(ULONG64 *) pCpu->OriginaVmxonR = (__readmsr(MSR_IA32_VMX_BASIC) & 0xffffffff); //set up vmcs_revision_id 73 | *(ULONG64 *) pCpu->OriginalVmcs = (__readmsr(MSR_IA32_VMX_BASIC) & 0xffffffff); 74 | 75 | PhyAddr = MmGetPhysicalAddress(pCpu->OriginaVmxonR); 76 | if (__vmx_on (&PhyAddr)) 77 | { 78 | KdPrint (("VmxOn Failed!\n")); 79 | return STATUS_UNSUCCESSFUL; 80 | } 81 | 82 | //============================= 配置VMCS ================================ 83 | PhyAddr = MmGetPhysicalAddress(pCpu->OriginalVmcs); 84 | __vmx_vmclear (&PhyAddr); // 取消当前的VMCS的激活状态 85 | __vmx_vmptrld (&PhyAddr); // 加载新的VMCS并设为激活状态 86 | 87 | VMM_Stack = (ULONG_PTR)pCpu->VMM_Stack + 2 * PAGE_SIZE - 8; 88 | if ( VmxSetupVMCS (VMM_Stack, CmGuestEip, GuestRsp) ) 89 | { 90 | KdPrint (("VmxSetupVMCS() failed!")); 91 | __vmx_off (); 92 | clear_in_cr4 (X86_CR4_VMXE); 93 | return STATUS_UNSUCCESSFUL; 94 | } 95 | 96 | InterlockedIncrement (&g_uSubvertedCPUs); // 已侵染的CPU数+=1 97 | 98 | // 一切准备工作完毕,使该CPU进入虚拟机 99 | __vmx_vmlaunch(); 100 | 101 | // never reached 102 | InterlockedDecrement (&g_uSubvertedCPUs); 103 | return STATUS_SUCCESS; 104 | } 105 | 106 | NTSTATUS 107 | HvmSpitOutBluepill () 108 | { 109 | KIRQL OldIrql; 110 | CHAR i; 111 | 112 | // 遍历所有处理器 113 | for (i = 0; i < KeNumberProcessors; i++) 114 | { 115 | KeSetSystemAffinityThread ((KAFFINITY) ((ULONG_PTR)1 << i)); // 将代码运行在指定CPU 116 | OldIrql = KeRaiseIrqlToDpcLevel (); 117 | 118 | VmxVmCall (NBP_HYPERCALL_UNLOAD); 119 | 120 | KeLowerIrql (OldIrql); 121 | KeRevertToUserAffinityThread (); 122 | } 123 | 124 | return STATUS_SUCCESS; 125 | } 126 | 127 | NTSTATUS 128 | HvmSwallowBluepill () 129 | { 130 | NTSTATUS Status; 131 | KIRQL OldIrql; 132 | CHAR i; 133 | 134 | // 遍历所有处理器 135 | for (i = 0; i < KeNumberProcessors; i++) 136 | { 137 | KeSetSystemAffinityThread ((KAFFINITY) ((ULONG_PTR)1 << i)); // 将代码运行在指定CPU 138 | OldIrql = KeRaiseIrqlToDpcLevel (); 139 | 140 | Status = CmSubvert (NULL); // CmSubvert的流程是保存所有寄存器(除了段寄存器)的内容到栈里后,调用HvmSubvertCpu 141 | 142 | KeLowerIrql (OldIrql); 143 | KeRevertToUserAffinityThread (); 144 | 145 | if (Status) 146 | { 147 | KdPrint (("HvmSwallowBluepill(): CmSubvert() failed with status 0x%08hX\n", Status)); 148 | break; 149 | } 150 | } 151 | 152 | if (KeNumberProcessors != g_uSubvertedCPUs) // 如果没有对每个核都侵染成功,则撤销更改 153 | { 154 | HvmSpitOutBluepill (); 155 | return STATUS_UNSUCCESSFUL; 156 | } 157 | 158 | return Status; 159 | } 160 | -------------------------------------------------------------------------------- /VT_demo/Hooks/Syscall.asm: -------------------------------------------------------------------------------- 1 | EXTERN HookEnabled:DB 2 | EXTERN ArgTble:DB 3 | EXTERN HookTable:DQ 4 | 5 | EXTERN KiSystemCall64Ptr:DQ 6 | EXTERN KiServiceCopyEndPtr:DQ 7 | 8 | USERMD_STACK_GS = 10h 9 | KERNEL_STACK_GS = 1A8h 10 | 11 | MAX_SYSCALL_INDEX = 1000h 12 | 13 | .CODE 14 | 15 | ; ********************************************************* 16 | ; 17 | ; Determine if the specific syscall should be hooked 18 | ; 19 | ; if (SyscallHookEnabled[EAX & 0xFFF] == TRUE) 20 | ; jmp KiSystemCall64_Emulate 21 | ; else (fall-through) 22 | ; jmp KiSystemCall64 23 | ; 24 | ; ********************************************************* 25 | SyscallEntryPoint PROC 26 | ;cli ; Disable interrupts 27 | swapgs ; swap GS base to kernel PCR 28 | mov gs:[USERMD_STACK_GS], rsp ; save user stack pointer 29 | 30 | cmp rax, MAX_SYSCALL_INDEX ; Is the index larger than the array size? 31 | jge KiSystemCall64 ; 32 | 33 | lea rsp, offset HookEnabled ; RSP = &SyscallHookEnabled 34 | cmp byte ptr [rsp + rax], 0 ; Is hooking enabled for this index? 35 | jne KiSystemCall64_Emulate ; NE = index is hooked 36 | SyscallEntryPoint ENDP 37 | 38 | ; ********************************************************* 39 | ; 40 | ; Return to the original NTOSKRNL syscall handler 41 | ; (Restore all old registers first) 42 | ; 43 | ; ********************************************************* 44 | KiSystemCall64 PROC 45 | mov rsp, gs:[USERMD_STACK_GS] ; Usermode RSP 46 | swapgs ; Switch to usermode GS 47 | jmp [KiSystemCall64Ptr] ; Jump back to the old syscall handler 48 | KiSystemCall64 ENDP 49 | 50 | ; ********************************************************* 51 | ; 52 | ; Emulated routine executed directly after a SYSCALL 53 | ; (See: MSR_LSTAR) 54 | ; 55 | ; ********************************************************* 56 | KiSystemCall64_Emulate PROC 57 | ; NOTE: 58 | ; First 2 lines are included in SyscallEntryPoint 59 | 60 | mov rsp, gs:[KERNEL_STACK_GS] ; set kernel stack pointer 61 | push 2Bh ; push dummy SS selector 62 | push qword ptr gs:[10h] ; push user stack pointer 63 | push r11 ; push previous EFLAGS 64 | push 33h ; push dummy 64-bit CS selector 65 | push rcx ; push return address 66 | mov rcx, r10 ; set first argument value 67 | 68 | sub rsp, 8h ; allocate dummy error code 69 | push rbp ; save standard register 70 | sub rsp, 158h ; allocate fixed frame 71 | lea rbp, [rsp+80h] ; set frame pointer 72 | mov [rbp+0C0h], rbx ; save nonvolatile registers 73 | mov [rbp+0C8h], rdi ; 74 | mov [rbp+0D0h], rsi ; 75 | mov byte ptr [rbp-55h], 2h ; set service active 76 | mov rbx, gs:[188h] ; get current thread address 77 | prefetchw byte ptr [rbx+90h] ; prefetch with write intent 78 | stmxcsr dword ptr [rbp-54h] ; save current MXCSR 79 | ldmxcsr dword ptr gs:[180h] ; set default MXCSR 80 | cmp byte ptr [rbx+3], 0 ; test if debug enabled 81 | mov word ptr [rbp+80h], 0 ; assume debug not enabled 82 | jz KiSS05 ; if z, debug not enabled 83 | mov [rbp-50h], rax ; save service argument registers 84 | mov [rbp-48h], rcx ; 85 | mov [rbp-40h], rdx ; 86 | mov [rbp-38h], r8 ; 87 | mov [rbp-30h], r9 ; 88 | 89 | int 3 ; FIXME (Syscall with debug registers active) 90 | align 10h 91 | 92 | KiSS05: 93 | ;sti ; enable interrupts 94 | mov [rbx+88h], rcx 95 | mov [rbx+80h], eax 96 | 97 | KiSystemCall64_Emulate ENDP 98 | 99 | KiSystemServiceStart_Emulate PROC 100 | mov [rbx+90h], rsp 101 | mov edi, eax 102 | shr edi, 7 103 | and edi, 20h 104 | and eax, 0FFFh 105 | KiSystemServiceStart_Emulate ENDP 106 | 107 | KiSystemServiceRepeat_Emulate PROC 108 | ; RAX = [IN ] syscall index 109 | ; RAX = [OUT] number of parameters 110 | ; R10 = [OUT] function address 111 | ; R11 = [I/O] trashed 112 | 113 | lea r11, offset HookTable 114 | mov r10, qword ptr [r11 + rax * 8h] 115 | 116 | lea r11, offset ArgTble 117 | movzx rax, byte ptr [r11 + rax] ; RAX = paramter count 118 | 119 | jmp [KiServiceCopyEndPtr] 120 | KiSystemServiceRepeat_Emulate ENDP 121 | 122 | END -------------------------------------------------------------------------------- /VT_demo/DRRWE.c: -------------------------------------------------------------------------------- 1 | #include "ntddk.h" 2 | typedef LONG DWORD; 3 | typedef struct _THREAD_dr_List{ 4 | LIST_ENTRY TList; 5 | DWORD Dr0; 6 | DWORD Dr1; 7 | DWORD Dr2; 8 | DWORD Dr3; 9 | DWORD Dr6; 10 | DWORD Dr7; 11 | DWORD eflag; 12 | PETHREAD Thread; 13 | 14 | }THREAD_dr_List, *PTHREAD_dr_List; 15 | 16 | 17 | typedef struct _PROCESS_List{ 18 | LIST_ENTRY PorcessList; 19 | PEPROCESS Process; 20 | KSPIN_LOCK loacl_lock; 21 | LIST_ENTRY ThreadList; 22 | }PROCESS_List, *PPROCESS_List; 23 | 24 | static KSPIN_LOCK g_lock; 25 | static LIST_ENTRY DrRwList; 26 | VOID InitListAndLock(){ 27 | InitializeListHead(&DrRwList); 28 | KeInitializeSpinLock(&g_lock); 29 | } 30 | 31 | PPROCESS_List Dr_FindProcessList(PEPROCESS Process){ 32 | KIRQL OldIrql; 33 | PLIST_ENTRY Entry; 34 | PROCESS_List *TempItem = NULL; 35 | PROCESS_List* DFind = NULL; 36 | KeAcquireSpinLock(&g_lock, &OldIrql); 37 | Entry = DrRwList.Flink; 38 | while (Entry!=&DrRwList) 39 | { 40 | TempItem = CONTAINING_RECORD(Entry, PROCESS_List, PorcessList); 41 | 42 | Entry = Entry->Flink; 43 | if (TempItem->Process==Process) 44 | { 45 | DFind = TempItem; 46 | break; 47 | } 48 | } 49 | KeReleaseSpinLock(&g_lock, OldIrql); 50 | return DFind; 51 | } 52 | PPROCESS_List Dr_AddProcessToList(PEPROCESS Process){ 53 | PPROCESS_List TempItem; 54 | TempItem = (PPROCESS_List)ExAllocatePoolWithTag(NonPagedPool, sizeof(PROCESS_List), 'drrp'); 55 | if (!TempItem) 56 | { 57 | return FALSE; 58 | } 59 | 60 | RtlZeroMemory(TempItem, sizeof(PROCESS_List)); 61 | TempItem->Process = Process; 62 | InitializeListHead(&TempItem->ThreadList); 63 | KeInitializeSpinLock(&TempItem->loacl_lock); 64 | ExInterlockedInsertTailList(&DrRwList,&TempItem->PorcessList,&g_lock); 65 | if (TempItem != NULL) 66 | { 67 | 68 | return TempItem; 69 | } 70 | 71 | return FALSE; 72 | } 73 | 74 | VOID NTAPI Dr_ExFreeItem(PPROCESS_List Item) 75 | { 76 | KIRQL OldIrql; 77 | KeAcquireSpinLock(&g_lock, &OldIrql); 78 | RemoveEntryList(&Item->PorcessList); 79 | KeReleaseSpinLock(&g_lock, OldIrql); 80 | ExFreePool(Item); 81 | return; 82 | 83 | 84 | } 85 | 86 | PTHREAD_dr_List Dr_AddThreadStructToList(PPROCESS_List DrRwListItem, PTHREAD_dr_List Struct){ 87 | 88 | PTHREAD_dr_List TempItem; 89 | TempItem = (PTHREAD_dr_List)ExAllocatePoolWithTag(NonPagedPool, sizeof(THREAD_dr_List), 'drrt'); 90 | if (!TempItem) 91 | { 92 | return FALSE; 93 | } 94 | RtlZeroMemory(TempItem, sizeof(THREAD_dr_List)); 95 | 96 | 97 | TempItem->Dr0 = Struct->Dr0; 98 | TempItem->Dr1 = Struct->Dr1; 99 | TempItem->Dr2 = Struct->Dr2; 100 | TempItem->Dr3 = Struct->Dr3; 101 | TempItem->Dr6 = Struct->Dr6; 102 | TempItem->Dr7 = Struct->Dr7; 103 | TempItem->eflag = Struct->eflag; 104 | 105 | TempItem->Thread = Struct->Thread; 106 | 107 | 108 | 109 | ExInterlockedInsertTailList(&DrRwListItem->ThreadList, &TempItem->TList, &DrRwListItem->loacl_lock); 110 | if (TempItem != NULL) 111 | { 112 | 113 | return TempItem; 114 | } 115 | } 116 | 117 | PTHREAD_dr_List Dr_FindThreadContextByThreadList(PPROCESS_List DrRwListItem, PETHREAD Thread){ 118 | KIRQL OldIrql; 119 | PLIST_ENTRY Entry; 120 | THREAD_dr_List *TempItem = NULL; 121 | THREAD_dr_List* DFind = NULL; 122 | KeAcquireSpinLock(&DrRwListItem->loacl_lock, &OldIrql); 123 | Entry = DrRwListItem->ThreadList.Flink; 124 | while (Entry != &DrRwListItem->ThreadList) 125 | { 126 | TempItem = CONTAINING_RECORD(Entry, THREAD_dr_List, TList); 127 | 128 | Entry = Entry->Flink; 129 | if (TempItem->Thread == Thread) 130 | { 131 | DFind = TempItem; 132 | break; 133 | } 134 | } 135 | 136 | KeReleaseSpinLock(&DrRwListItem->loacl_lock, OldIrql); 137 | 138 | return DFind; 139 | 140 | } 141 | 142 | 143 | PTHREAD_dr_List Dr_UpdataThreadContextByThreadList(PPROCESS_List DrRwListItem, PETHREAD Thread, PTHREAD_dr_List UpData){ 144 | KIRQL OldIrql; 145 | PLIST_ENTRY Entry; 146 | THREAD_dr_List *TempItem = NULL; 147 | THREAD_dr_List* DFind = NULL; 148 | KeAcquireSpinLock(&DrRwListItem->loacl_lock, &OldIrql); 149 | Entry = DrRwListItem->ThreadList.Flink; 150 | while (Entry != &DrRwListItem->ThreadList) 151 | { 152 | TempItem = CONTAINING_RECORD(Entry, THREAD_dr_List, TList); 153 | 154 | Entry = Entry->Flink; 155 | if (TempItem->Thread == Thread) 156 | { 157 | 158 | DFind = TempItem; 159 | DFind->Dr0 = UpData->Dr0; 160 | DFind->Dr1 = UpData->Dr1; 161 | DFind->Dr2 = UpData->Dr2; 162 | DFind->Dr3 = UpData->Dr3; 163 | DFind->Dr6 = UpData->Dr6; 164 | DFind->Dr7 = UpData->Dr7; 165 | DFind->eflag = UpData->eflag; 166 | 167 | 168 | break; 169 | } 170 | } 171 | 172 | KeReleaseSpinLock(&DrRwListItem->loacl_lock, OldIrql); 173 | 174 | return DFind; 175 | 176 | } 177 | 178 | 179 | VOID NTAPI Dr_ExFreeTheadListItem(PPROCESS_List DrRwListItem, PTHREAD_dr_List Struct) 180 | { 181 | KIRQL OldIrql; 182 | KeAcquireSpinLock(&DrRwListItem->loacl_lock, &OldIrql); 183 | 184 | RemoveEntryList(&Struct->TList); 185 | KeReleaseSpinLock(&DrRwListItem->loacl_lock, OldIrql); 186 | ExFreePool(Struct); 187 | return; 188 | 189 | 190 | } 191 | -------------------------------------------------------------------------------- /VT_demo/ept.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | #include "ntddk.h" 3 | #define EPT_READ 0x01 4 | #define EPT_WRIT 0x02 5 | #define EPT_EXECUTE 0x04 6 | 7 | typedef struct _MemoryType{ 8 | unsigned bit0 : 1; 9 | unsigned bit1 : 1; 10 | unsigned bit2 : 1; 11 | unsigned bit3 : 1; 12 | unsigned bit4 : 1; 13 | unsigned bit5 : 1; 14 | unsigned bit6 : 1; 15 | unsigned bit7 : 1; 16 | unsigned bit8 : 1; 17 | unsigned bit9 : 1; 18 | unsigned bit10 : 1; 19 | unsigned bit11 : 1; 20 | unsigned bit12 : 1; 21 | unsigned bit13 : 1; 22 | unsigned bit14 : 1; 23 | unsigned bit15 : 1; 24 | unsigned bit16 : 1; 25 | unsigned bit17 : 1; 26 | unsigned bit18 : 1; 27 | unsigned bit19 : 1; 28 | unsigned bit20 : 1; 29 | unsigned bit21 : 1; 30 | unsigned bit22 : 1; 31 | unsigned bit23 : 1; 32 | unsigned bit24 : 1; 33 | unsigned bit25 : 1; 34 | unsigned bit26 : 1; 35 | unsigned bit27 : 1; 36 | unsigned bit28 : 1; 37 | unsigned bit29 : 1; 38 | unsigned bit30 : 1; 39 | unsigned bit31 : 1; 40 | unsigned bit32 : 1; 41 | unsigned bit33 : 1; 42 | unsigned bit34 : 1; 43 | unsigned bit35 : 1; 44 | unsigned bit36 : 1; 45 | unsigned bit37 : 1; 46 | unsigned bit38 : 1; 47 | unsigned bit39 : 1; 48 | unsigned bit40 : 1; 49 | unsigned bit41 : 1; 50 | unsigned bit42 : 1; 51 | unsigned bit43 : 1; 52 | unsigned bit44 : 1; 53 | unsigned bit45 : 1; 54 | unsigned bit46 : 1; 55 | unsigned bit47 : 1; 56 | unsigned bit48 : 1; 57 | unsigned bit49 : 1; 58 | unsigned bit50 : 1; 59 | unsigned bit51 : 1; 60 | unsigned bit52 : 1; 61 | unsigned bit53 : 1; 62 | unsigned bit54 : 1; 63 | unsigned bit55 : 1; 64 | unsigned bit56 : 1; 65 | unsigned bit57 : 1; 66 | unsigned bit58 : 1; 67 | unsigned bit59 : 1; 68 | unsigned bit60 : 1; 69 | unsigned bit61 : 1; 70 | unsigned bit62 : 1; 71 | unsigned bit63 : 1; 72 | 73 | }MemoryType, *pMemoryType; 74 | 75 | typedef struct _InveptDescriptor{ 76 | ULONG64 EPTP; 77 | ULONG64 Reserve; 78 | }InveptDescriptor, *pInveptDescriptor; 79 | 80 | typedef struct _EPTP{ 81 | union{ 82 | struct{ 83 | unsigned MemType : 3; // bit0-bit2 84 | unsigned PageWalk : 3; // bit3-bit5 85 | unsigned dirty : 1; // bit6 86 | unsigned reserved : 5; // bit7-bit11 87 | unsigned pml4Pa : 28; // bit12-bit39 88 | unsigned reserved1 : 24; // bit40-bit63 89 | }; 90 | ULONG64 Value; 91 | }; 92 | }EPTP, *P_EPTP; 93 | 94 | typedef struct _EPTPML4E{ 95 | union{ 96 | struct{ 97 | unsigned R : 1; // bit0 98 | unsigned W : 1; // bit1 99 | unsigned E : 1; // bit2 100 | unsigned Reserved : 5; // bit3-bit7 101 | unsigned AccessedFlag : 1; // bit8 102 | unsigned Ignored : 3; // bit9-bit11 103 | unsigned PAGE_PA_39_12 : 28; // bit12-bit39 104 | unsigned Reserved1 : 12; // bit40-bit51 105 | unsigned Ignored1 : 12; // bit52-bit63 106 | }; 107 | ULONG64 Value; 108 | }; 109 | }EPTPML4E, *P_EPTPML4E; 110 | 111 | typedef struct _EPTPDPTE{ 112 | union{ 113 | struct{ 114 | unsigned R : 1; // bit0 115 | unsigned W : 1; // bit1 116 | unsigned E : 1; // bit2 117 | unsigned Reserved : 5; // bit3-bit7 118 | unsigned AccessedFlag : 1; // bit8 119 | unsigned Ignored : 3; // bit9-bit11 120 | unsigned PAGE_PA_39_12 : 28; // bit12-bit39 121 | unsigned Reserved1 : 12; // bit40-bit51 122 | unsigned Ignored1 : 12; // bit52-bit63 123 | }; 124 | ULONG64 Value; 125 | }; 126 | }EPTPDPTE, *P_EPTPDPTE; 127 | 128 | typedef struct _EPTPDE_2MB{ 129 | union{ 130 | struct{ 131 | unsigned R : 1; // bit0 132 | unsigned W : 1; // bit1 133 | unsigned E : 1; // bit2 134 | unsigned MemType : 3; // bit3-bit5 135 | unsigned IgnorePatMemType : 1; // bit6 136 | unsigned PS : 1; // bit7 137 | unsigned AccesedFlag : 1; // bit8 138 | unsigned DirtyFlag : 1; // bit9 139 | unsigned Ignored : 2; // bit10-bit11 140 | unsigned Reserved : 9; // bit12-bit20 141 | unsigned PAGE_PA_39_21 : 19; // bit21-bit39 142 | unsigned Reserved1 : 12; // bit40-bit51 143 | unsigned Ignored1 : 11; // bit52-bit62 144 | unsigned SuppressVE : 1; // bit63 145 | }; 146 | ULONG64 Value; 147 | }; 148 | 149 | }EPTPDE_2MB, *P_EPTPDE_2MB; 150 | 151 | typedef struct _EPT_VIOLATION{ 152 | union{ 153 | struct{ 154 | unsigned R : 1; // bit0 155 | unsigned W : 1; // bit1 156 | unsigned E : 1; // bit2 157 | unsigned PageRead : 1; // bit3 158 | unsigned PageWrite : 1; // bit4 159 | unsigned PageExecute : 1; // bit5 160 | unsigned Reserved : 1; // bit6 161 | unsigned LinearAddrValid : 1; // bit7 162 | unsigned IfBit7 : 1; // bit8 163 | unsigned Reserved1 : 3; // bit9-bit11 164 | unsigned NmiUnblocking : 1; // bit12 165 | unsigned Reserved2 : 19; //bit13-bit31 166 | }; 167 | ULONG64 Value; 168 | }; 169 | 170 | }EPT_VIOLATION, *P_EPT_VIOLATION; 171 | 172 | typedef struct _GUEST_PAGE{ 173 | union{ 174 | struct{ 175 | unsigned PageOffset : 21; // 2M bit0-bit20 176 | unsigned PDIndex : 9; // bit21-bit29 177 | unsigned PDPTIndex : 9; // bit30-bit38 178 | unsigned PML4Index : 9; // bit39-bit47 179 | unsigned Reserved : 16; 180 | }; 181 | ULONG64 Value; 182 | }; 183 | }GUEST_PAGE, *P_GUEST_PAGE; 184 | 185 | typedef struct _EPT_INFO{ 186 | EPTP Eptps; 187 | PHYSICAL_ADDRESS pPml4PA; 188 | PVOID pPml4s; 189 | PHYSICAL_ADDRESS pPdptPA; 190 | PVOID pPDPTs; 191 | PHYSICAL_ADDRESS pPdPA; 192 | PVOID pPDs; 193 | }EPT_INFO, *P_EPT_INFO; 194 | 195 | 196 | -------------------------------------------------------------------------------- /VT_demo/Include/Common.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | #include "Native.h" 3 | #include 4 | 5 | typedef struct _R3EPT_HOOK_2{ 6 | ULONG64 Code_PAGE_VA; 7 | ULONG64 Code_PAGE_PFN; 8 | ULONG64 Data_PAGE_VA; 9 | ULONG64 Data_PAGE_PFN; 10 | ULONG64 OriginalPtr; 11 | PEPROCESS TargetProcess; 12 | ULONG64 TargetCr3; 13 | BOOLEAN IsHook; 14 | PMDL mdl; 15 | ULONG RefCount; 16 | LIST_ENTRY PageList; 17 | }R3EPT_HOOK_2, *PR3EPT_HOOK_2; 18 | 19 | #define DPRINT(format, ...) DbgPrintEx(DPFLTR_IHVDRIVER_ID, DPFLTR_ERROR_LEVEL, format, __VA_ARGS__) 20 | //#define DPRINT(format, ...) 21 | #define HB_POOL_TAG '0mVZ' 22 | 23 | #define NBP_MAGIC ((ULONG32)'!LTI') 24 | #define HYPERCALL_UNLOAD 0x1 25 | #define HYPERCALL_HOOK_LSTAR 0x2 26 | #define HYPERCALL_UNHOOK_LSTAR 0x3 27 | #define HYPERCALL_HOOK_PAGE 0x4 28 | #define HYPERCALL_UNHOOK_PAGE 0x5 29 | 30 | #define MAX_CPU_PER_GROUP 64 31 | 32 | #define BUG_CHECK_UNSPECIFIED 0 33 | #define BUG_CHECK_INVALID_VM 1 34 | #define BUG_CHECK_TRIPLE_FAULT 2 35 | #define BUG_CHECK_EPT_MISCONFIG 3 36 | #define BUG_CHECK_EPT_VIOLATION 4 37 | #define BUG_CHECK_EPT_NO_PAGES 5 38 | 39 | #define CPU_IDX (KeGetCurrentProcessorNumberEx( NULL )) 40 | #define PFN(addr) (ULONG64)((addr) >> PAGE_SHIFT) 41 | #define SSDTIndex(ptr) *(PULONG)((ULONG_PTR)ptr + 0x15) 42 | 43 | #define PAGES_PER_ENTRY ((PAGE_SIZE - sizeof( LIST_ENTRY ) - sizeof( ULONG64 )) / sizeof( union _EPT_MMPTE* )) 44 | #define EPT_PREALLOC_PAGES 512 45 | 46 | /// 47 | /// CPU vendor 48 | /// 49 | typedef enum _CPU_VENDOR 50 | { 51 | CPU_Other = 0, 52 | CPU_Intel, 53 | CPU_AMD 54 | } CPU_VENDOR; 55 | 56 | /// 57 | /// Virtual CPU state 58 | /// 59 | typedef enum _VCPU_VMX_STATE 60 | { 61 | VMX_STATE_OFF = 0, // No virtualization 62 | VMX_STATE_TRANSITION = 1, // Virtualized, context not yet restored 63 | VMX_STATE_ON = 2 // Virtualized, running guest 64 | } VCPU_VMX_STATE; 65 | 66 | #pragma warning(disable: 4214) 67 | 68 | /// 69 | /// VMXON and VMCS regions 70 | /// 71 | typedef struct _VMX_VMCS 72 | { 73 | ULONG RevisionId; 74 | ULONG AbortIndicator; 75 | UCHAR Data[PAGE_SIZE - 2 * sizeof( ULONG )]; 76 | } VMX_VMCS, *PVMX_VMCS; 77 | 78 | /// 79 | /// EPT pages storage 80 | /// 81 | typedef struct _EPT_PAGES_ENTRY 82 | { 83 | LIST_ENTRY link; 84 | ULONG64 count; 85 | union _EPT_MMPTE* pages[PAGES_PER_ENTRY]; 86 | } EPT_PAGES_ENTRY, *PEPT_PAGES_ENTRY; 87 | 88 | typedef struct _VMX_FEATURES 89 | { 90 | ULONG64 SecondaryControls : 1; // Secondary controls are enabled 91 | ULONG64 TrueMSRs : 1; // True VMX MSR values are supported 92 | ULONG64 EPT : 1; // EPT supported by CPU 93 | ULONG64 VPID : 1; // VPID supported by CPU 94 | ULONG64 ExecOnlyEPT : 1; // EPT translation with execute-only access is supported 95 | ULONG64 InvSingleAddress : 1; // IVVPID for single address 96 | ULONG64 VMFUNC : 1; // VMFUNC is supported 97 | } VMX_FEATURES, *PVMX_FEATURES; 98 | 99 | /// 100 | /// VCPU EPT info 101 | /// 102 | typedef struct _EPT_DATA 103 | { 104 | union _EPT_MMPTE* PML4Ptr; // EPT PML4 pointer 105 | LIST_ENTRY PageList; // EPT_PAGES_ENTRY list 106 | union _EPT_MMPTE* Pages[EPT_PREALLOC_PAGES]; // Array of preallocated pages 107 | ULONG Preallocations; // Number of used preallocated pages 108 | ULONG TotalPages; // Total number of EPT pages 109 | } EPT_DATA, *PEPT_DATA; 110 | 111 | /// 112 | /// Page hook trace state 113 | /// 114 | typedef struct _PAGE_HOOK_STATE 115 | { 116 | struct _PAGE_HOOK_ENTRY*krPentry; 117 | struct _R3EPT_HOOK_2* pEntry; 118 | ULONG64 Rip; 119 | } PAGE_HOOK_STATE, *PPAGE_HOOK_STATE; 120 | 121 | /// 122 | /// Virtual CPU stuff 123 | /// 124 | typedef struct _VCPU 125 | { 126 | KPROCESSOR_STATE HostState; // Host CPU state before virtualization 127 | volatile VCPU_VMX_STATE VmxState; // CPU virtualization state 128 | ULONG64 SystemDirectoryTableBase; // Kernel CR3 129 | LARGE_INTEGER MsrData[18]; // VMX-specific MSR data 130 | PVMX_VMCS VMXON; // VMXON region 131 | PVMX_VMCS VMCS; // VMCS region 132 | PVOID VMMStack; // Host VMM stack memory 133 | EPT_DATA EPT; // EPT mapping data 134 | ULONG64 OriginalLSTAR; // LSTAR MSR value 135 | ULONG64 TscOffset; // TSC VMM offset value 136 | PAGE_HOOK_STATE HookDispatch; // Page hooking trace state 137 | } VCPU, *PVCPU; 138 | 139 | /// 140 | /// Global data 141 | /// 142 | typedef struct _GLOBAL_DATA 143 | { 144 | CPU_VENDOR CPUVendor; // Intel or AMD 145 | VMX_FEATURES Features; // VMX CPU features 146 | PPHYSICAL_MEMORY_DESCRIPTOR Memory; // Used PFN regions 147 | PUCHAR MSRBitmap; // MSR vmexit bitmap 148 | LONG vcpus; // Number of virtualized CPUs 149 | VCPU cpu_data[ANYSIZE_ARRAY]; // Per-CPU data 150 | } GLOBAL_DATA, *PGLOBAL_DATA; 151 | 152 | extern PGLOBAL_DATA g_Data; 153 | #pragma warning(default: 4214) 154 | -------------------------------------------------------------------------------- /VT_demo/syscalhook.c: -------------------------------------------------------------------------------- 1 | #include "ntddk.h" 2 | #include "amd64.h" 3 | 4 | 5 | 6 | typedef ULONG64(__fastcall *NTUSERQUERYWINDOW) 7 | ( 8 | IN HANDLE WindowHandle, 9 | IN ULONG64 TypeInformation 10 | ); 11 | typedef struct _LARGE_STRING 12 | { 13 | ULONG Length; 14 | ULONG MaximumLength : 31; 15 | ULONG bAnsi : 1; 16 | PVOID Buffer; 17 | } LARGE_STRING, *PLARGE_STRING; 18 | 19 | NTSTATUS __fastcall proxyNtCreateDebugObject( 20 | OUT PHANDLE DebugObjectHandle, 21 | IN ACCESS_MASK DesiredAccess, 22 | IN POBJECT_ATTRIBUTES ObjectAttributes, 23 | IN ULONG Flags 24 | ); 25 | NTSTATUS 26 | NTAPI 27 | proxyNtDebugContinue(IN HANDLE DebugHandle, 28 | IN PCLIENT_ID AppClientId, 29 | IN NTSTATUS ContinueStatus); 30 | NTSTATUS 31 | __fastcall 32 | proxyNtWaitForDebugEvent(IN HANDLE DebugHandle, 33 | IN BOOLEAN Alertable, 34 | IN PLARGE_INTEGER Timeout OPTIONAL, 35 | OUT ULONG64 StateChange); 36 | NTSTATUS 37 | __fastcall 38 | proxyNtDebugActiveProcess(IN HANDLE ProcessHandle, 39 | IN HANDLE DebugHandle); 40 | NTSTATUS 41 | NTAPI 42 | NtRemoveProcessDebug(IN HANDLE ProcessHandle, 43 | IN HANDLE DebugHandle); 44 | NTSTATUS __fastcall myNtQueryInformationThread(IN HANDLE ThreadHandle, 45 | IN THREADINFOCLASS ThreadInformationClass, 46 | OUT PVOID ThreadInformation, 47 | IN ULONG ThreadInformationLength, 48 | OUT PULONG ReturnLength OPTIONAL 49 | ); 50 | signed __int64 __fastcall MyNtWriteVirtualMemory(PHANDLE ProcessHandle, __int64 a2, unsigned __int64 AccessMode, __int64 a4, unsigned __int64 a5); 51 | ULONG __fastcall MyNtOpenProcess( 52 | __out PHANDLE ProcessHandle, 53 | __in ACCESS_MASK AccessMask, 54 | __in PVOID ObjectAttributes, 55 | __in PCLIENT_ID ClientId); 56 | signed __int64 __fastcall MyNtReadVirtualMemory(PHANDLE ProcessHandle, unsigned __int64 AccessMode, __int64 a3, __int64 a4, unsigned __int64 a5); 57 | 58 | NTSTATUS myNtSetInformationThread(HANDLE threadHandle, THREADINFOCLASS threadInformationClass, PVOID threadInformation, ULONG threadInformationLength); 59 | typedef NTSTATUS(__fastcall*CALLFUNC)(); 60 | ULONG64 NtSyscallHandler; 61 | ULONG64 GuestSyscallHandler; 62 | ULONG64 NtSyscallHandler32; 63 | ULONG64 NtKernelsyscallBase; 64 | ULONG64 NtKernelSSDT; 65 | ULONG64 KeGdiFlushUserBatch; 66 | ULONG64 KiSaveDebugRegisterState; 67 | ULONG64 KiUmsCallEntry; 68 | ULONG64 KiSystemServiceRepeat; 69 | ULONG64 MmUserProbeAddress_Address; 70 | ULONG64 KiSystemServiceCopyEnd; 71 | CHAR SyscallHookEnabled[4096]; 72 | CHAR SyscallParamTable[4096]; 73 | PVOID SyscallPointerTable[4096]; 74 | ULONG64 KeServiceDescriptorTable; 75 | ULONG64 KeServiceDescriptorTableShadow; 76 | ULONG64 KiSystemServiceExit; 77 | VOID SyscallEntryPoint(); 78 | extern ULONG KiSystemServiceRepeat_Emulate(); 79 | 80 | 81 | 82 | 83 | 84 | 85 | NTSTATUS AddServiceCallHook(ULONG Index, UCHAR ParameterCount, PVOID Function) 86 | { 87 | if (Index >= ARRAYSIZE(SyscallHookEnabled)) 88 | return STATUS_INVALID_PARAMETER_1; 89 | 90 | if (ParameterCount > 15) 91 | return STATUS_INVALID_PARAMETER_2; 92 | 93 | // 94 | // Ensure this function isn't interrupted 95 | // 96 | KIRQL irql = KeGetCurrentIrql(); 97 | 98 | if (irql < DISPATCH_LEVEL) 99 | irql = KeRaiseIrqlToDpcLevel(); 100 | 101 | // 102 | // If the syscall hook is enabled, disable it immediately 103 | // 104 | InterlockedExchange8(&SyscallHookEnabled[Index], FALSE); 105 | 106 | SyscallParamTable[Index] = ParameterCount; 107 | SyscallPointerTable[Index] = Function; 108 | 109 | // 110 | // If the function is valid, re-enable it 111 | // 112 | if (Function) 113 | InterlockedExchange8(&SyscallHookEnabled[Index], TRUE); 114 | 115 | // 116 | // Reset IRQL 117 | // 118 | 119 | if (KeGetCurrentIrql() > irql) 120 | KeLowerIrql(irql); 121 | return STATUS_SUCCESS; 122 | } 123 | NTSTATUS RemoveServiceCallHook(ULONG Index) 124 | { 125 | return AddServiceCallHook(Index, 0, NULL); 126 | } 127 | VOID EnbaleHookSysCALL(){ 128 | __writemsr(MSR_LSTAR, GuestSyscallHandler); 129 | 130 | 131 | } 132 | VOID DisableHookSysCALL(){ 133 | 134 | __writemsr(MSR_LSTAR, NtSyscallHandler); 135 | } 136 | 137 | VOID HookMsr(CALLFUNC func) 138 | { 139 | NTSTATUS status; 140 | KMUTEX mutex; 141 | KeInitializeMutex(&mutex, 0); 142 | KeWaitForSingleObject(&mutex, Executive, KernelMode, FALSE, NULL); 143 | 144 | for (LONG i = 0; i < KeQueryActiveProcessorCount(NULL); i++) 145 | { 146 | KAFFINITY oldAffinity = KeSetSystemAffinityThreadEx((KAFFINITY)(1 << i)); 147 | KIRQL oldIrql = KeRaiseIrqlToDpcLevel(); 148 | func(); 149 | KeLowerIrql(oldIrql); 150 | KeRevertToUserAffinityThreadEx(oldAffinity); 151 | } 152 | KeReleaseMutex(&mutex, FALSE); 153 | } 154 | VOID UnLoadSysHook(){ 155 | HookMsr(&DisableHookSysCALL);//Disable hook 156 | } 157 | VOID initdata(){ 158 | 159 | 160 | NtKernelsyscallBase = (ULONG64)__readmsr(MSR_LSTAR);//kisystemcall64 entry point 161 | 162 | NtSyscallHandler = (ULONG64)__readmsr(MSR_LSTAR); 163 | 164 | NtSyscallHandler32 = (ULONG64)__readmsr(MSR_CSTAR); 165 | 166 | GuestSyscallHandler = (ULONG64)&SyscallEntryPoint; 167 | 168 | // proxyNtQueryWindow = ssdt_GetSSDTShaDowFuncX64(16); 169 | 170 | } 171 | 172 | 173 | VOID inithook(){ 174 | 175 | // init data 176 | RtlSecureZeroMemory(SyscallHookEnabled, sizeof(SyscallHookEnabled)); 177 | RtlSecureZeroMemory(SyscallParamTable, sizeof(SyscallParamTable)); 178 | RtlSecureZeroMemory(SyscallPointerTable, sizeof(SyscallPointerTable)); 179 | 180 | 181 | AddServiceCallHook(144, 4, (PVOID)&proxyNtCreateDebugObject); 182 | AddServiceCallHook(395, 4, (PVOID)&proxyNtWaitForDebugEvent); 183 | AddServiceCallHook(174, 3, (PVOID)&proxyNtDebugContinue); 184 | AddServiceCallHook(173,2, (PVOID)&proxyNtDebugActiveProcess); 185 | AddServiceCallHook(314, 2, (PVOID)&NtRemoveProcessDebug); 186 | AddServiceCallHook(34, 5, (PVOID)&myNtQueryInformationThread); 187 | 188 | 189 | 190 | // AddServiceCallHook(10, 4, (PVOID)&myNtSetInformationThread); 191 | // AddServiceCallHook(55, 5, (PVOID)&MyNtWriteVirtualMemory); 192 | //AddServiceCallHook(60, 5, (PVOID)&MyNtReadVirtualMemory); 193 | // AddServiceCallHook(35, 4, (PVOID)&MyNtOpenProcess); 194 | 195 | 196 | HookMsr(&EnbaleHookSysCALL);//ENABLE hook 197 | } 198 | 199 | 200 | 201 | -------------------------------------------------------------------------------- /VT_demo/VMH/vmcs.h: -------------------------------------------------------------------------------- 1 | /* 2 | * shamelessly stolen from XEN-3.1 3 | */ 4 | 5 | #pragma once 6 | 7 | #define CPU_BASED_VIRTUAL_INTR_PENDING 0x00000004 8 | #define CPU_BASED_USE_TSC_OFFSETING 0x00000008 9 | #define CPU_BASED_HLT_EXITING 0x00000080 10 | #define CPU_BASED_INVDPG_EXITING 0x00000200 11 | #define CPU_BASED_MWAIT_EXITING 0x00000400 12 | #define CPU_BASED_RDPMC_EXITING 0x00000800 13 | #define CPU_BASED_RDTSC_EXITING 0x00001000 14 | #define CPU_BASED_CR8_LOAD_EXITING 0x00080000 15 | #define CPU_BASED_CR8_STORE_EXITING 0x00100000 16 | #define CPU_BASED_TPR_SHADOW 0x00200000 17 | #define CPU_BASED_MOV_DR_EXITING 0x00800000 18 | #define CPU_BASED_UNCOND_IO_EXITING 0x01000000 19 | #define CPU_BASED_ACTIVATE_IO_BITMAP 0x02000000 20 | #define CPU_BASED_ACTIVATE_MSR_BITMAP 0x10000000 21 | #define CPU_BASED_MONITOR_EXITING 0x20000000 22 | #define CPU_BASED_PAUSE_EXITING 0x40000000 23 | 24 | #define PIN_BASED_EXT_INTR_MASK 0x00000001 25 | #define PIN_BASED_NMI_EXITING 0x00000008 26 | 27 | #define VM_EXIT_IA32E_MODE 0x00000200 28 | #define VM_EXIT_ACK_INTR_ON_EXIT 0x00008000 29 | 30 | #define VM_ENTRY_IA32E_MODE 0x00000200 31 | #define VM_ENTRY_SMM 0x00000400 32 | #define VM_ENTRY_DEACT_DUAL_MONITOR 0x00000800 33 | 34 | /* VMCS Encordings */ 35 | enum 36 | { 37 | HOST_IA32_EFER = 0x00002c02, 38 | VIRTUAL_PROCESSOR_ID = 0x00000000, 39 | EPT_POINTER = 0x0000201a, 40 | GUEST_ES_SELECTOR = 0x00000800, 41 | GUEST_CS_SELECTOR = 0x00000802, 42 | GUEST_SS_SELECTOR = 0x00000804, 43 | GUEST_DS_SELECTOR = 0x00000806, 44 | GUEST_FS_SELECTOR = 0x00000808, 45 | GUEST_GS_SELECTOR = 0x0000080a, 46 | GUEST_LDTR_SELECTOR = 0x0000080c, 47 | GUEST_TR_SELECTOR = 0x0000080e, 48 | HOST_ES_SELECTOR = 0x00000c00, 49 | HOST_CS_SELECTOR = 0x00000c02, 50 | HOST_SS_SELECTOR = 0x00000c04, 51 | HOST_DS_SELECTOR = 0x00000c06, 52 | HOST_FS_SELECTOR = 0x00000c08, 53 | HOST_GS_SELECTOR = 0x00000c0a, 54 | HOST_TR_SELECTOR = 0x00000c0c, 55 | IO_BITMAP_A = 0x00002000, 56 | IO_BITMAP_A_HIGH = 0x00002001, 57 | IO_BITMAP_B = 0x00002002, 58 | IO_BITMAP_B_HIGH = 0x00002003, 59 | MSR_BITMAP = 0x00002004, 60 | X86_CR0_PG= 0x80000000 , 61 | MSR_BITMAP_HIGH = 0x00002005, 62 | VM_EXIT_MSR_STORE_ADDR = 0x00002006, 63 | VM_EXIT_MSR_STORE_ADDR_HIGH = 0x00002007, 64 | VM_EXIT_MSR_LOAD_ADDR = 0x00002008, 65 | VM_EXIT_MSR_LOAD_ADDR_HIGH = 0x00002009, 66 | VM_ENTRY_MSR_LOAD_ADDR = 0x0000200a, 67 | VM_ENTRY_MSR_LOAD_ADDR_HIGH = 0x0000200b, 68 | TSC_OFFSET = 0x00002010, 69 | TSC_OFFSET_HIGH = 0x00002011, 70 | VIRTUAL_APIC_PAGE_ADDR = 0x00002012, 71 | VIRTUAL_APIC_PAGE_ADDR_HIGH = 0x00002013, 72 | VMCS_LINK_POINTER = 0x00002800, 73 | VMCS_LINK_POINTER_HIGH = 0x00002801, 74 | GUEST_IA32_DEBUGCTL = 0x00002802, 75 | GUEST_IA32_DEBUGCTL_HIGH = 0x00002803, 76 | PIN_BASED_VM_EXEC_CONTROL = 0x00004000, 77 | CPU_BASED_VM_EXEC_CONTROL = 0x00004002, 78 | EXCEPTION_BITMAP = 0x00004004, 79 | PAGE_FAULT_ERROR_CODE_MASK = 0x00004006, 80 | PAGE_FAULT_ERROR_CODE_MATCH = 0x00004008, 81 | CR3_TARGET_COUNT = 0x0000400a, 82 | VM_EXIT_CONTROLS = 0x0000400c, 83 | VM_EXIT_MSR_STORE_COUNT = 0x0000400e, 84 | VM_EXIT_MSR_LOAD_COUNT = 0x00004010, 85 | VM_ENTRY_CONTROLS = 0x00004012, 86 | VM_ENTRY_MSR_LOAD_COUNT = 0x00004014, 87 | VM_ENTRY_INTR_INFO_FIELD = 0x00004016, 88 | VM_ENTRY_EXCEPTION_ERROR_CODE = 0x00004018, 89 | VM_ENTRY_INSTRUCTION_LEN = 0x0000401a, 90 | TPR_THRESHOLD = 0x0000401c, 91 | SECONDARY_VM_EXEC_CONTROL = 0x0000401e, 92 | VM_INSTRUCTION_ERROR = 0x00004400, 93 | VM_EXIT_REASON = 0x00004402, 94 | VM_EXIT_INTR_INFO = 0x00004404, 95 | VM_EXIT_INTR_ERROR_CODE = 0x00004406, 96 | IDT_VECTORING_INFO_FIELD = 0x00004408, 97 | IDT_VECTORING_ERROR_CODE = 0x0000440a, 98 | VM_EXIT_INSTRUCTION_LEN = 0x0000440c, 99 | VMX_INSTRUCTION_INFO = 0x0000440e, 100 | GUEST_ES_LIMIT = 0x00004800, 101 | GUEST_CS_LIMIT = 0x00004802, 102 | GUEST_SS_LIMIT = 0x00004804, 103 | GUEST_DS_LIMIT = 0x00004806, 104 | GUEST_FS_LIMIT = 0x00004808, 105 | GUEST_GS_LIMIT = 0x0000480a, 106 | GUEST_LDTR_LIMIT = 0x0000480c, 107 | GUEST_TR_LIMIT = 0x0000480e, 108 | GUEST_GDTR_LIMIT = 0x00004810, 109 | GUEST_IDTR_LIMIT = 0x00004812, 110 | GUEST_ES_AR_BYTES = 0x00004814, 111 | GUEST_CS_AR_BYTES = 0x00004816, 112 | GUEST_SS_AR_BYTES = 0x00004818, 113 | GUEST_DS_AR_BYTES = 0x0000481a, 114 | GUEST_FS_AR_BYTES = 0x0000481c, 115 | GUEST_GS_AR_BYTES = 0x0000481e, 116 | GUEST_LDTR_AR_BYTES = 0x00004820, 117 | GUEST_TR_AR_BYTES = 0x00004822, 118 | GUEST_INTERRUPTIBILITY_STATE = 0x00004824, 119 | GUEST_ACTIVITY_STATE = 0x00004826, 120 | GUEST_SM_BASE = 0x00004828, 121 | GUEST_SYSENTER_CS = 0x0000482A, 122 | HOST_IA32_SYSENTER_CS = 0x00004c00, 123 | CR0_GUEST_HOST_MASK = 0x00006000, 124 | CR4_GUEST_HOST_MASK = 0x00006002, 125 | CR0_READ_SHADOW = 0x00006004, 126 | CR4_READ_SHADOW = 0x00006006, 127 | CR3_TARGET_VALUE0 = 0x00006008, 128 | CR3_TARGET_VALUE1 = 0x0000600a, 129 | CR3_TARGET_VALUE2 = 0x0000600c, 130 | CR3_TARGET_VALUE3 = 0x0000600e, 131 | EXIT_QUALIFICATION = 0x00006400, 132 | GUEST_LINEAR_ADDRESS = 0x0000640a, 133 | GUEST_CR0 = 0x00006800, 134 | GUEST_CR3 = 0x00006802, 135 | GUEST_CR4 = 0x00006804, 136 | GUEST_ES_BASE = 0x00006806, 137 | GUEST_CS_BASE = 0x00006808, 138 | GUEST_SS_BASE = 0x0000680a, 139 | GUEST_DS_BASE = 0x0000680c, 140 | GUEST_FS_BASE = 0x0000680e, 141 | GUEST_GS_BASE = 0x00006810, 142 | GUEST_LDTR_BASE = 0x00006812, 143 | GUEST_TR_BASE = 0x00006814, 144 | GUEST_GDTR_BASE = 0x00006816, 145 | GUEST_IDTR_BASE = 0x00006818, 146 | GUEST_DR7 = 0x0000681a, 147 | GUEST_RSP = 0x0000681c, 148 | GUEST_RIP = 0x0000681e, 149 | GUEST_RFLAGS = 0x00006820, 150 | GUEST_PENDING_DBG_EXCEPTIONS = 0x00006822, 151 | GUEST_SYSENTER_ESP = 0x00006824, 152 | GUEST_SYSENTER_EIP = 0x00006826, 153 | HOST_CR0 = 0x00006c00, 154 | HOST_CR3 = 0x00006c02, 155 | HOST_CR4 = 0x00006c04, 156 | HOST_FS_BASE = 0x00006c06, 157 | HOST_GS_BASE = 0x00006c08, 158 | HOST_TR_BASE = 0x00006c0a, 159 | HOST_GDTR_BASE = 0x00006c0c, 160 | HOST_IDTR_BASE = 0x00006c0e, 161 | HOST_IA32_SYSENTER_ESP = 0x00006c10, 162 | HOST_IA32_SYSENTER_EIP = 0x00006c12, 163 | HOST_RSP = 0x00006c14, 164 | HOST_RIP = 0x00006c16, 165 | }; -------------------------------------------------------------------------------- /VT_demo/Arch/Intel/EPT.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | #define VM_VPID 1 3 | #define EPT_TABLE_ORDER 9 4 | #define EPT_TABLE_ENTRIES 512 5 | 6 | /// 7 | /// EPT page access 8 | /// 9 | typedef enum _EPT_ACCESS 10 | { 11 | EPT_ACCESS_NONE = 0, 12 | EPT_ACCESS_READ = 1, 13 | EPT_ACCESS_WRITE = 2, 14 | EPT_ACCESS_EXEC = 4, 15 | EPT_ACCESS_RW = EPT_ACCESS_READ | EPT_ACCESS_WRITE, 16 | EPT_ACCESS_ALL = EPT_ACCESS_READ | EPT_ACCESS_WRITE | EPT_ACCESS_EXEC 17 | } EPT_ACCESS; 18 | 19 | 20 | /// 21 | /// ETP table level 22 | /// 23 | typedef enum _EPT_TABLE_LEVEL 24 | { 25 | EPT_LEVEL_PTE = 0, 26 | EPT_LEVEL_PDE = 1, 27 | EPT_LEVEL_PDPTE = 2, 28 | EPT_LEVEL_PML4 = 3, 29 | EPT_TOP_LEVEL = EPT_LEVEL_PML4 30 | } EPT_TABLE_LEVEL; 31 | 32 | #pragma warning(disable: 4214) 33 | #pragma pack(push, 1) 34 | /// 35 | /// PEPT 36 | /// 37 | typedef union _EPT_TABLE_POINTER 38 | { 39 | ULONG64 All; 40 | struct 41 | { 42 | ULONG64 MemoryType : 3; // EPT Paging structure memory type (0 for UC) 43 | ULONG64 PageWalkLength : 3; // Page-walk length 44 | ULONG64 reserved1 : 6; 45 | ULONG64 PhysAddr : 40; // Physical address of the EPT PML4 table 46 | ULONG64 reserved2 : 12; 47 | } Fields; 48 | } EPT_TABLE_POINTER, *PEPT_TABLE_POINTER; 49 | 50 | /// 51 | /// PML4, PDPTE, PDTE pointing to another table 52 | /// 53 | typedef union _EPT_MMPTE 54 | { 55 | ULONG64 All; 56 | struct 57 | { 58 | ULONG64 Present : 1; // If the region is present (read access) 59 | ULONG64 Write : 1; // If the region is writable 60 | ULONG64 Execute : 1; // If the region is executable 61 | ULONG64 reserved1 : 9; // Reserved 62 | ULONG64 PhysAddr : 40; // Physical address 63 | ULONG64 reserved2 : 12; // Reserved 64 | } Fields; 65 | } EPT_PML4_ENTRY, EPT_MMPTE, *PEPT_PML4_ENTRY, *PEPT_MMPTE; 66 | 67 | /// 68 | /// 2 MB PDE entry 69 | /// 70 | typedef union _EPT_PDE_LARGE_ENTRY 71 | { 72 | ULONG64 All; 73 | struct 74 | { 75 | ULONG64 Present : 1; // If the 2 MB region is present (read access) 76 | ULONG64 Write : 1; // If the 2 MB region is writable 77 | ULONG64 Execute : 1; // If the 2 MB region is executable 78 | ULONG64 MemoryType : 3; // EPT Memory type 79 | ULONG64 IgnorePat : 1; // Flag for whether to ignore PAT 80 | ULONG64 Size : 1; // Must be 1 81 | ULONG64 reserved1 : 13; // Reserved 82 | ULONG64 PhysAddr : 40; // Physical address 83 | ULONG64 reserved2 : 12; // Reserved 84 | } Fields; 85 | } EPT_PDE_LARGE_ENTRY, *PEPT_PDE_LARGE_ENTRY; 86 | 87 | /// 88 | /// PTE entry 89 | /// 90 | typedef union _EPT_PTE_ENTRY 91 | { 92 | ULONG64 All; 93 | struct 94 | { 95 | ULONG64 Read : 1; // Region is present (read access) 96 | ULONG64 Write : 1; // Region is writable 97 | ULONG64 Execute : 1; // Region is executable 98 | ULONG64 MemoryType : 3; // EPT Memory type 99 | ULONG64 IgnorePat : 1; // Flag for whether to ignore PAT 100 | ULONG64 reserved1 : 5; // Reserved 101 | ULONG64 PhysAddr : 40; // Physical address 102 | ULONG64 reserved2 : 12; // Reserved 103 | } Fields; 104 | } EPT_PTE_ENTRY, *PEPT_PTE_ENTRY; 105 | 106 | /// 107 | /// Guest physical to host physical address bits 108 | /// 109 | typedef union _GUEST_PHYSICAL 110 | { 111 | ULONG64 All; 112 | struct 113 | { 114 | ULONG64 offset : 12; // [0-11] 115 | ULONG64 pte : 9; // [12-20] 116 | ULONG64 pde : 9; // [21-29] 117 | ULONG64 pdpte : 9; // [30-38] 118 | ULONG64 pml4 : 9; // [39-47] 119 | ULONG64 reserved : 16; // Reserved 120 | } Fields; 121 | } GUEST_PHYSICAL, *PGUEST_PHYSICAL; 122 | 123 | /// 124 | /// Exit qualification for EPT violation 125 | /// 126 | typedef union _EPT_VIOLATION_DATA 127 | { 128 | ULONG64 All; 129 | struct 130 | { 131 | ULONG64 Read : 1; // Read access 132 | ULONG64 Write : 1; // Write access 133 | ULONG64 Execute : 1; // Execute access 134 | ULONG64 PTERead : 1; // PTE entry has read access 135 | ULONG64 PTEWrite : 1; // PTE entry has write access 136 | ULONG64 PTEExecute : 1; // PTE entry has execute access 137 | ULONG64 Reserved1 : 1; // 138 | ULONG64 GuestLinear : 1; // GUEST_LINEAR_ADDRESS field is valid 139 | ULONG64 FailType : 1; // 140 | ULONG64 Reserved2 : 3; // 141 | ULONG64 NMIBlock : 1; // NMI unblocking due to IRET 142 | ULONG64 Reserved3 : 51; // 143 | } Fields; 144 | } EPT_VIOLATION_DATA, *PEPT_VIOLATION_DATA; 145 | 146 | struct _EPT_DATA; 147 | #pragma pack(pop) 148 | #pragma warning(default: 4214) 149 | 150 | /// 151 | /// Enable EPT for CPU 152 | /// 153 | /// PML4 pointer to use 154 | VOID EptEnable( IN PEPT_PML4_ENTRY PML4 ); 155 | 156 | /// 157 | /// Disable EPT for CPU 158 | /// 159 | VOID EptDisable(); 160 | 161 | /// 162 | /// Create Guest to Host page mappings 163 | /// 164 | /// CPU EPT data 165 | /// Status code 166 | NTSTATUS EptBuildIdentityMap( IN struct _EPT_DATA* pEPT ); 167 | 168 | /// 169 | /// Release Guest to Host page mappings 170 | /// 171 | /// CPU EPT data 172 | /// Status code 173 | NTSTATUS EptFreeIdentityMap( IN struct _EPT_DATA* pEPT ); 174 | 175 | /// 176 | /// Update EPT entry 177 | /// 178 | /// CPU EPT data 179 | /// EPT table 180 | /// EPT table level 181 | /// Page frame number to update 182 | /// New PFN access 183 | /// New hot PFN 184 | /// Number of entries to update 185 | /// Status code 186 | NTSTATUS EptUpdateTableRecursive( 187 | IN struct _EPT_DATA* pEPTData, 188 | IN PEPT_MMPTE pTable, 189 | IN EPT_TABLE_LEVEL level, 190 | IN ULONG64 pfn, 191 | IN EPT_ACCESS access, 192 | IN ULONG64 hostPFN, 193 | IN ULONG count 194 | ); 195 | 196 | /// 197 | /// Get EPT PTE entry for guest physical address 198 | /// 199 | /// PTE PML4 pointer 200 | /// Guest physical address 201 | /// Found entry or NULL 202 | /// Status code 203 | NTSTATUS EptGetPTEForPhysical( IN PEPT_PML4_ENTRY PML4, IN PHYSICAL_ADDRESS phys, OUT PEPT_PTE_ENTRY* pEntry ); -------------------------------------------------------------------------------- /VT_demo.sln: -------------------------------------------------------------------------------- 1 | 2 | Microsoft Visual Studio Solution File, Format Version 12.00 3 | # Visual Studio 2013 4 | VisualStudioVersion = 12.0.30501.0 5 | MinimumVisualStudioVersion = 10.0.40219.1 6 | Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "VT_demo", "VT_demo\VT_demo.vcxproj", "{CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}" 7 | EndProject 8 | Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "VT_demo Package", "VT_demo Package\VT_demo Package.vcxproj", "{6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}" 9 | ProjectSection(ProjectDependencies) = postProject 10 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A} = {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A} 11 | EndProjectSection 12 | EndProject 13 | Global 14 | GlobalSection(SolutionConfigurationPlatforms) = preSolution 15 | Win7 Debug|Win32 = Win7 Debug|Win32 16 | Win7 Debug|x64 = Win7 Debug|x64 17 | Win7 Release|Win32 = Win7 Release|Win32 18 | Win7 Release|x64 = Win7 Release|x64 19 | Win8 Debug|Win32 = Win8 Debug|Win32 20 | Win8 Debug|x64 = Win8 Debug|x64 21 | Win8 Release|Win32 = Win8 Release|Win32 22 | Win8 Release|x64 = Win8 Release|x64 23 | Win8.1 Debug|Win32 = Win8.1 Debug|Win32 24 | Win8.1 Debug|x64 = Win8.1 Debug|x64 25 | Win8.1 Release|Win32 = Win8.1 Release|Win32 26 | Win8.1 Release|x64 = Win8.1 Release|x64 27 | EndGlobalSection 28 | GlobalSection(ProjectConfigurationPlatforms) = postSolution 29 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win7 Debug|Win32.ActiveCfg = Win7 Debug|Win32 30 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win7 Debug|Win32.Build.0 = Win7 Debug|Win32 31 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win7 Debug|Win32.Deploy.0 = Win7 Debug|Win32 32 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win7 Debug|x64.ActiveCfg = Win7 Debug|x64 33 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win7 Debug|x64.Build.0 = Win7 Debug|x64 34 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win7 Debug|x64.Deploy.0 = Win7 Debug|x64 35 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win7 Release|Win32.ActiveCfg = Win7 Release|Win32 36 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win7 Release|Win32.Build.0 = Win7 Release|Win32 37 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win7 Release|Win32.Deploy.0 = Win7 Release|Win32 38 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win7 Release|x64.ActiveCfg = Win7 Release|x64 39 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win7 Release|x64.Build.0 = Win7 Release|x64 40 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win7 Release|x64.Deploy.0 = Win7 Release|x64 41 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win8 Debug|Win32.ActiveCfg = Win8 Debug|Win32 42 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win8 Debug|Win32.Build.0 = Win8 Debug|Win32 43 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win8 Debug|Win32.Deploy.0 = Win8 Debug|Win32 44 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win8 Debug|x64.ActiveCfg = Win8 Debug|x64 45 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win8 Debug|x64.Build.0 = Win8 Debug|x64 46 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win8 Debug|x64.Deploy.0 = Win8 Debug|x64 47 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win8 Release|Win32.ActiveCfg = Win8 Release|Win32 48 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win8 Release|Win32.Build.0 = Win8 Release|Win32 49 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win8 Release|Win32.Deploy.0 = Win8 Release|Win32 50 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win8 Release|x64.ActiveCfg = Win8 Release|x64 51 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win8 Release|x64.Build.0 = Win8 Release|x64 52 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win8 Release|x64.Deploy.0 = Win8 Release|x64 53 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win8.1 Debug|Win32.ActiveCfg = Win8.1 Debug|Win32 54 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win8.1 Debug|Win32.Build.0 = Win8.1 Debug|Win32 55 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win8.1 Debug|Win32.Deploy.0 = Win8.1 Debug|Win32 56 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win8.1 Debug|x64.ActiveCfg = Win8.1 Debug|x64 57 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win8.1 Debug|x64.Build.0 = Win8.1 Debug|x64 58 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win8.1 Debug|x64.Deploy.0 = Win8.1 Debug|x64 59 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win8.1 Release|Win32.ActiveCfg = Win8.1 Release|Win32 60 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win8.1 Release|Win32.Build.0 = Win8.1 Release|Win32 61 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win8.1 Release|Win32.Deploy.0 = Win8.1 Release|Win32 62 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win8.1 Release|x64.ActiveCfg = Win8.1 Release|x64 63 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win8.1 Release|x64.Build.0 = Win8.1 Release|x64 64 | {CE63B980-91E8-4B5C-9B04-F862FBDDCB6A}.Win8.1 Release|x64.Deploy.0 = Win8.1 Release|x64 65 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win7 Debug|Win32.ActiveCfg = Win7 Debug|Win32 66 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win7 Debug|Win32.Build.0 = Win7 Debug|Win32 67 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win7 Debug|Win32.Deploy.0 = Win7 Debug|Win32 68 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win7 Debug|x64.ActiveCfg = Win7 Debug|x64 69 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win7 Debug|x64.Build.0 = Win7 Debug|x64 70 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win7 Debug|x64.Deploy.0 = Win7 Debug|x64 71 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win7 Release|Win32.ActiveCfg = Win7 Release|Win32 72 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win7 Release|Win32.Build.0 = Win7 Release|Win32 73 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win7 Release|Win32.Deploy.0 = Win7 Release|Win32 74 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win7 Release|x64.ActiveCfg = Win7 Release|x64 75 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win7 Release|x64.Build.0 = Win7 Release|x64 76 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win7 Release|x64.Deploy.0 = Win7 Release|x64 77 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win8 Debug|Win32.ActiveCfg = Win8 Debug|Win32 78 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win8 Debug|Win32.Build.0 = Win8 Debug|Win32 79 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win8 Debug|Win32.Deploy.0 = Win8 Debug|Win32 80 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win8 Debug|x64.ActiveCfg = Win8 Debug|x64 81 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win8 Debug|x64.Build.0 = Win8 Debug|x64 82 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win8 Debug|x64.Deploy.0 = Win8 Debug|x64 83 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win8 Release|Win32.ActiveCfg = Win8 Release|Win32 84 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win8 Release|Win32.Build.0 = Win8 Release|Win32 85 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win8 Release|Win32.Deploy.0 = Win8 Release|Win32 86 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win8 Release|x64.ActiveCfg = Win8 Release|x64 87 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win8 Release|x64.Build.0 = Win8 Release|x64 88 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win8 Release|x64.Deploy.0 = Win8 Release|x64 89 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win8.1 Debug|Win32.ActiveCfg = Win8.1 Debug|Win32 90 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win8.1 Debug|Win32.Build.0 = Win8.1 Debug|Win32 91 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win8.1 Debug|Win32.Deploy.0 = Win8.1 Debug|Win32 92 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win8.1 Debug|x64.ActiveCfg = Win8.1 Debug|x64 93 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win8.1 Debug|x64.Build.0 = Win8.1 Debug|x64 94 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win8.1 Debug|x64.Deploy.0 = Win8.1 Debug|x64 95 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win8.1 Release|Win32.ActiveCfg = Win8.1 Release|Win32 96 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win8.1 Release|Win32.Build.0 = Win8.1 Release|Win32 97 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win8.1 Release|Win32.Deploy.0 = Win8.1 Release|Win32 98 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win8.1 Release|x64.ActiveCfg = Win8.1 Release|x64 99 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win8.1 Release|x64.Build.0 = Win8.1 Release|x64 100 | {6E3C962A-F275-4FAC-9C3E-D0D1324DA0E1}.Win8.1 Release|x64.Deploy.0 = Win8.1 Release|x64 101 | EndGlobalSection 102 | GlobalSection(SolutionProperties) = preSolution 103 | HideSolutionNode = FALSE 104 | EndGlobalSection 105 | EndGlobal 106 | -------------------------------------------------------------------------------- /VT_demo/Arch/Intel/VMCS.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | #include 3 | #include 4 | 5 | // VMCS data fields 6 | typedef enum _VMCS_ENCODING 7 | { 8 | VIRTUAL_PROCESSOR_ID = 0x00000000, // 16-Bit Control Field 9 | POSTED_INTERRUPT_NOTIFICATION = 0x00000002, 10 | EPTP_INDEX = 0x00000004, 11 | GUEST_ES_SELECTOR = 0x00000800, // 16-Bit Guest-State Fields 12 | GUEST_CS_SELECTOR = 0x00000802, 13 | GUEST_SS_SELECTOR = 0x00000804, 14 | GUEST_DS_SELECTOR = 0x00000806, 15 | GUEST_FS_SELECTOR = 0x00000808, 16 | GUEST_GS_SELECTOR = 0x0000080a, 17 | GUEST_LDTR_SELECTOR = 0x0000080c, 18 | GUEST_TR_SELECTOR = 0x0000080e, 19 | GUEST_INTERRUPT_STATUS = 0x00000810, 20 | HOST_ES_SELECTOR = 0x00000c00, // 16-Bit Host-State Fields 21 | HOST_CS_SELECTOR = 0x00000c02, 22 | HOST_SS_SELECTOR = 0x00000c04, 23 | HOST_DS_SELECTOR = 0x00000c06, 24 | HOST_FS_SELECTOR = 0x00000c08, 25 | HOST_GS_SELECTOR = 0x00000c0a, 26 | HOST_TR_SELECTOR = 0x00000c0c, 27 | IO_BITMAP_A = 0x00002000, // 64-Bit Control Fields 28 | IO_BITMAP_A_HIGH = 0x00002001, 29 | IO_BITMAP_B = 0x00002002, 30 | IO_BITMAP_B_HIGH = 0x00002003, 31 | MSR_BITMAP = 0x00002004, 32 | MSR_BITMAP_HIGH = 0x00002005, 33 | VM_EXIT_MSR_STORE_ADDR = 0x00002006, 34 | VM_EXIT_MSR_STORE_ADDR_HIGH = 0x00002007, 35 | VM_EXIT_MSR_LOAD_ADDR = 0x00002008, 36 | VM_EXIT_MSR_LOAD_ADDR_HIGH = 0x00002009, 37 | VM_ENTRY_MSR_LOAD_ADDR = 0x0000200a, 38 | VM_ENTRY_MSR_LOAD_ADDR_HIGH = 0x0000200b, 39 | EXECUTIVE_VMCS_POINTER = 0x0000200c, 40 | EXECUTIVE_VMCS_POINTER_HIGH = 0x0000200d, 41 | TSC_OFFSET = 0x00002010, 42 | TSC_OFFSET_HIGH = 0x00002011, 43 | VIRTUAL_APIC_PAGE_ADDR = 0x00002012, 44 | VIRTUAL_APIC_PAGE_ADDR_HIGH = 0x00002013, 45 | APIC_ACCESS_ADDR = 0x00002014, 46 | APIC_ACCESS_ADDR_HIGH = 0x00002015, 47 | EPT_POINTER = 0x0000201a, 48 | EPT_POINTER_HIGH = 0x0000201b, 49 | EOI_EXIT_BITMAP_0 = 0x0000201c, 50 | EOI_EXIT_BITMAP_0_HIGH = 0x0000201d, 51 | EOI_EXIT_BITMAP_1 = 0x0000201e, 52 | EOI_EXIT_BITMAP_1_HIGH = 0x0000201f, 53 | EOI_EXIT_BITMAP_2 = 0x00002020, 54 | EOI_EXIT_BITMAP_2_HIGH = 0x00002021, 55 | EOI_EXIT_BITMAP_3 = 0x00002022, 56 | EOI_EXIT_BITMAP_3_HIGH = 0x00002023, 57 | EPTP_LIST_ADDRESS = 0x00002024, 58 | EPTP_LIST_ADDRESS_HIGH = 0x00002025, 59 | VMREAD_BITMAP_ADDRESS = 0x00002026, 60 | VMREAD_BITMAP_ADDRESS_HIGH = 0x00002027, 61 | VMWRITE_BITMAP_ADDRESS = 0x00002028, 62 | VMWRITE_BITMAP_ADDRESS_HIGH = 0x00002029, 63 | VIRTUALIZATION_EXCEPTION_INFO_ADDDRESS = 0x0000202a, 64 | VIRTUALIZATION_EXCEPTION_INFO_ADDDRESS_HIGH = 0x0000202b, 65 | XSS_EXITING_BITMAP = 0x0000202c, 66 | XSS_EXITING_BITMAP_HIGH = 0x0000202d, 67 | GUEST_PHYSICAL_ADDRESS = 0x00002400, // 64-Bit Read-Only Data Field 68 | GUEST_PHYSICAL_ADDRESS_HIGH = 0x00002401, 69 | VMCS_LINK_POINTER = 0x00002800, // 64-Bit Guest-State Fields 70 | VMCS_LINK_POINTER_HIGH = 0x00002801, 71 | GUEST_IA32_DEBUGCTL = 0x00002802, 72 | GUEST_IA32_DEBUGCTL_HIGH = 0x00002803, 73 | GUEST_IA32_PAT = 0x00002804, 74 | GUEST_IA32_PAT_HIGH = 0x00002805, 75 | GUEST_IA32_EFER = 0x00002806, 76 | GUEST_IA32_EFER_HIGH = 0x00002807, 77 | GUEST_IA32_PERF_GLOBAL_CTRL = 0x00002808, 78 | GUEST_IA32_PERF_GLOBAL_CTRL_HIGH = 0x00002809, 79 | GUEST_PDPTR0 = 0x0000280a, 80 | GUEST_PDPTR0_HIGH = 0x0000280b, 81 | GUEST_PDPTR1 = 0x0000280c, 82 | GUEST_PDPTR1_HIGH = 0x0000280d, 83 | GUEST_PDPTR2 = 0x0000280e, 84 | GUEST_PDPTR2_HIGH = 0x0000280f, 85 | GUEST_PDPTR3 = 0x00002810, 86 | GUEST_PDPTR3_HIGH = 0x00002811, 87 | HOST_IA32_PAT = 0x00002c00, // 64-Bit Host-State Fields 88 | HOST_IA32_PAT_HIGH = 0x00002c01, 89 | HOST_IA32_EFER = 0x00002c02, 90 | HOST_IA32_EFER_HIGH = 0x00002c03, 91 | HOST_IA32_PERF_GLOBAL_CTRL = 0x00002c04, 92 | HOST_IA32_PERF_GLOBAL_CTRL_HIGH = 0x00002c05, 93 | PIN_BASED_VM_EXEC_CONTROL = 0x00004000, // 32-Bit Control Fields 94 | CPU_BASED_VM_EXEC_CONTROL = 0x00004002, 95 | EXCEPTION_BITMAP = 0x00004004, 96 | PAGE_FAULT_ERROR_CODE_MASK = 0x00004006, 97 | PAGE_FAULT_ERROR_CODE_MATCH = 0x00004008, 98 | CR3_TARGET_COUNT = 0x0000400a, 99 | VM_EXIT_CONTROLS = 0x0000400c, 100 | VM_EXIT_MSR_STORE_COUNT = 0x0000400e, 101 | VM_EXIT_MSR_LOAD_COUNT = 0x00004010, 102 | VM_ENTRY_CONTROLS = 0x00004012, 103 | VM_ENTRY_MSR_LOAD_COUNT = 0x00004014, 104 | VM_ENTRY_INTR_INFO_FIELD = 0x00004016, 105 | VM_ENTRY_EXCEPTION_ERROR_CODE = 0x00004018, 106 | VM_ENTRY_INSTRUCTION_LEN = 0x0000401a, 107 | TPR_THRESHOLD = 0x0000401c, 108 | SECONDARY_VM_EXEC_CONTROL = 0x0000401e, 109 | PLE_GAP = 0x00004020, 110 | PLE_WINDOW = 0x00004022, 111 | VM_INSTRUCTION_ERROR = 0x00004400, // 32-Bit Read-Only Data Fields 112 | VM_EXIT_REASON = 0x00004402, 113 | VM_EXIT_INTR_INFO = 0x00004404, 114 | VM_EXIT_INTR_ERROR_CODE = 0x00004406, 115 | IDT_VECTORING_INFO_FIELD = 0x00004408, 116 | IDT_VECTORING_ERROR_CODE = 0x0000440a, 117 | VM_EXIT_INSTRUCTION_LEN = 0x0000440c, 118 | VMX_INSTRUCTION_INFO = 0x0000440e, 119 | GUEST_ES_LIMIT = 0x00004800, // 32-Bit Guest-State Fields 120 | GUEST_CS_LIMIT = 0x00004802, 121 | GUEST_SS_LIMIT = 0x00004804, 122 | GUEST_DS_LIMIT = 0x00004806, 123 | GUEST_FS_LIMIT = 0x00004808, 124 | GUEST_GS_LIMIT = 0x0000480a, 125 | GUEST_LDTR_LIMIT = 0x0000480c, 126 | GUEST_TR_LIMIT = 0x0000480e, 127 | GUEST_GDTR_LIMIT = 0x00004810, 128 | GUEST_IDTR_LIMIT = 0x00004812, 129 | GUEST_ES_AR_BYTES = 0x00004814, 130 | GUEST_CS_AR_BYTES = 0x00004816, 131 | GUEST_SS_AR_BYTES = 0x00004818, 132 | GUEST_DS_AR_BYTES = 0x0000481a, 133 | GUEST_FS_AR_BYTES = 0x0000481c, 134 | GUEST_GS_AR_BYTES = 0x0000481e, 135 | GUEST_LDTR_AR_BYTES = 0x00004820, 136 | GUEST_TR_AR_BYTES = 0x00004822, 137 | GUEST_INTERRUPTIBILITY_INFO = 0x00004824, 138 | GUEST_ACTIVITY_STATE = 0x00004826, 139 | GUEST_SMBASE = 0x00004828, 140 | GUEST_SYSENTER_CS = 0x0000482a, 141 | VMX_PREEMPTION_TIMER_VALUE = 0x0000482e, 142 | HOST_IA32_SYSENTER_CS = 0x00004c00, // 32-Bit Host-State Field 143 | CR0_GUEST_HOST_MASK = 0x00006000, // Natural-Width Control Fields 144 | CR4_GUEST_HOST_MASK = 0x00006002, 145 | CR0_READ_SHADOW = 0x00006004, 146 | CR4_READ_SHADOW = 0x00006006, 147 | CR3_TARGET_VALUE0 = 0x00006008, 148 | CR3_TARGET_VALUE1 = 0x0000600a, 149 | CR3_TARGET_VALUE2 = 0x0000600c, 150 | CR3_TARGET_VALUE3 = 0x0000600e, 151 | EXIT_QUALIFICATION = 0x00006400, // Natural-Width Read-Only Data Fields 152 | IO_RCX = 0x00006402, 153 | IO_RSI = 0x00006404, 154 | IO_RDI = 0x00006406, 155 | IO_RIP = 0x00006408, 156 | GUEST_LINEAR_ADDRESS = 0x0000640a, 157 | GUEST_CR0 = 0x00006800, // Natural-Width Guest-State Fields 158 | GUEST_CR3 = 0x00006802, 159 | GUEST_CR4 = 0x00006804, 160 | GUEST_ES_BASE = 0x00006806, 161 | GUEST_CS_BASE = 0x00006808, 162 | GUEST_SS_BASE = 0x0000680a, 163 | GUEST_DS_BASE = 0x0000680c, 164 | GUEST_FS_BASE = 0x0000680e, 165 | GUEST_GS_BASE = 0x00006810, 166 | GUEST_LDTR_BASE = 0x00006812, 167 | GUEST_TR_BASE = 0x00006814, 168 | GUEST_GDTR_BASE = 0x00006816, 169 | GUEST_IDTR_BASE = 0x00006818, 170 | GUEST_DR7 = 0x0000681a, 171 | GUEST_RSP = 0x0000681c, 172 | GUEST_RIP = 0x0000681e, 173 | GUEST_RFLAGS = 0x00006820, 174 | GUEST_PENDING_DBG_EXCEPTIONS = 0x00006822, 175 | GUEST_SYSENTER_ESP = 0x00006824, 176 | GUEST_SYSENTER_EIP = 0x00006826, 177 | HOST_CR0 = 0x00006c00, // Natural-Width Host-State Fields 178 | HOST_CR3 = 0x00006c02, 179 | HOST_CR4 = 0x00006c04, 180 | HOST_FS_BASE = 0x00006c06, 181 | HOST_GS_BASE = 0x00006c08, 182 | HOST_TR_BASE = 0x00006c0a, 183 | HOST_GDTR_BASE = 0x00006c0c, 184 | HOST_IDTR_BASE = 0x00006c0e, 185 | HOST_IA32_SYSENTER_ESP = 0x00006c10, 186 | HOST_IA32_SYSENTER_EIP = 0x00006c12, 187 | HOST_RSP = 0x00006c14, 188 | HOST_RIP = 0x00006c16 189 | } VMCS_ENCODING; 190 | 191 | /// 192 | /// Read VMCS field 193 | /// 194 | /// Field encoding 195 | /// Data 196 | ULONG_PTR VmcsRead(IN ULONG VmcsFieldId); 197 | -------------------------------------------------------------------------------- /VT_demo/VT_demo.vcxproj.filters: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | {4FC737F1-C7A5-4376-A066-2A32D752A2FF} 6 | cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx 7 | 8 | 9 | {93995380-89BD-4b04-88EB-625FBE52EBFB} 10 | h;hpp;hxx;hm;inl;inc;xsd 11 | 12 | 13 | {67DA6AB6-F800-4c08-8B7A-83BB121AAD01} 14 | rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms 15 | 16 | 17 | {8E41214B-6785-4CFE-B992-037D68949A14} 18 | inf;inv;inx;mof;mc; 19 | 20 | 21 | {4fe58238-b8e0-45a2-b574-88ac63420442} 22 | 23 | 24 | 25 | 26 | Source Files 27 | 28 | 29 | Source Files 30 | 31 | 32 | Source Files 33 | 34 | 35 | Source Files 36 | 37 | 38 | Source Files 39 | 40 | 41 | Source Files 42 | 43 | 44 | Source Files 45 | 46 | 47 | Source Files 48 | 49 | 50 | Source Files\VMM2 51 | 52 | 53 | Source Files\VMM2 54 | 55 | 56 | Source Files 57 | 58 | 59 | Source Files 60 | 61 | 62 | Source Files 63 | 64 | 65 | Source Files 66 | 67 | 68 | Source Files 69 | 70 | 71 | Source Files 72 | 73 | 74 | Source Files 75 | 76 | 77 | Source Files\VMM2 78 | 79 | 80 | Source Files\VMM2 81 | 82 | 83 | Source Files\VMM2 84 | 85 | 86 | Source Files 87 | 88 | 89 | Source Files 90 | 91 | 92 | Source Files 93 | 94 | 95 | Source Files 96 | 97 | 98 | Source Files 99 | 100 | 101 | Source Files 102 | 103 | 104 | Source Files\VMM2 105 | 106 | 107 | Source Files\VMM2 108 | 109 | 110 | Source Files 111 | 112 | 113 | 114 | 115 | Header Files 116 | 117 | 118 | Header Files 119 | 120 | 121 | Header Files 122 | 123 | 124 | Header Files 125 | 126 | 127 | Header Files 128 | 129 | 130 | Header Files 131 | 132 | 133 | Header Files 134 | 135 | 136 | Header Files 137 | 138 | 139 | Header Files 140 | 141 | 142 | Header Files 143 | 144 | 145 | Header Files 146 | 147 | 148 | Header Files 149 | 150 | 151 | Header Files 152 | 153 | 154 | Header Files 155 | 156 | 157 | Source Files\VMM2 158 | 159 | 160 | Source Files\VMM2 161 | 162 | 163 | Source Files\VMM2 164 | 165 | 166 | Source Files\VMM2 167 | 168 | 169 | Source Files 170 | 171 | 172 | Header Files 173 | 174 | 175 | Header Files 176 | 177 | 178 | Header Files 179 | 180 | 181 | Header Files 182 | 183 | 184 | Header Files 185 | 186 | 187 | Header Files 188 | 189 | 190 | Header Files 191 | 192 | 193 | Header Files 194 | 195 | 196 | Header Files 197 | 198 | 199 | Header Files 200 | 201 | 202 | Header Files 203 | 204 | 205 | 206 | 207 | Header Files 208 | 209 | 210 | Header Files 211 | 212 | 213 | Source Files 214 | 215 | 216 | Source Files 217 | 218 | 219 | Source Files\VMM2 220 | 221 | 222 | Source Files 223 | 224 | 225 | -------------------------------------------------------------------------------- /VT_demo/gobalConter.h: -------------------------------------------------------------------------------- 1 | #include "ntddk.h" 2 | #include "ntstrsafe.h" 3 | ULONG64 G_GuestCr3; 4 | VOID NTAPI HookEptMemoryPage(PEPROCESS Process, ULONG64 Address); 5 | BOOLEAN NTAPI UnHookEptPage(PVOID GuestPA); 6 | ULONG64 Search64Process(HANDLE hProcess); 7 | PEPROCESS TargetProcess; 8 | ULONG64 oldGuestRip; 9 | ULONG64 oldCr3; 10 | ULONG64 TargetAddress; 11 | typedef struct _DBGSTRUCT{ 12 | ULONG64 Pte; 13 | BOOLEAN addrHook; 14 | ULONG64 Addr; 15 | 16 | }DBGSTRUCT, *PDBGSTRUCT; 17 | DBGSTRUCT Bpaddr[6]; 18 | ULONG64 Guest_CR3; 19 | 20 | #define DEVICE_NAME L"\\Device\\vmmHardBreak" 21 | #define LINK_NAME L"\\DosDevices\\vmmHardBreak" 22 | #define LINK_GLOBAL_NAME L"\\DosDevices\\Global\\vmmHardBreak" 23 | 24 | 25 | 26 | 27 | #define Hookpage CTL_CODE(FILE_DEVICE_UNKNOWN, 0x650, METHOD_BUFFERED, FILE_ANY_ACCESS) 28 | #define Unhookpage CTL_CODE(FILE_DEVICE_UNKNOWN, 0x651, METHOD_BUFFERED, FILE_ANY_ACCESS) 29 | #define TargetHookAddress CTL_CODE(FILE_DEVICE_UNKNOWN, 0x652, METHOD_BUFFERED, FILE_ANY_ACCESS) 30 | #define TargetProcessId CTL_CODE(FILE_DEVICE_UNKNOWN, 0x653, METHOD_BUFFERED, FILE_ANY_ACCESS) 31 | #define ISrecv CTL_CODE(FILE_DEVICE_UNKNOWN, 0x654, METHOD_BUFFERED, FILE_ANY_ACCESS) 32 | 33 | 34 | #define IOCTL_notiyenable CTL_CODE(FILE_DEVICE_UNKNOWN, 0x802, METHOD_BUFFERED, FILE_ANY_ACCESS) 35 | 36 | #define IOCTL_ObDuplicateObject CTL_CODE(FILE_DEVICE_UNKNOWN, 0x907, METHOD_BUFFERED, FILE_ANY_ACCESS) 37 | 38 | #define IOCTL_KiSaveDebugRegisterState CTL_CODE(FILE_DEVICE_UNKNOWN, 0x917, METHOD_BUFFERED, FILE_ANY_ACCESS) 39 | #define IOCTL_KiUmsCallEntry CTL_CODE(FILE_DEVICE_UNKNOWN, 0x918, METHOD_BUFFERED, FILE_ANY_ACCESS) 40 | #define IOCTL_KiSystemServiceExit CTL_CODE(FILE_DEVICE_UNKNOWN, 0x919, METHOD_BUFFERED, FILE_ANY_ACCESS) 41 | #define IOCTL_KeGdiFlushUserBatch CTL_CODE(FILE_DEVICE_UNKNOWN, 0x920, METHOD_BUFFERED, FILE_ANY_ACCESS) 42 | #define IOCTL_KiSystemServiceRepeat CTL_CODE(FILE_DEVICE_UNKNOWN, 0x921, METHOD_BUFFERED, FILE_ANY_ACCESS) 43 | 44 | #define IOCTL_KeServiceDescriptorTable CTL_CODE(FILE_DEVICE_UNKNOWN, 0x804, METHOD_BUFFERED, FILE_ANY_ACCESS) 45 | #define IOCTL_KeServiceDescriptorTableShadow CTL_CODE(FILE_DEVICE_UNKNOWN, 0x805, METHOD_BUFFERED, FILE_ANY_ACCESS) 46 | #define IOCTL_KiSystemServiceCopyEnd CTL_CODE(FILE_DEVICE_UNKNOWN, 0x922, METHOD_BUFFERED, FILE_ANY_ACCESS) 47 | #define IOCTL_DbgkDebugObjectType CTL_CODE(FILE_DEVICE_UNKNOWN, 0x923, METHOD_BUFFERED, FILE_ANY_ACCESS) 48 | #define IOCTL_DbgkpPostFakeThreadMessages CTL_CODE(FILE_DEVICE_UNKNOWN, 0x893, METHOD_BUFFERED, FILE_ANY_ACCESS) 49 | 50 | #define IOCTL_DbgkpPostModuleMessages CTL_CODE(FILE_DEVICE_UNKNOWN, 0x897, METHOD_BUFFERED, FILE_ANY_ACCESS) 51 | #define IOCTL_KeFreezeAllThreads CTL_CODE(FILE_DEVICE_UNKNOWN, 0x901, METHOD_BUFFERED, FILE_ANY_ACCESS) 52 | #define IOCTL_PsResumeThread CTL_CODE(FILE_DEVICE_UNKNOWN, 0x811, METHOD_BUFFERED, FILE_ANY_ACCESS) 53 | #define IOCTL_KeThawAllThreads CTL_CODE(FILE_DEVICE_UNKNOWN, 0x902, METHOD_BUFFERED, FILE_ANY_ACCESS) 54 | #define IOCTL_PsGetNextProcessThread CTL_CODE(FILE_DEVICE_UNKNOWN, 0x885, METHOD_BUFFERED, FILE_ANY_ACCESS) 55 | #define IOCTL_PsSuspendThread CTL_CODE(FILE_DEVICE_UNKNOWN, 0x924, METHOD_BUFFERED, FILE_ANY_ACCESS) 56 | 57 | #define IOCTL_LpcRequestWaitReplyPortEx CTL_CODE(FILE_DEVICE_UNKNOWN, 0x925, METHOD_BUFFERED, FILE_ANY_ACCESS) 58 | #define IOCTL_DbgkpProcessDebugPortMutex CTL_CODE(FILE_DEVICE_UNKNOWN, 0x889, METHOD_BUFFERED, FILE_ANY_ACCESS) 59 | 60 | #define IOCTL_KiConvertToGuiThread CTL_CODE(FILE_DEVICE_UNKNOWN, 0x930, METHOD_BUFFERED, FILE_ANY_ACCESS) 61 | #define IOCTL_KiRetireDpcList CTL_CODE(FILE_DEVICE_UNKNOWN, 0x911, METHOD_BUFFERED, FILE_ANY_ACCESS) 62 | #define IOCTL_DbgkCopyProcessDebugPort CTL_CODE(FILE_DEVICE_UNKNOWN, 0x850, METHOD_BUFFERED, FILE_ANY_ACCESS) 63 | #define IOCTL_KiDispatchException CTL_CODE(FILE_DEVICE_UNKNOWN, 0x854, METHOD_BUFFERED, FILE_ANY_ACCESS) 64 | 65 | #define IOCTL_DbgkForwardException CTL_CODE(FILE_DEVICE_UNKNOWN, 0x852, METHOD_BUFFERED, FILE_ANY_ACCESS) 66 | 67 | #define IOCTL_MmGetFileNameForSection CTL_CODE(FILE_DEVICE_UNKNOWN, 0x903, METHOD_BUFFERED, FILE_ANY_ACCESS) 68 | 69 | #define IOCTL_PsGetNextProcess CTL_CODE(FILE_DEVICE_UNKNOWN, 0x931, METHOD_BUFFERED, FILE_ANY_ACCESS) 70 | #define IOCTL_PsTerminateProcess CTL_CODE(FILE_DEVICE_UNKNOWN, 0x932, METHOD_BUFFERED, FILE_ANY_ACCESS) 71 | #define IOCTL_DbgkpSendApiMessage CTL_CODE(FILE_DEVICE_UNKNOWN, 0x934, METHOD_BUFFERED, FILE_ANY_ACCESS) 72 | 73 | 74 | 75 | #define IOCTL_DbgkOpenProcessDebugPort CTL_CODE(FILE_DEVICE_UNKNOWN, 0x858, METHOD_BUFFERED, FILE_ANY_ACCESS) 76 | 77 | #define IOCTL_DbgkUnMapViewOfSection CTL_CODE(FILE_DEVICE_UNKNOWN, 0x855, METHOD_BUFFERED, FILE_ANY_ACCESS) 78 | 79 | #define IOCTL_DbgkMapViewOfSection CTL_CODE(FILE_DEVICE_UNKNOWN, 0x856, METHOD_BUFFERED, FILE_ANY_ACCESS) 80 | #define IOCTL_ObTypeIndexTable CTL_CODE(FILE_DEVICE_UNKNOWN, 0x933, METHOD_BUFFERED, FILE_ANY_ACCESS) 81 | #define IOCTL_DbgkExitProcess CTL_CODE(FILE_DEVICE_UNKNOWN, 0x862, METHOD_BUFFERED, FILE_ANY_ACCESS) 82 | #define IOCTL_DbgkExitThread CTL_CODE(FILE_DEVICE_UNKNOWN, 0x861, METHOD_BUFFERED, FILE_ANY_ACCESS) 83 | #define IOCTL_ObpCallPreOperationCallbacks CTL_CODE(FILE_DEVICE_UNKNOWN, 0x900, METHOD_BUFFERED, FILE_ANY_ACCESS) 84 | #define IOCTL_ExGetCallBackBlockRoutine CTL_CODE(FILE_DEVICE_UNKNOWN, 0x898, METHOD_BUFFERED, FILE_ANY_ACCESS) 85 | 86 | #define IOCTL_dbgProcessId CTL_CODE(FILE_DEVICE_UNKNOWN, 0x881, METHOD_BUFFERED, FILE_ANY_ACCESS) 87 | 88 | #define IOCTL_DbgkpQueueMessage CTL_CODE(FILE_DEVICE_UNKNOWN, 0x853, METHOD_BUFFERED, FILE_ANY_ACCESS) 89 | #define IOCTL_DbgkpSetProcessDebugObject CTL_CODE(FILE_DEVICE_UNKNOWN, 0x851, METHOD_BUFFERED, FILE_ANY_ACCESS) 90 | #define IOCTL_DbgkpPostFakeProcessCreateMessages CTL_CODE(FILE_DEVICE_UNKNOWN, 0x892, METHOD_BUFFERED, FILE_ANY_ACCESS) 91 | #define IOCTL_MmGetFileNameForAddress CTL_CODE(FILE_DEVICE_UNKNOWN, 0x935, METHOD_BUFFERED, FILE_ANY_ACCESS) 92 | #define IOCTL_PspSystemDlls CTL_CODE(FILE_DEVICE_UNKNOWN, 0x904, METHOD_BUFFERED, FILE_ANY_ACCESS) 93 | 94 | #define IOCTL_DbgkpWakeTarget CTL_CODE(FILE_DEVICE_UNKNOWN, 0x891, METHOD_BUFFERED, FILE_ANY_ACCESS) 95 | #define IOCTL_NtQueryInformationThread CTL_CODE(FILE_DEVICE_UNKNOWN, 0x914, METHOD_BUFFERED, FILE_ANY_ACCESS) 96 | 97 | #define IOCTL_ExCompareExchangeCallBack CTL_CODE(FILE_DEVICE_UNKNOWN, 0x936, METHOD_BUFFERED, FILE_ANY_ACCESS) 98 | 99 | #define IOCTL_KiRestoreDebugRegisterState CTL_CODE(FILE_DEVICE_UNKNOWN, 0x937, METHOD_BUFFERED, FILE_ANY_ACCESS) 100 | #define IOCTL_RtlpCopyLegacyContextX86 CTL_CODE(FILE_DEVICE_UNKNOWN, 0x938, METHOD_BUFFERED, FILE_ANY_ACCESS) 101 | 102 | #define IOCTL_keycode CTL_CODE(FILE_DEVICE_UNKNOWN, 0x939, METHOD_BUFFERED, FILE_ANY_ACCESS) 103 | #define IOCTL_keycheck CTL_CODE(FILE_DEVICE_UNKNOWN, 0x940, METHOD_BUFFERED, FILE_ANY_ACCESS) 104 | 105 | 106 | #define IOCTL_NtReadVirtualMemory CTL_CODE(FILE_DEVICE_UNKNOWN, 0x941, METHOD_BUFFERED, FILE_ANY_ACCESS) 107 | #define IOCTL_NtWriteVirtualMemory CTL_CODE(FILE_DEVICE_UNKNOWN, 0x942, METHOD_BUFFERED, FILE_ANY_ACCESS) 108 | #define IOCTL_NtOpenProcess CTL_CODE(FILE_DEVICE_UNKNOWN, 0x943, METHOD_BUFFERED, FILE_ANY_ACCESS) 109 | #define IOCTL_KiAttachProcess CTL_CODE(FILE_DEVICE_UNKNOWN, 0x944, METHOD_BUFFERED, FILE_ANY_ACCESS) 110 | 111 | 112 | #define IOCTL_NtCreateDebugObject CTL_CODE(FILE_DEVICE_UNKNOWN, 0x895, METHOD_BUFFERED, FILE_ANY_ACCESS) 113 | #define IOCTL_NtWaitForDebugEvent CTL_CODE(FILE_DEVICE_UNKNOWN, 0x910, METHOD_BUFFERED, FILE_ANY_ACCESS) 114 | #define IOCTL_NtDebugContinue CTL_CODE(FILE_DEVICE_UNKNOWN, 0x909, METHOD_BUFFERED, FILE_ANY_ACCESS) 115 | #define IOCTL_NtDebugActiveProcess CTL_CODE(FILE_DEVICE_UNKNOWN, 0x894, METHOD_BUFFERED, FILE_ANY_ACCESS) 116 | 117 | #define IOCTL_NtRemoveProcessDebug CTL_CODE(FILE_DEVICE_UNKNOWN, 0x908, METHOD_BUFFERED, FILE_ANY_ACCESS) 118 | 119 | #define IOCTL_DbgLol CTL_CODE(FILE_DEVICE_UNKNOWN, 0x950, METHOD_BUFFERED, FILE_ANY_ACCESS) 120 | 121 | 122 | 123 | #define IOCTL_SwapContext_PatchXRstor CTL_CODE(FILE_DEVICE_UNKNOWN, 0x945, METHOD_BUFFERED, FILE_ANY_ACCESS) 124 | 125 | #define IOCTL_SwapContext CTL_CODE(FILE_DEVICE_UNKNOWN, 0x946, METHOD_BUFFERED, FILE_ANY_ACCESS) 126 | 127 | extern ULONG64 SwapContext_PatchXRstor; 128 | extern ULONG64 SwapContext; 129 | 130 | BOOLEAN DbgConter = FALSE; 131 | extern ULONG64 myNtRemoveProcessDebug; 132 | extern ULONG64 NtDebugActiveProcess; 133 | extern ULONG64 NtDebugContinue; 134 | extern ULONG64 NtWaitForDebugEvent; 135 | extern ULONG64 NtCreateDebugObject; 136 | 137 | ULONG64 NtReadVirtualMemory; 138 | ULONG64 NtWriteVirtualMemory; 139 | ULONG64 XNtOpenProcess; 140 | extern ULONG64 KiAttachProcess; 141 | 142 | char keycode[1024] = { 0 }; 143 | char keycheck[1024] = { 0 }; 144 | 145 | extern ULONG64 RtlpCopyLegacyContextX86; 146 | extern ULONG64 KiRestoreDebugRegisterState; 147 | extern ULONG64 ExCompareExchangeCallBack; 148 | extern ULONG64 NtQueryInformationThread; 149 | extern ULONG64 DbgkpWakeTarget_2; 150 | extern ULONG64 MmGetFileNameForAddress; 151 | extern ULONG64 ExGetCallBackBlockRoutine; 152 | extern ULONG64 ObpCallPreOperationCallbacks; 153 | extern ULONG64 ObTypeIndexTable; 154 | extern ULONG64 DbgkOpenProcessDebugPort; 155 | extern ULONG64 DbgkUnMapViewOfSection; 156 | extern ULONG64 DbgkMapViewOfSection; 157 | 158 | extern ULONG64 DbgkExitProcess; 159 | extern ULONG64 DbgkExitThread; 160 | extern ULONG64 PspSystemDlls; 161 | extern ULONG64 DbgkpPostFakeProcessCreateMessages; 162 | extern ULONG64 DbgkpSetProcessDebugObject; 163 | extern ULONG64 PsTerminateProcess; 164 | extern ULONG64 PsGetNextProcess; 165 | extern ULONG64 MmGetFileNameForSection; 166 | extern ULONG64 DbgkForwardException; 167 | extern ULONG64 KiDispatchException; 168 | ULONG64 KiConvertToGuiThread; 169 | extern ULONG64 ObDuplicateObject; 170 | extern ULONG64 KiRetireDpcList; 171 | extern ULONG64 DbgkCopyProcessDebugPort; 172 | extern ULONG64 KiSaveDebugRegisterState; 173 | extern ULONG64 KiUmsCallEntry; 174 | extern ULONG64 KiSystemServiceExit; 175 | extern ULONG64 KeGdiFlushUserBatch; 176 | extern ULONG64 KiSystemServiceRepeat; 177 | extern ULONG64 KeServiceDescriptorTable; 178 | extern ULONG64 KeServiceDescriptorTableShadow; 179 | extern ULONG64 KiSystemServiceCopyEnd; 180 | extern ULONG64 DbgkDebugObjectType; 181 | extern ULONG64 PsGetNextProcessThread; 182 | extern ULONG64 DbgkpPostModuleMessages; 183 | extern ULONG64 PsSuspendThread; 184 | extern ULONG64 KeFreezeAllThreads; 185 | extern ULONG64 DbgkpPostFakeThreadMessages; 186 | extern ULONG64 KeThawAllThreads; 187 | extern ULONG64 PsResumeThread; 188 | extern ULONG64 LpcRequestWaitReplyPortEx; 189 | extern ULONG64 DbgkpProcessDebugPortMutex; 190 | extern ULONG64 DbgkpSendApiMessage; 191 | extern ULONG64 DbgkpQueueMessage; 192 | -------------------------------------------------------------------------------- /VT_demo/Include/CPU.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | #include 3 | 4 | #define MSR_APIC_BASE 0x01B 5 | #define MSR_IA32_FEATURE_CONTROL 0x03A 6 | 7 | #define MSR_IA32_VMX_BASIC 0x480 8 | #define MSR_IA32_VMX_PINBASED_CTLS 0x481 9 | #define MSR_IA32_VMX_PROCBASED_CTLS 0x482 10 | #define MSR_IA32_VMX_EXIT_CTLS 0x483 11 | #define MSR_IA32_VMX_ENTRY_CTLS 0x484 12 | #define MSR_IA32_VMX_MISC 0x485 13 | #define MSR_IA32_VMX_CR0_FIXED0 0x486 14 | #define MSR_IA32_VMX_CR0_FIXED1 0x487 15 | #define MSR_IA32_VMX_CR4_FIXED0 0x488 16 | #define MSR_IA32_VMX_CR4_FIXED1 0x489 17 | #define MSR_IA32_VMX_VMCS_ENUM 0x48A 18 | #define MSR_IA32_VMX_PROCBASED_CTLS2 0x48B 19 | #define MSR_IA32_VMX_EPT_VPID_CAP 0x48C 20 | #define MSR_IA32_VMX_TRUE_PINBASED_CTLS 0x48D 21 | #define MSR_IA32_VMX_TRUE_PROCBASED_CTLS 0x48E 22 | #define MSR_IA32_VMX_TRUE_EXIT_CTLS 0x48F 23 | #define MSR_IA32_VMX_TRUE_ENTRY_CTLS 0x490 24 | #define MSR_IA32_VMX_VMFUNC 0x491 25 | 26 | #define MSR_IA32_SYSENTER_CS 0x174 27 | #define MSR_IA32_SYSENTER_ESP 0x175 28 | #define MSR_IA32_SYSENTER_EIP 0x176 29 | #define MSR_IA32_DEBUGCTL 0x1D9 30 | 31 | #define MSR_LSTAR 0xC0000082 32 | 33 | #define MSR_FS_BASE 0xC0000100 34 | #define MSR_GS_BASE 0xC0000101 35 | #define MSR_SHADOW_GS_BASE 0xC0000102 // SwapGS GS shadow 36 | 37 | 38 | #pragma warning(disable: 4214 4201) 39 | typedef struct _CPUID 40 | { 41 | int eax; 42 | int ebx; 43 | int ecx; 44 | int edx; 45 | } CPUID, *PCPUID; 46 | 47 | // RFLAGS 48 | typedef union _EFLAGS 49 | { 50 | ULONG_PTR All; 51 | struct 52 | { 53 | ULONG CF : 1; // [0] Carry flag 54 | ULONG Reserved1 : 1; // [1] Always 1 55 | ULONG PF : 1; // [2] Parity flag 56 | ULONG Reserved2 : 1; // [3] Always 0 57 | ULONG AF : 1; // [4] Borrow flag 58 | ULONG Reserved3 : 1; // [5] Always 0 59 | ULONG ZF : 1; // [6] Zero flag 60 | ULONG SF : 1; // [7] Sign flag 61 | ULONG TF : 1; // [8] Trap flag 62 | ULONG IF : 1; // [9] Interrupt flag 63 | ULONG DF : 1; // [10] 64 | ULONG OF : 1; // [11] 65 | ULONG IOPL : 2; // [12-13] I/O privilege level 66 | ULONG NT : 1; // [14] Nested task flag 67 | ULONG Reserved4 : 1; // [15] Always 0 68 | ULONG RF : 1; // [16] Resume flag 69 | ULONG VM : 1; // [17] Virtual 8086 mode 70 | ULONG AC : 1; // [18] Alignment check 71 | ULONG VIF : 1; // [19] Virtual interrupt flag 72 | ULONG VIP : 1; // [20] Virtual interrupt pending 73 | ULONG ID : 1; // [21] Identification flag 74 | ULONG Reserved5 : 10; // [22-31] Always 0 75 | } Fields; 76 | } EFLAGS, *PEFLAGS; 77 | 78 | // CR0 79 | typedef union _CR0_REG 80 | { 81 | ULONG_PTR All; 82 | struct 83 | { 84 | ULONG PE : 1; // [0] Protected Mode Enabled 85 | ULONG MP : 1; // [1] Monitor Coprocessor FLAG 86 | ULONG EM : 1; // [2] Emulate FLAG 87 | ULONG TS : 1; // [3] Task Switched FLAG 88 | ULONG ET : 1; // [4] Extension Type FLAG 89 | ULONG NE : 1; // [5] Numeric Error 90 | ULONG Reserved1 : 10; // [6-15] 91 | ULONG WP : 1; // [16] Write Protect 92 | ULONG Reserved2 : 1; // [17] 93 | ULONG AM : 1; // [18] Alignment Mask 94 | ULONG Reserved3 : 10; // [19-28] 95 | ULONG NW : 1; // [29] Not Write-Through 96 | ULONG CD : 1; // [30] Cache Disable 97 | ULONG PG : 1; // [31] Paging Enabled 98 | } Fields; 99 | } CR0_REG, *PCR0_REG; 100 | 101 | // CR4 102 | typedef union _CR4_REG 103 | { 104 | ULONG_PTR All; 105 | struct 106 | { 107 | ULONG VME : 1; // [0] Virtual Mode Extensions 108 | ULONG PVI : 1; // [1] Protected-Mode Virtual Interrupts 109 | ULONG TSD : 1; // [2] Time Stamp Disable 110 | ULONG DE : 1; // [3] Debugging Extensions 111 | ULONG PSE : 1; // [4] Page Size Extensions 112 | ULONG PAE : 1; // [5] Physical Address Extension 113 | ULONG MCE : 1; // [6] Machine-Check Enable 114 | ULONG PGE : 1; // [7] Page Global Enable 115 | ULONG PCE : 1; // [8] Performance-Monitoring Counter Enable 116 | ULONG OSFXSR : 1; // [9] OS Support for FXSAVE/FXRSTOR 117 | ULONG OSXMMEXCPT : 1; // [10] OS Support for Unmasked SIMD Exceptions 118 | ULONG Reserved1 : 2; // [11-12] 119 | ULONG VMXE : 1; // [13] Virtual Machine Extensions Enabled 120 | ULONG SMXE : 1; // [14] SMX-Enable Bit 121 | ULONG Reserved2 : 2; // [15-16] 122 | ULONG PCIDE : 1; // [17] PCID Enable 123 | ULONG OSXSAVE : 1; // [18] XSAVE and Processor Extended States-Enable 124 | ULONG Reserved3 : 1; // [19] 125 | ULONG SMEP : 1; // [20] Supervisor Mode Execution Protection Enable 126 | ULONG SMAP : 1; // [21] Supervisor Mode Access Protection Enable 127 | } Fields; 128 | } CR4_REG, *PCR4_REG; 129 | 130 | typedef union _IA32_APIC_BASE 131 | { 132 | ULONG64 All; 133 | struct 134 | { 135 | ULONG64 Reserved1 : 8; // [0-7] 136 | ULONG64 Bootstrap_processor : 1; // [8] 137 | ULONG64 Reserved2 : 1; // [9] 138 | ULONG64 Enable_x2apic_mode : 1; // [10] 139 | ULONG64 Enable_xapic_global : 1; // [11] 140 | ULONG64 Apic_base : 24; // [12-35] 141 | } Fields; 142 | } IA32_APIC_BASE, *PIA32_APIC_BASE; 143 | 144 | typedef union _IA32_VMX_BASIC_MSR 145 | { 146 | ULONG64 All; 147 | struct 148 | { 149 | ULONG32 RevisionIdentifier : 31; // [0-30] 150 | ULONG32 Reserved1 : 1; // [31] 151 | ULONG32 RegionSize : 12; // [32-43] 152 | ULONG32 RegionClear : 1; // [44] 153 | ULONG32 Reserved2 : 3; // [45-47] 154 | ULONG32 SupportedIA64 : 1; // [48] 155 | ULONG32 SupportedDualMoniter : 1; // [49] 156 | ULONG32 MemoryType : 4; // [50-53] 157 | ULONG32 VmExitReport : 1; // [54] 158 | ULONG32 VmxCapabilityHint : 1; // [55] 159 | ULONG32 Reserved3 : 8; // [56-63] 160 | } Fields; 161 | } IA32_VMX_BASIC_MSR, *PIA32_VMX_BASIC_MSR; 162 | 163 | typedef union _IA32_VMX_PROCBASED_CTLS_MSR 164 | { 165 | ULONG64 All; 166 | struct 167 | { 168 | ULONG64 Reserved0 : 32; // [0-31] 169 | ULONG64 Reserved1 : 2; // [32 + 0-1] 170 | ULONG64 InterruptWindowExiting : 1; // [32 + 2] 171 | ULONG64 UseTSCOffseting : 1; // [32 + 3] 172 | ULONG64 Reserved2 : 3; // [32 + 4-6] 173 | ULONG64 HLTExiting : 1; // [32 + 7] 174 | ULONG64 Reserved3 : 1; // [32 + 8] 175 | ULONG64 INVLPGExiting : 1; // [32 + 9] 176 | ULONG64 MWAITExiting : 1; // [32 + 10] 177 | ULONG64 RDPMCExiting : 1; // [32 + 11] 178 | ULONG64 RDTSCExiting : 1; // [32 + 12] 179 | ULONG64 Reserved4 : 2; // [32 + 13-14] 180 | ULONG64 CR3LoadExiting : 1; // [32 + 15] 181 | ULONG64 CR3StoreExiting : 1; // [32 + 16] 182 | ULONG64 Reserved5 : 2; // [32 + 17-18] 183 | ULONG64 CR8LoadExiting : 1; // [32 + 19] 184 | ULONG64 CR8StoreExiting : 1; // [32 + 20] 185 | ULONG64 UseTPRShadowExiting : 1; // [32 + 21] 186 | ULONG64 NMIWindowExiting : 1; // [32 + 22] 187 | ULONG64 MovDRExiting : 1; // [32 + 23] 188 | ULONG64 UnconditionalIOExiting : 1; // [32 + 24] 189 | ULONG64 UseIOBitmaps : 1; // [32 + 25] 190 | ULONG64 Reserved6 : 1; // [32 + 26] 191 | ULONG64 MonitorTrapFlag : 1; // [32 + 27] 192 | ULONG64 UseMSRBitmaps : 1; // [32 + 28] 193 | ULONG64 MONITORExiting : 1; // [32 + 29] 194 | ULONG64 PAUSEExiting : 1; // [32 + 30] 195 | ULONG64 ActivateSecondaryControl : 1; // [32 + 31] Does VMX_PROCBASED_CTLS2_MSR exist 196 | } Fields; 197 | } IA32_VMX_PROCBASED_CTLS_MSR, *PIA32_VMX_PROCBASED_CTLS_MSR; 198 | 199 | typedef union _IA32_VMX_PROCBASED_CTLS2_MSR 200 | { 201 | ULONG64 All; 202 | struct 203 | { 204 | ULONG64 Reserved0 : 32; // [0-31] 205 | ULONG64 VirtualizeAPICAccesses : 1; // [32 + 0] 206 | ULONG64 EnableEPT : 1; // [32 + 1] 207 | ULONG64 DescriptorTableExiting : 1; // [32 + 2] 208 | ULONG64 EnableRDTSCP : 1; // [32 + 3] 209 | ULONG64 VirtualizeX2APICMode : 1; // [32 + 4] 210 | ULONG64 EnableVPID : 1; // [32 + 5] 211 | ULONG64 WBINVDExiting : 1; // [32 + 6] 212 | ULONG64 UnrestrictedGuest : 1; // [32 + 7] 213 | ULONG64 APICRegisterVirtualization : 1; // [32 + 8] 214 | ULONG64 VirtualInterruptDelivery : 1; // [32 + 9] 215 | ULONG64 PAUSELoopExiting : 1; // [32 + 10] 216 | ULONG64 RDRANDExiting : 1; // [32 + 11] 217 | ULONG64 EnableINVPCID : 1; // [32 + 12] 218 | ULONG64 EnableVMFunctions : 1; // [32 + 13] 219 | ULONG64 VMCSShadowing : 1; // [32 + 14] 220 | ULONG64 Reserved1 : 1; // [32 + 15] 221 | ULONG64 RDSEEDExiting : 1; // [32 + 16] 222 | ULONG64 Reserved2 : 1; // [32 + 17] 223 | ULONG64 EPTViolation : 1; // [32 + 18] 224 | ULONG64 Reserved3 : 1; // [32 + 19] 225 | ULONG64 EnableXSAVESXSTORS : 1; // [32 + 20] 226 | } Fields; 227 | } IA32_VMX_PROCBASED_CTLS2_MSR, *PIA32_VMX_PROCBASED_CTLS2_MSR; 228 | 229 | typedef union _IA32_FEATURE_CONTROL_MSR 230 | { 231 | ULONG64 All; 232 | struct 233 | { 234 | ULONG64 Lock : 1; // [0] 235 | ULONG64 EnableSMX : 1; // [1] 236 | ULONG64 EnableVmxon : 1; // [2] 237 | ULONG64 Reserved2 : 5; // [3-7] 238 | ULONG64 EnableLocalSENTER : 7; // [8-14] 239 | ULONG64 EnableGlobalSENTER : 1; // [15] 240 | ULONG64 Reserved3a : 16; // 241 | ULONG64 Reserved3b : 32; // [16-63] 242 | } Fields; 243 | } IA32_FEATURE_CONTROL_MSR, *PIA32_FEATURE_CONTROL_MSR; 244 | 245 | typedef union _IA32_VMX_EPT_VPID_CAP_MSR 246 | { 247 | ULONG64 All; 248 | struct 249 | { 250 | ULONG64 ExecuteOnly : 1; // Bit 0 defines if the EPT implementation supports execute-only translation 251 | ULONG64 Reserved1 : 31; // Undefined 252 | ULONG64 Reserved2 : 8; // Undefined 253 | ULONG64 IndividualAddressInvVpid : 1; // Bit 40 defines if type 0 INVVPID instructions are supported 254 | ULONG64 Reserved3 : 23; 255 | } Fields; 256 | } IA32_VMX_EPT_VPID_CAP_MSR, *PIA32_VMX_EPT_VPID_CAP_MSR; 257 | #pragma warning(disable: 4214 4201) 258 | -------------------------------------------------------------------------------- /VT_demo/Util/Utils.c: -------------------------------------------------------------------------------- 1 | #include "Utils.h" 2 | #include "../Include/PE.h" 3 | #include "../Include/CPU.h" 4 | #include "../Include/Common.h" 5 | #include "../Include/Native.h" 6 | 7 | PVOID g_KernelBase = NULL; 8 | ULONG g_KernelSize = 0; 9 | PSYSTEM_SERVICE_DESCRIPTOR_TABLE g_SSDT = NULL; 10 | 11 | /// 12 | /// Get CPU vendor 13 | /// 14 | /// Intel or AMD. If failed - Other 15 | CPU_VENDOR UtilCPUVendor() 16 | { 17 | CPUID data = { 0 }; 18 | char vendor[0x20] = { 0 }; 19 | __cpuid( (int*)&data, 0 ); 20 | *(int*)(vendor) = data.ebx; 21 | *(int*)(vendor + 4) = data.edx; 22 | *(int*)(vendor + 8) = data.ecx; 23 | 24 | if (memcmp( vendor, "GenuineIntel", 12 ) == 0) 25 | return CPU_Intel; 26 | if (memcmp( vendor, "AuthenticAMD", 12 ) == 0) 27 | return CPU_AMD; 28 | 29 | return CPU_Other; 30 | } 31 | 32 | /// 33 | /// Get ntoskrnl base address 34 | /// 35 | /// Size of module 36 | /// Found address, NULL if not found 37 | PVOID UtilKernelBase( OUT PULONG pSize ) 38 | { 39 | NTSTATUS status = STATUS_SUCCESS; 40 | ULONG bytes = 0; 41 | PRTL_PROCESS_MODULES pMods = NULL; 42 | PVOID checkPtr = NULL; 43 | UNICODE_STRING routineName; 44 | 45 | // Already found 46 | if (g_KernelBase != NULL) 47 | { 48 | if (pSize) 49 | *pSize = g_KernelSize; 50 | return g_KernelBase; 51 | } 52 | 53 | RtlInitUnicodeString( &routineName, L"NtOpenFile" ); 54 | 55 | checkPtr = MmGetSystemRoutineAddress( &routineName ); 56 | if (checkPtr == NULL) 57 | return NULL; 58 | 59 | // Protect from UserMode AV 60 | __try 61 | { 62 | status = ZwQuerySystemInformation( SystemModuleInformation, 0, bytes, &bytes ); 63 | if (bytes == 0) 64 | { 65 | DPRINT( "BlackBone: %s: Invalid SystemModuleInformation size\n", CPU_IDX, __FUNCTION__ ); 66 | return NULL; 67 | } 68 | 69 | pMods = (PRTL_PROCESS_MODULES)ExAllocatePoolWithTag( NonPagedPoolNx, bytes, HB_POOL_TAG ); 70 | RtlZeroMemory( pMods, bytes ); 71 | 72 | status = ZwQuerySystemInformation( SystemModuleInformation, pMods, bytes, &bytes ); 73 | 74 | if (NT_SUCCESS( status )) 75 | { 76 | PRTL_PROCESS_MODULE_INFORMATION pMod = pMods->Modules; 77 | 78 | for (ULONG i = 0; i < pMods->NumberOfModules; i++) 79 | { 80 | // System routine is inside module 81 | if (checkPtr >= pMod[i].ImageBase && 82 | checkPtr < (PVOID)((PUCHAR)pMod[i].ImageBase + pMod[i].ImageSize)) 83 | { 84 | g_KernelBase = pMod[i].ImageBase; 85 | g_KernelSize = pMod[i].ImageSize; 86 | if (pSize) 87 | *pSize = g_KernelSize; 88 | break; 89 | } 90 | } 91 | } 92 | 93 | } 94 | __except (EXCEPTION_EXECUTE_HANDLER) 95 | { 96 | DPRINT( "BlackBone: %s: Exception\n", CPU_IDX, __FUNCTION__ ); 97 | } 98 | 99 | if (pMods) 100 | ExFreePoolWithTag( pMods, HB_POOL_TAG ); 101 | 102 | return g_KernelBase; 103 | } 104 | 105 | /// 106 | /// Gets SSDT base - KiServiceTable 107 | /// 108 | /// SSDT base, NULL if not found 109 | PSYSTEM_SERVICE_DESCRIPTOR_TABLE UtilSSDTBase() 110 | { 111 | PUCHAR ntosBase = UtilKernelBase( NULL ); 112 | 113 | // Already found 114 | if (g_SSDT != NULL) 115 | return g_SSDT; 116 | 117 | if (!ntosBase) 118 | return NULL; 119 | 120 | PIMAGE_NT_HEADERS pHdr = RtlImageNtHeader( ntosBase ); 121 | PIMAGE_SECTION_HEADER pFirstSec = (PIMAGE_SECTION_HEADER)(pHdr + 1); 122 | for (PIMAGE_SECTION_HEADER pSec = pFirstSec; pSec < pFirstSec + pHdr->FileHeader.NumberOfSections; pSec++) 123 | { 124 | // Non-paged, non-discardable, readable sections 125 | // Probably still not fool-proof enough... 126 | if (pSec->Characteristics & IMAGE_SCN_MEM_NOT_PAGED && 127 | pSec->Characteristics & IMAGE_SCN_MEM_EXECUTE && 128 | !(pSec->Characteristics & IMAGE_SCN_MEM_DISCARDABLE) && 129 | (*(PULONG)pSec->Name != 'TINI') && 130 | (*(PULONG)pSec->Name != 'EGAP')) 131 | { 132 | PVOID pFound = NULL; 133 | 134 | // KiSystemServiceRepeat pattern 135 | UCHAR pattern[] = "\x4c\x8d\x15\xcc\xcc\xcc\xcc\x4c\x8d\x1d\xcc\xcc\xcc\xcc\xf7"; 136 | NTSTATUS status = UtilSearchPattern( pattern, 0xCC, sizeof( pattern ) - 1, ntosBase + pSec->VirtualAddress, pSec->Misc.VirtualSize, &pFound ); 137 | if (NT_SUCCESS( status )) 138 | { 139 | g_SSDT = (PSYSTEM_SERVICE_DESCRIPTOR_TABLE)((PUCHAR)pFound + *(PULONG)((PUCHAR)pFound + 3) + 7); 140 | //DPRINT( "BlackBone: %s: KeSystemServiceDescriptorTable = 0x%p\n", CPU_NUM, __FUNCTION__, g_SSDT ); 141 | return g_SSDT; 142 | } 143 | } 144 | } 145 | 146 | return NULL; 147 | } 148 | 149 | /// 150 | /// Gets the SSDT entry address by index. 151 | /// 152 | /// Service index 153 | /// Found service address, NULL if not found 154 | PVOID UtilSSDTEntry( IN ULONG index ) 155 | { 156 | ULONG size = 0; 157 | PSYSTEM_SERVICE_DESCRIPTOR_TABLE pSSDT = UtilSSDTBase(); 158 | PVOID pBase = UtilKernelBase( &size ); 159 | 160 | if (pSSDT && pBase) 161 | { 162 | // Index range check 163 | if (index > pSSDT->NumberOfServices) 164 | return NULL; 165 | 166 | return (PUCHAR)pSSDT->ServiceTableBase + (((PLONG)pSSDT->ServiceTableBase)[index] >> 4); 167 | } 168 | 169 | return NULL; 170 | } 171 | 172 | /// 173 | /// Gather info about used physical pages 174 | /// 175 | /// Status code 176 | NTSTATUS UtilQueryPhysicalMemory() 177 | { 178 | if (g_Data->Memory != NULL) 179 | return STATUS_SUCCESS; 180 | 181 | PPHYSICAL_MEMORY_RANGE pBaseRange = MmGetPhysicalMemoryRanges(); 182 | if (pBaseRange == NULL) 183 | return STATUS_UNSUCCESSFUL; 184 | 185 | // Get ranges count 186 | ULONG runsCount = 0, pageCount = 0; 187 | for (PPHYSICAL_MEMORY_RANGE pRange = pBaseRange; pRange->NumberOfBytes.QuadPart != 0; pRange++) 188 | { 189 | pageCount += (ULONG)PFN( pRange->NumberOfBytes.QuadPart ); 190 | runsCount++; 191 | } 192 | 193 | // Get APIC physical page 194 | IA32_APIC_BASE apic = { 0 }; 195 | apic.All = __readmsr( MSR_APIC_BASE ); 196 | 197 | runsCount += 2; 198 | ULONG size = sizeof( PPHYSICAL_MEMORY_DESCRIPTOR ) + runsCount * sizeof( PHYSICAL_MEMORY_RUN ); 199 | g_Data->Memory = ExAllocatePoolWithTag( NonPagedPoolNx, size, HB_POOL_TAG ); 200 | if (g_Data->Memory != NULL) 201 | { 202 | RtlZeroMemory( g_Data->Memory, size ); 203 | 204 | g_Data->Memory->NumberOfPages = pageCount; 205 | g_Data->Memory->NumberOfRuns = runsCount; 206 | 207 | runsCount = 0; 208 | for (PPHYSICAL_MEMORY_RANGE pRange = pBaseRange; pRange->BaseAddress.QuadPart != 0; pRange++, runsCount++) 209 | { 210 | g_Data->Memory->Run[runsCount].BasePage = PFN( pRange->BaseAddress.QuadPart ); 211 | g_Data->Memory->Run[runsCount].PageCount = PFN( pRange->NumberOfBytes.QuadPart ); 212 | } 213 | 214 | // APIC and other hardcoded stuff 215 | g_Data->Memory->Run[runsCount].BasePage = apic.Fields.Apic_base; 216 | g_Data->Memory->Run[runsCount].PageCount = 1; 217 | g_Data->Memory->Run[runsCount + 1].BasePage = PFN( 0xF0000000 ); 218 | g_Data->Memory->Run[runsCount + 1].PageCount = 0x10000; 219 | 220 | ExFreePool( pBaseRange ); 221 | return STATUS_SUCCESS; 222 | } 223 | 224 | ExFreePool( pBaseRange ); 225 | return STATUS_UNSUCCESSFUL; 226 | } 227 | 228 | /// 229 | /// Change protection of nonpaged system address 230 | /// 231 | /// Address 232 | /// Size of region 233 | /// New protection flags 234 | /// Status code 235 | NTSTATUS UtilProtectNonpagedMemory( IN PVOID ptr, IN ULONG64 size, IN ULONG protection ) 236 | { 237 | NTSTATUS status = STATUS_SUCCESS; 238 | PMDL pMdl = IoAllocateMdl( ptr, (ULONG)size, FALSE, FALSE, NULL ); 239 | if (pMdl) 240 | { 241 | MmBuildMdlForNonPagedPool( pMdl ); 242 | pMdl->MdlFlags |= MDL_MAPPED_TO_SYSTEM_VA; 243 | status = MmProtectMdlSystemAddress( pMdl, protection ); 244 | IoFreeMdl( pMdl ); 245 | return status; 246 | } 247 | 248 | return STATUS_UNSUCCESSFUL; 249 | } 250 | 251 | /// 252 | /// Search for pattern 253 | /// 254 | /// Pattern to search for 255 | /// Used wildcard 256 | /// Pattern length 257 | /// Base address for searching 258 | /// Address range to search in 259 | /// Found location 260 | /// Status code 261 | NTSTATUS UtilSearchPattern( IN PCUCHAR pattern, IN UCHAR wildcard, IN ULONG_PTR len, IN const VOID* base, IN ULONG_PTR size, OUT PVOID* ppFound ) 262 | { 263 | NT_ASSERT( ppFound != NULL && pattern != NULL && base != NULL ); 264 | if (ppFound == NULL || pattern == NULL || base == NULL) 265 | return STATUS_INVALID_PARAMETER; 266 | 267 | __try 268 | { 269 | for (ULONG_PTR i = 0; i < size - len; i++) 270 | { 271 | BOOLEAN found = TRUE; 272 | for (ULONG_PTR j = 0; j < len; j++) 273 | { 274 | if (pattern[j] != wildcard && pattern[j] != ((PCUCHAR)base)[i + j]) 275 | { 276 | found = FALSE; 277 | break; 278 | } 279 | } 280 | 281 | if (found != FALSE) 282 | { 283 | *ppFound = (PUCHAR)base + i; 284 | return STATUS_SUCCESS; 285 | } 286 | } 287 | } 288 | __except (EXCEPTION_EXECUTE_HANDLER) 289 | { 290 | return STATUS_UNHANDLED_EXCEPTION; 291 | } 292 | 293 | return STATUS_NOT_FOUND; 294 | } 295 | 296 | /// 297 | /// Find pattern in kernel PE section 298 | /// 299 | /// Section name 300 | /// Pattern data 301 | /// Pattern wildcard symbol 302 | /// Pattern length 303 | /// Found address 304 | /// Status code 305 | NTSTATUS UtilScanSection( IN PCCHAR section, IN PCUCHAR pattern, IN UCHAR wildcard, IN ULONG_PTR len, OUT PVOID* ppFound ) 306 | { 307 | NT_ASSERT( ppFound != NULL ); 308 | if (ppFound == NULL) 309 | return STATUS_INVALID_PARAMETER; 310 | 311 | PVOID base = UtilKernelBase( NULL ); 312 | if (!base) 313 | return STATUS_NOT_FOUND; 314 | 315 | PIMAGE_NT_HEADERS64 pHdr = RtlImageNtHeader( base ); 316 | if (!pHdr) 317 | return STATUS_INVALID_IMAGE_FORMAT; 318 | 319 | PIMAGE_SECTION_HEADER pFirstSection = (PIMAGE_SECTION_HEADER)(pHdr + 1); 320 | for (PIMAGE_SECTION_HEADER pSection = pFirstSection; pSection < pFirstSection + pHdr->FileHeader.NumberOfSections; pSection++) 321 | { 322 | ANSI_STRING s1, s2; 323 | RtlInitAnsiString( &s1, section ); 324 | RtlInitAnsiString( &s2, (PCCHAR)pSection->Name ); 325 | if (RtlCompareString( &s1, &s2, TRUE ) == 0) 326 | return UtilSearchPattern( pattern, wildcard, len, (PUCHAR)base + pSection->VirtualAddress, pSection->Misc.VirtualSize, ppFound ); 327 | } 328 | 329 | return STATUS_NOT_FOUND; 330 | } -------------------------------------------------------------------------------- /VT_demo/Include/PE.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | #include 3 | 4 | 5 | #define IMAGE_DOS_SIGNATURE 0x5A4D // MZ 6 | #define IMAGE_NT_SIGNATURE 0x00004550 // PE00 7 | 8 | #define IMAGE_NT_OPTIONAL_HDR32_MAGIC 0x10b 9 | #define IMAGE_NT_OPTIONAL_HDR64_MAGIC 0x20b 10 | 11 | #define IMAGE_NUMBEROF_DIRECTORY_ENTRIES 16 12 | 13 | #define IMAGE_DIRECTORY_ENTRY_EXPORT 0 // Export Directory 14 | #define IMAGE_DIRECTORY_ENTRY_IMPORT 1 // Import Directory 15 | #define IMAGE_DIRECTORY_ENTRY_RESOURCE 2 // Resource Directory 16 | #define IMAGE_DIRECTORY_ENTRY_EXCEPTION 3 // Exception Directory 17 | #define IMAGE_DIRECTORY_ENTRY_SECURITY 4 // Security Directory 18 | #define IMAGE_DIRECTORY_ENTRY_BASERELOC 5 // Base Relocation Table 19 | #define IMAGE_DIRECTORY_ENTRY_DEBUG 6 // Debug Directory 20 | // IMAGE_DIRECTORY_ENTRY_COPYRIGHT 7 // (X86 usage) 21 | #define IMAGE_DIRECTORY_ENTRY_ARCHITECTURE 7 // Architecture Specific Data 22 | #define IMAGE_DIRECTORY_ENTRY_GLOBALPTR 8 // RVA of GP 23 | #define IMAGE_DIRECTORY_ENTRY_TLS 9 // TLS Directory 24 | #define IMAGE_DIRECTORY_ENTRY_LOAD_CONFIG 10 // Load Configuration Directory 25 | #define IMAGE_DIRECTORY_ENTRY_BOUND_IMPORT 11 // Bound Import Directory in headers 26 | #define IMAGE_DIRECTORY_ENTRY_IAT 12 // Import Address Table 27 | #define IMAGE_DIRECTORY_ENTRY_DELAY_IMPORT 13 // Delay Load Import Descriptors 28 | #define IMAGE_DIRECTORY_ENTRY_COM_DESCRIPTOR 14 // COM Runtime descriptor 29 | 30 | #define IMAGE_REL_BASED_ABSOLUTE 0 31 | #define IMAGE_REL_BASED_HIGH 1 32 | #define IMAGE_REL_BASED_LOW 2 33 | #define IMAGE_REL_BASED_HIGHLOW 3 34 | #define IMAGE_REL_BASED_HIGHADJ 4 35 | #define IMAGE_REL_BASED_MIPS_JMPADDR 5 36 | #define IMAGE_REL_BASED_SECTION 6 37 | #define IMAGE_REL_BASED_REL32 7 38 | #define IMAGE_REL_BASED_MIPS_JMPADDR16 9 39 | #define IMAGE_REL_BASED_IA64_IMM64 9 40 | #define IMAGE_REL_BASED_DIR64 10 41 | 42 | #define IMAGE_SIZEOF_BASE_RELOCATION 8 43 | 44 | 45 | #define IMAGE_FILE_RELOCS_STRIPPED 0x0001 // Relocation info stripped from file. 46 | #define IMAGE_FILE_EXECUTABLE_IMAGE 0x0002 // File is executable (i.e. no unresolved external references). 47 | #define IMAGE_FILE_LINE_NUMS_STRIPPED 0x0004 // Line nunbers stripped from file. 48 | #define IMAGE_FILE_LOCAL_SYMS_STRIPPED 0x0008 // Local symbols stripped from file. 49 | #define IMAGE_FILE_AGGRESIVE_WS_TRIM 0x0010 // Aggressively trim working set 50 | #define IMAGE_FILE_LARGE_ADDRESS_AWARE 0x0020 // App can handle >2gb addresses 51 | #define IMAGE_FILE_BYTES_REVERSED_LO 0x0080 // Bytes of machine word are reversed. 52 | #define IMAGE_FILE_32BIT_MACHINE 0x0100 // 32 bit word machine. 53 | #define IMAGE_FILE_DEBUG_STRIPPED 0x0200 // Debugging info stripped from file in .DBG file 54 | #define IMAGE_FILE_REMOVABLE_RUN_FROM_SWAP 0x0400 // If Image is on removable media, copy and run from the swap file. 55 | #define IMAGE_FILE_NET_RUN_FROM_SWAP 0x0800 // If Image is on Net, copy and run from the swap file. 56 | #define IMAGE_FILE_SYSTEM 0x1000 // System File. 57 | #define IMAGE_FILE_DLL 0x2000 // File is a DLL. 58 | #define IMAGE_FILE_UP_SYSTEM_ONLY 0x4000 // File should only be run on a UP machine 59 | #define IMAGE_FILE_BYTES_REVERSED_HI 0x8000 // Bytes of machine word are reversed. 60 | 61 | #define IMAGE_FILE_MACHINE_UNKNOWN 0 62 | #define IMAGE_FILE_MACHINE_I386 0x014c // Intel 386. 63 | #define IMAGE_FILE_MACHINE_R3000 0x0162 // MIPS little-endian, 0x160 big-endian 64 | #define IMAGE_FILE_MACHINE_R4000 0x0166 // MIPS little-endian 65 | #define IMAGE_FILE_MACHINE_R10000 0x0168 // MIPS little-endian 66 | #define IMAGE_FILE_MACHINE_WCEMIPSV2 0x0169 // MIPS little-endian WCE v2 67 | #define IMAGE_FILE_MACHINE_ALPHA 0x0184 // Alpha_AXP 68 | #define IMAGE_FILE_MACHINE_SH3 0x01a2 // SH3 little-endian 69 | #define IMAGE_FILE_MACHINE_SH3DSP 0x01a3 70 | #define IMAGE_FILE_MACHINE_SH3E 0x01a4 // SH3E little-endian 71 | #define IMAGE_FILE_MACHINE_SH4 0x01a6 // SH4 little-endian 72 | #define IMAGE_FILE_MACHINE_SH5 0x01a8 // SH5 73 | #define IMAGE_FILE_MACHINE_ARM 0x01c0 // ARM Little-Endian 74 | #define IMAGE_FILE_MACHINE_THUMB 0x01c2 // ARM Thumb/Thumb-2 Little-Endian 75 | #define IMAGE_FILE_MACHINE_ARMNT 0x01c4 // ARM Thumb-2 Little-Endian 76 | #define IMAGE_FILE_MACHINE_AM33 0x01d3 77 | #define IMAGE_FILE_MACHINE_POWERPC 0x01F0 // IBM PowerPC Little-Endian 78 | #define IMAGE_FILE_MACHINE_POWERPCFP 0x01f1 79 | #define IMAGE_FILE_MACHINE_IA64 0x0200 // Intel 64 80 | #define IMAGE_FILE_MACHINE_MIPS16 0x0266 // MIPS 81 | #define IMAGE_FILE_MACHINE_ALPHA64 0x0284 // ALPHA64 82 | #define IMAGE_FILE_MACHINE_MIPSFPU 0x0366 // MIPS 83 | #define IMAGE_FILE_MACHINE_MIPSFPU16 0x0466 // MIPS 84 | #define IMAGE_FILE_MACHINE_AXP64 IMAGE_FILE_MACHINE_ALPHA64 85 | #define IMAGE_FILE_MACHINE_TRICORE 0x0520 // Infineon 86 | #define IMAGE_FILE_MACHINE_CEF 0x0CEF 87 | #define IMAGE_FILE_MACHINE_EBC 0x0EBC // EFI Byte Code 88 | #define IMAGE_FILE_MACHINE_AMD64 0x8664 // AMD64 (K8) 89 | #define IMAGE_FILE_MACHINE_M32R 0x9041 // M32R little-endian 90 | #define IMAGE_FILE_MACHINE_CEE 0xC0EE 91 | 92 | #define IMAGE_ORDINAL_FLAG64 0x8000000000000000 93 | #define IMAGE_ORDINAL_FLAG32 0x80000000 94 | #define IMAGE_ORDINAL64(Ordinal) (Ordinal & 0xffff) 95 | #define IMAGE_ORDINAL32(Ordinal) (Ordinal & 0xffff) 96 | #define IMAGE_SNAP_BY_ORDINAL64(Ordinal) ((Ordinal & IMAGE_ORDINAL_FLAG64) != 0) 97 | #define IMAGE_SNAP_BY_ORDINAL32(Ordinal) ((Ordinal & IMAGE_ORDINAL_FLAG32) != 0) 98 | 99 | // 100 | // Section characteristics. 101 | // 102 | // IMAGE_SCN_TYPE_REG 0x00000000 // Reserved. 103 | // IMAGE_SCN_TYPE_DSECT 0x00000001 // Reserved. 104 | // IMAGE_SCN_TYPE_NOLOAD 0x00000002 // Reserved. 105 | // IMAGE_SCN_TYPE_GROUP 0x00000004 // Reserved. 106 | #define IMAGE_SCN_TYPE_NO_PAD 0x00000008 // Reserved. 107 | // IMAGE_SCN_TYPE_COPY 0x00000010 // Reserved. 108 | 109 | #define IMAGE_SCN_CNT_CODE 0x00000020 // Section contains code. 110 | #define IMAGE_SCN_CNT_INITIALIZED_DATA 0x00000040 // Section contains initialized data. 111 | #define IMAGE_SCN_CNT_UNINITIALIZED_DATA 0x00000080 // Section contains uninitialized data. 112 | 113 | #define IMAGE_SCN_LNK_OTHER 0x00000100 // Reserved. 114 | #define IMAGE_SCN_LNK_INFO 0x00000200 // Section contains comments or some other type of information. 115 | // IMAGE_SCN_TYPE_OVER 0x00000400 // Reserved. 116 | #define IMAGE_SCN_LNK_REMOVE 0x00000800 // Section contents will not become part of image. 117 | #define IMAGE_SCN_LNK_COMDAT 0x00001000 // Section contents comdat. 118 | // 0x00002000 // Reserved. 119 | // IMAGE_SCN_MEM_PROTECTED - Obsolete 0x00004000 120 | #define IMAGE_SCN_NO_DEFER_SPEC_EXC 0x00004000 // Reset speculative exceptions handling bits in the TLB entries for this section. 121 | #define IMAGE_SCN_GPREL 0x00008000 // Section content can be accessed relative to GP 122 | #define IMAGE_SCN_MEM_FARDATA 0x00008000 123 | // IMAGE_SCN_MEM_SYSHEAP - Obsolete 0x00010000 124 | #define IMAGE_SCN_MEM_PURGEABLE 0x00020000 125 | #define IMAGE_SCN_MEM_16BIT 0x00020000 126 | #define IMAGE_SCN_MEM_LOCKED 0x00040000 127 | #define IMAGE_SCN_MEM_PRELOAD 0x00080000 128 | 129 | #define IMAGE_SCN_ALIGN_1BYTES 0x00100000 // 130 | #define IMAGE_SCN_ALIGN_2BYTES 0x00200000 // 131 | #define IMAGE_SCN_ALIGN_4BYTES 0x00300000 // 132 | #define IMAGE_SCN_ALIGN_8BYTES 0x00400000 // 133 | #define IMAGE_SCN_ALIGN_16BYTES 0x00500000 // Default alignment if no others are specified. 134 | #define IMAGE_SCN_ALIGN_32BYTES 0x00600000 // 135 | #define IMAGE_SCN_ALIGN_64BYTES 0x00700000 // 136 | #define IMAGE_SCN_ALIGN_128BYTES 0x00800000 // 137 | #define IMAGE_SCN_ALIGN_256BYTES 0x00900000 // 138 | #define IMAGE_SCN_ALIGN_512BYTES 0x00A00000 // 139 | #define IMAGE_SCN_ALIGN_1024BYTES 0x00B00000 // 140 | #define IMAGE_SCN_ALIGN_2048BYTES 0x00C00000 // 141 | #define IMAGE_SCN_ALIGN_4096BYTES 0x00D00000 // 142 | #define IMAGE_SCN_ALIGN_8192BYTES 0x00E00000 // 143 | // Unused 0x00F00000 144 | #define IMAGE_SCN_ALIGN_MASK 0x00F00000 145 | 146 | #define IMAGE_SCN_LNK_NRELOC_OVFL 0x01000000 // Section contains extended relocations. 147 | #define IMAGE_SCN_MEM_DISCARDABLE 0x02000000 // Section can be discarded. 148 | #define IMAGE_SCN_MEM_NOT_CACHED 0x04000000 // Section is not cachable. 149 | #define IMAGE_SCN_MEM_NOT_PAGED 0x08000000 // Section is not pageable. 150 | #define IMAGE_SCN_MEM_SHARED 0x10000000 // Section is shareable. 151 | #define IMAGE_SCN_MEM_EXECUTE 0x20000000 // Section is executable. 152 | #define IMAGE_SCN_MEM_READ 0x40000000 // Section is readable. 153 | #define IMAGE_SCN_MEM_WRITE 0x80000000 // Section is writeable. 154 | 155 | 156 | typedef struct _IMAGE_FILE_HEADER // Size=20 157 | { 158 | USHORT Machine; 159 | USHORT NumberOfSections; 160 | ULONG TimeDateStamp; 161 | ULONG PointerToSymbolTable; 162 | ULONG NumberOfSymbols; 163 | USHORT SizeOfOptionalHeader; 164 | USHORT Characteristics; 165 | } IMAGE_FILE_HEADER, *PIMAGE_FILE_HEADER; 166 | 167 | typedef struct _IMAGE_SECTION_HEADER 168 | { 169 | UCHAR Name[8]; 170 | union 171 | { 172 | ULONG PhysicalAddress; 173 | ULONG VirtualSize; 174 | } Misc; 175 | ULONG VirtualAddress; 176 | ULONG SizeOfRawData; 177 | ULONG PointerToRawData; 178 | ULONG PointerToRelocations; 179 | ULONG PointerToLinenumbers; 180 | USHORT NumberOfRelocations; 181 | USHORT NumberOfLinenumbers; 182 | ULONG Characteristics; 183 | } IMAGE_SECTION_HEADER, *PIMAGE_SECTION_HEADER; 184 | 185 | typedef struct _IMAGE_DATA_DIRECTORY 186 | { 187 | ULONG VirtualAddress; 188 | ULONG Size; 189 | } IMAGE_DATA_DIRECTORY, *PIMAGE_DATA_DIRECTORY; 190 | 191 | typedef struct _IMAGE_OPTIONAL_HEADER64 192 | { 193 | USHORT Magic; 194 | UCHAR MajorLinkerVersion; 195 | UCHAR MinorLinkerVersion; 196 | ULONG SizeOfCode; 197 | ULONG SizeOfInitializedData; 198 | ULONG SizeOfUninitializedData; 199 | ULONG AddressOfEntryPoint; 200 | ULONG BaseOfCode; 201 | ULONGLONG ImageBase; 202 | ULONG SectionAlignment; 203 | ULONG FileAlignment; 204 | USHORT MajorOperatingSystemVersion; 205 | USHORT MinorOperatingSystemVersion; 206 | USHORT MajorImageVersion; 207 | USHORT MinorImageVersion; 208 | USHORT MajorSubsystemVersion; 209 | USHORT MinorSubsystemVersion; 210 | ULONG Win32VersionValue; 211 | ULONG SizeOfImage; 212 | ULONG SizeOfHeaders; 213 | ULONG CheckSum; 214 | USHORT Subsystem; 215 | USHORT DllCharacteristics; 216 | ULONGLONG SizeOfStackReserve; 217 | ULONGLONG SizeOfStackCommit; 218 | ULONGLONG SizeOfHeapReserve; 219 | ULONGLONG SizeOfHeapCommit; 220 | ULONG LoaderFlags; 221 | ULONG NumberOfRvaAndSizes; 222 | struct _IMAGE_DATA_DIRECTORY DataDirectory[IMAGE_NUMBEROF_DIRECTORY_ENTRIES]; 223 | } IMAGE_OPTIONAL_HEADER64, *PIMAGE_OPTIONAL_HEADER64; 224 | 225 | typedef struct _IMAGE_NT_HEADERS64 226 | { 227 | ULONG Signature; 228 | struct _IMAGE_FILE_HEADER FileHeader; 229 | struct _IMAGE_OPTIONAL_HEADER64 OptionalHeader; 230 | } IMAGE_NT_HEADERS64, *PIMAGE_NT_HEADERS64; 231 | -------------------------------------------------------------------------------- /VT_demo/Hooks/PageHook.c: -------------------------------------------------------------------------------- 1 | #include "PageHook.h" 2 | #include "../Include/Common.h" 3 | #include "../Arch/Intel/VMX.h" 4 | #include "../Arch/Intel/EPT.h" 5 | #include "../Util/LDasm.h" 6 | 7 | LIST_ENTRY g_PageList = { 0 }; 8 | 9 | typedef struct _HOOK_CONTEXT 10 | { 11 | BOOLEAN Hook; // TRUE to hook page, FALSE to unhook 12 | ULONG64 DataPagePFN; // Physical data page PFN 13 | ULONG64 CodePagePFN; // Physical code page PFN 14 | } HOOK_CONTEXT, *PHOOK_CONTEXT; 15 | 16 | #pragma pack(push, 1) 17 | typedef struct _JUMP_THUNK 18 | { 19 | UCHAR PushOp; // 0x68 20 | ULONG AddressLow; // 21 | ULONG MovOp; // 0x042444C7 22 | ULONG AddressHigh; // 23 | UCHAR RetOp; // 0xC3 24 | } JUMP_THUNK, *PJUMP_THUNK; 25 | #pragma pack(pop) 26 | 27 | /// 28 | /// Construct jump 29 | /// 30 | /// Data to initialize 31 | /// Address of jump 32 | VOID PHpInitJumpThunk( IN OUT PJUMP_THUNK pThunk, IN ULONG64 To ) 33 | { 34 | PULARGE_INTEGER liTo = (PULARGE_INTEGER)&To; 35 | 36 | pThunk->PushOp = 0x68; 37 | pThunk->AddressLow = liTo->LowPart; 38 | pThunk->MovOp = 0x042444C7; 39 | pThunk->AddressHigh = liTo->HighPart; 40 | pThunk->RetOp = 0xC3; 41 | } 42 | 43 | /// 44 | /// Per-CPU page hook/unhook routine 45 | /// 46 | /// Unused 47 | /// Valid PHOOK_CONTEXT 48 | /// Unused 49 | /// Unused 50 | VOID PHpHookCallbackDPC( IN PRKDPC Dpc, IN PVOID Context, IN PVOID SystemArgument1, IN PVOID SystemArgument2 ) 51 | { 52 | UNREFERENCED_PARAMETER( Dpc ); 53 | PHOOK_CONTEXT pCTX = (PHOOK_CONTEXT)Context; 54 | 55 | if (pCTX != NULL) 56 | __vmx_vmcall( pCTX->Hook ? HYPERCALL_HOOK_PAGE : HYPERCALL_UNHOOK_PAGE, pCTX->DataPagePFN, pCTX->CodePagePFN, 0 ); 57 | 58 | KeSignalCallDpcSynchronize( SystemArgument2 ); 59 | KeSignalCallDpcDone( SystemArgument1 ); 60 | } 61 | 62 | /// 63 | /// Copy original bytes using LDASM 64 | /// 65 | /// Original function ptr 66 | /// Buffer to store bytes 67 | /// Lenght of copied data 68 | /// Status code 69 | NTSTATUS PHpCopyCode( IN PVOID pFunc, OUT PUCHAR OriginalStore, OUT PULONG pSize ) 70 | { 71 | // Store original bytes 72 | PUCHAR src = pFunc; 73 | PUCHAR old = OriginalStore; 74 | ULONG all_len = 0; 75 | ldasm_data ld = { 0 }; 76 | 77 | do 78 | { 79 | ULONG len = ldasm( src, &ld, TRUE ); 80 | 81 | // Determine code end 82 | if (ld.flags & F_INVALID 83 | || (len == 1 && (src[ld.opcd_offset] == 0xCC || src[ld.opcd_offset] == 0xC3)) 84 | || (len == 3 && src[ld.opcd_offset] == 0xC2) 85 | || len + all_len > 128) 86 | { 87 | break; 88 | } 89 | 90 | // move instruction 91 | memcpy( old, src, len ); 92 | 93 | // if instruction has relative offset, calculate new offset 94 | if (ld.flags & F_RELATIVE) 95 | { 96 | LONG diff = 0; 97 | const uintptr_t ofst = (ld.disp_offset != 0 ? ld.disp_offset : ld.imm_offset); 98 | const uintptr_t sz = ld.disp_size != 0 ? ld.disp_size : ld.imm_size; 99 | 100 | memcpy( &diff, src + ofst, sz ); 101 | // exit if jump is greater then 2GB 102 | if (_abs64( src + len + diff - old ) > INT_MAX) 103 | { 104 | break; 105 | } 106 | else 107 | { 108 | diff += (LONG)(src - old); 109 | memcpy( old + ofst, &diff, sz ); 110 | } 111 | } 112 | 113 | src += len; 114 | old += len; 115 | all_len += len; 116 | 117 | } while (all_len < sizeof( JUMP_THUNK )); 118 | 119 | // Failed to copy old code, use backup plan 120 | if (all_len < sizeof( JUMP_THUNK )) 121 | { 122 | return STATUS_UNSUCCESSFUL; 123 | } 124 | else 125 | { 126 | PHpInitJumpThunk( (PJUMP_THUNK)old, (ULONG64)src ); 127 | *pSize = all_len; 128 | } 129 | 130 | return STATUS_SUCCESS; 131 | } 132 | 133 | /// 134 | /// Hook function 135 | /// 136 | /// Function address 137 | /// Hook address 138 | /// /// Hook type 139 | /// Status code 140 | NTSTATUS PHHook( IN PVOID pFunc, IN PVOID pHook ) 141 | { 142 | PUCHAR CodePage = NULL; 143 | BOOLEAN Newpage = FALSE; 144 | PHYSICAL_ADDRESS phys = { 0 }; 145 | phys.QuadPart = MAXULONG64; 146 | 147 | // No CPU support 148 | if (!g_Data->Features.EPT || !g_Data->Features.ExecOnlyEPT) 149 | return STATUS_NOT_SUPPORTED; 150 | 151 | // Check if page is already hooked 152 | PPAGE_HOOK_ENTRY pEntry = PHGetHookEntryByPage( pFunc, DATA_PAGE ); 153 | if (pEntry != NULL) 154 | { 155 | CodePage = pEntry->CodePageVA; 156 | } 157 | else 158 | { 159 | CodePage = MmAllocateContiguousMemory( PAGE_SIZE, phys ); 160 | Newpage = TRUE; 161 | } 162 | 163 | if (CodePage == NULL) 164 | return STATUS_INSUFFICIENT_RESOURCES; 165 | 166 | PPAGE_HOOK_ENTRY pHookEntry = ExAllocatePoolWithTag( NonPagedPool, sizeof( PAGE_HOOK_ENTRY ), HB_POOL_TAG ); 167 | if (pHookEntry == NULL) 168 | return STATUS_INSUFFICIENT_RESOURCES; 169 | 170 | RtlZeroMemory( pHookEntry, sizeof( PAGE_HOOK_ENTRY ) ); 171 | RtlCopyMemory( CodePage, PAGE_ALIGN( pFunc ), PAGE_SIZE ); 172 | 173 | // Copy original code 174 | NTSTATUS status = PHpCopyCode( pFunc, pHookEntry->OriginalData, &pHookEntry->OriginalSize ); 175 | if (!NT_SUCCESS( status )) 176 | { 177 | ExFreePoolWithTag( pHookEntry, HB_POOL_TAG ); 178 | return status; 179 | } 180 | 181 | ULONG_PTR page_offset = (ULONG_PTR)pFunc - (ULONG_PTR)PAGE_ALIGN( pFunc ); 182 | 183 | // TODO: atomic memory patching, i.e. with other CPUs spinlocked 184 | JUMP_THUNK thunk = { 0 }; 185 | PHpInitJumpThunk( &thunk, (ULONG64)pHook ); 186 | memcpy( CodePage + page_offset, &thunk, sizeof( thunk ) ); 187 | 188 | pHookEntry->OriginalPtr = pFunc; 189 | pHookEntry->DataPageVA = PAGE_ALIGN( pFunc ); 190 | pHookEntry->DataPagePFN = PFN( MmGetPhysicalAddress( pFunc ).QuadPart ); 191 | pHookEntry->CodePageVA = CodePage; 192 | pHookEntry->CodePagePFN = PFN( MmGetPhysicalAddress( CodePage ).QuadPart ); 193 | 194 | // Add to list 195 | if (g_PageList.Flink == NULL) 196 | InitializeListHead( &g_PageList ); 197 | InsertTailList( &g_PageList, &pHookEntry->Link ); 198 | 199 | // Create EPT page translation 200 | if (Newpage) 201 | { 202 | HOOK_CONTEXT ctx = { 0 }; 203 | ctx.Hook = TRUE; 204 | ctx.DataPagePFN = pHookEntry->DataPagePFN; 205 | ctx.CodePagePFN = pHookEntry->CodePagePFN; 206 | 207 | KeGenericCallDpc( PHpHookCallbackDPC, &ctx ); 208 | } 209 | 210 | return STATUS_SUCCESS; 211 | } 212 | NTSTATUS PHHOOK2(IN PVOID pFunc, IN PVOID code,IN ULONG Size){ 213 | 214 | PUCHAR CodePage = NULL; 215 | BOOLEAN Newpage = FALSE; 216 | PHYSICAL_ADDRESS phys = { 0 }; 217 | phys.QuadPart = MAXULONG64; 218 | 219 | // No CPU support 220 | if (!g_Data->Features.EPT || !g_Data->Features.ExecOnlyEPT) 221 | return STATUS_NOT_SUPPORTED; 222 | 223 | // Check if page is already hooked 224 | PPAGE_HOOK_ENTRY pEntry = PHGetHookEntryByPage(pFunc, DATA_PAGE); 225 | if (pEntry != NULL) 226 | { 227 | CodePage = pEntry->CodePageVA; 228 | } 229 | else 230 | { 231 | CodePage = MmAllocateContiguousMemory(PAGE_SIZE, phys); 232 | Newpage = TRUE; 233 | } 234 | 235 | if (CodePage == NULL) 236 | return STATUS_INSUFFICIENT_RESOURCES; 237 | 238 | PPAGE_HOOK_ENTRY pHookEntry = ExAllocatePoolWithTag(NonPagedPool, sizeof(PAGE_HOOK_ENTRY), HB_POOL_TAG); 239 | if (pHookEntry == NULL) 240 | return STATUS_INSUFFICIENT_RESOURCES; 241 | 242 | RtlZeroMemory(pHookEntry, sizeof(PAGE_HOOK_ENTRY)); 243 | RtlCopyMemory(CodePage, PAGE_ALIGN(pFunc), PAGE_SIZE); 244 | ////////////////// 245 | pHookEntry->OriginalSize = Size; 246 | memcpy(pHookEntry->OriginalData, pFunc,Size); 247 | 248 | ///////////////// 249 | 250 | ULONG_PTR page_offset = (ULONG_PTR)pFunc - (ULONG_PTR)PAGE_ALIGN(pFunc); 251 | 252 | 253 | 254 | memcpy(CodePage + page_offset, code, Size); 255 | pHookEntry->OriginalPtr = pFunc; 256 | pHookEntry->DataPageVA = PAGE_ALIGN(pFunc); 257 | pHookEntry->DataPagePFN = PFN(MmGetPhysicalAddress(pFunc).QuadPart); 258 | pHookEntry->CodePageVA = CodePage; 259 | pHookEntry->CodePagePFN = PFN(MmGetPhysicalAddress(CodePage).QuadPart); 260 | 261 | // Add to list 262 | if (g_PageList.Flink == NULL) 263 | InitializeListHead(&g_PageList); 264 | InsertTailList(&g_PageList, &pHookEntry->Link); 265 | 266 | // Create EPT page translation 267 | if (Newpage) 268 | { 269 | HOOK_CONTEXT ctx = { 0 }; 270 | ctx.Hook = TRUE; 271 | ctx.DataPagePFN = pHookEntry->DataPagePFN; 272 | ctx.CodePagePFN = pHookEntry->CodePagePFN; 273 | 274 | KeGenericCallDpc(PHpHookCallbackDPC, &ctx); 275 | } 276 | 277 | return STATUS_SUCCESS; 278 | } 279 | NTSTATUS PHRestore2(IN PVOID pFunc){ 280 | 281 | } 282 | /// 283 | /// Restore hooked function 284 | /// 285 | /// Function address 286 | /// Status code 287 | NTSTATUS PHRestore( IN PVOID pFunc ) 288 | { 289 | // No CPU support 290 | if (!g_Data->Features.ExecOnlyEPT) 291 | return STATUS_NOT_SUPPORTED; 292 | 293 | PPAGE_HOOK_ENTRY pHookEntry = PHGetHookEntry( pFunc ); 294 | if (pHookEntry == NULL) 295 | return STATUS_NOT_FOUND; 296 | 297 | // Restore original bytes 298 | if (PHPageHookCount( pFunc, DATA_PAGE ) > 1) 299 | { 300 | // TODO: atomic memory patching, i.e. with other CPUs spinlocked 301 | ULONG_PTR page_offset = (ULONG_PTR)pFunc - (ULONG_PTR)PAGE_ALIGN( pFunc ); 302 | memcpy( (PUCHAR)pHookEntry->CodePageVA + page_offset, pHookEntry->OriginalData, pHookEntry->OriginalSize ); 303 | 304 | RemoveEntryList(&pHookEntry->Link); 305 | ExFreePoolWithTag(pHookEntry, HB_POOL_TAG); 306 | return STATUS_SUCCESS; 307 | 308 | } 309 | // Swap pages 310 | else 311 | { 312 | HOOK_CONTEXT ctx = { 0 }; 313 | ctx.Hook = FALSE; 314 | ctx.DataPagePFN = pHookEntry->DataPagePFN; 315 | ctx.CodePagePFN = pHookEntry->CodePagePFN;; 316 | 317 | KeGenericCallDpc( PHpHookCallbackDPC, &ctx ); 318 | } 319 | 320 | MmFreeContiguousMemory(pHookEntry->CodePageVA); 321 | RemoveEntryList(&pHookEntry->Link); 322 | ExFreePoolWithTag(pHookEntry, HB_POOL_TAG); 323 | 324 | return STATUS_SUCCESS; 325 | } 326 | 327 | /// 328 | /// Get hook data by function pointer 329 | /// 330 | /// Function address 331 | /// Found entry or NULL 332 | PPAGE_HOOK_ENTRY PHGetHookEntry( IN PVOID ptr ) 333 | { 334 | if (g_PageList.Flink == NULL || IsListEmpty( &g_PageList )) 335 | return NULL; 336 | 337 | for (PLIST_ENTRY pListEntry = g_PageList.Flink; pListEntry != &g_PageList; pListEntry = pListEntry->Flink) 338 | { 339 | PPAGE_HOOK_ENTRY pEntry = CONTAINING_RECORD( pListEntry, PAGE_HOOK_ENTRY, Link ); 340 | if (pEntry->OriginalPtr == ptr) 341 | return pEntry; 342 | } 343 | 344 | return NULL; 345 | } 346 | 347 | /// 348 | /// Get number of hooks in one page 349 | /// 350 | /// Function address 351 | /// Page type 352 | /// Number of hooks 353 | ULONG PHPageHookCount( IN PVOID ptr, IN PAGE_TYPE Type ) 354 | { 355 | ULONG count = 0; 356 | if (g_PageList.Flink == NULL || IsListEmpty( &g_PageList )) 357 | return count; 358 | 359 | PVOID page = PAGE_ALIGN( ptr ); 360 | for (PLIST_ENTRY pListEntry = g_PageList.Flink; pListEntry != &g_PageList; pListEntry = pListEntry->Flink) 361 | { 362 | PPAGE_HOOK_ENTRY pEntry = CONTAINING_RECORD( pListEntry, PAGE_HOOK_ENTRY, Link ); 363 | if ((Type == DATA_PAGE && pEntry->DataPageVA == page) || (Type == CODE_PAGE && pEntry->CodePageVA == page)) 364 | count++; 365 | } 366 | 367 | return count; 368 | } 369 | 370 | /// 371 | /// Get hook data by page address 372 | /// 373 | /// Function pointer 374 | /// Page type 375 | /// Found hook entry or NULL 376 | PPAGE_HOOK_ENTRY PHGetHookEntryByPage( IN PVOID ptr, IN PAGE_TYPE Type ) 377 | { 378 | if (g_PageList.Flink == NULL || IsListEmpty( &g_PageList )) 379 | return NULL; 380 | 381 | PVOID page = PAGE_ALIGN( ptr ); 382 | for (PLIST_ENTRY pListEntry = g_PageList.Flink; pListEntry != &g_PageList; pListEntry = pListEntry->Flink) 383 | { 384 | PPAGE_HOOK_ENTRY pEntry = CONTAINING_RECORD( pListEntry, PAGE_HOOK_ENTRY, Link ); 385 | if ((Type == DATA_PAGE && pEntry->DataPageVA == page) || (Type == CODE_PAGE && pEntry->CodePageVA == page)) 386 | return pEntry; 387 | } 388 | 389 | return NULL; 390 | } 391 | 392 | /// 393 | /// Get hook data by Physical page frame number 394 | /// 395 | /// PFN 396 | /// Page type 397 | /// Found hook entry or NULL 398 | PPAGE_HOOK_ENTRY PHGetHookEntryByPFN( IN ULONG64 pfn, IN PAGE_TYPE Type ) 399 | { 400 | if (g_PageList.Flink == NULL || IsListEmpty( &g_PageList )) 401 | return NULL; 402 | 403 | for (PLIST_ENTRY pListEntry = g_PageList.Flink; pListEntry != &g_PageList; pListEntry = pListEntry->Flink) 404 | { 405 | PPAGE_HOOK_ENTRY pEntry = CONTAINING_RECORD( pListEntry, PAGE_HOOK_ENTRY, Link ); 406 | if ((Type == DATA_PAGE && pEntry->DataPagePFN == pfn) || (Type == CODE_PAGE && pEntry->CodePagePFN == pfn)) 407 | return pEntry; 408 | } 409 | 410 | return NULL; 411 | } 412 | 413 | -------------------------------------------------------------------------------- /VT_demo/vmxdebug.c: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright holder: Invisible Things Lab 3 | */ 4 | 5 | #include "vmx.h" 6 | 7 | VOID VmxDumpVmcs () 8 | { 9 | ULONG32 addr; 10 | 11 | KdPrint (("\n/*****16-bit Guest-State Fields*****/\n")); 12 | KdPrint (("GUEST_ES_SELECTOR 0x%X: 0x%llx\n", GUEST_ES_SELECTOR, VmxRead (GUEST_ES_SELECTOR))); 13 | KdPrint (("GUEST_CS_SELECTOR 0x%X: 0x%llx\n", GUEST_CS_SELECTOR, VmxRead (GUEST_CS_SELECTOR))); 14 | KdPrint (("GUEST_SS_SELECTOR 0x%X: 0x%llx\n", GUEST_SS_SELECTOR, VmxRead (GUEST_SS_SELECTOR))); 15 | KdPrint (("GUEST_DS_SELECTOR 0x%X: 0x%llx\n", GUEST_DS_SELECTOR, VmxRead (GUEST_DS_SELECTOR))); 16 | KdPrint (("GUEST_FS_SELECTOR 0x%X: 0x%llx\n", GUEST_FS_SELECTOR, VmxRead (GUEST_FS_SELECTOR))); 17 | KdPrint (("GUEST_GS_SELECTOR 0x%X: 0x%llx\n", GUEST_GS_SELECTOR, VmxRead (GUEST_GS_SELECTOR))); 18 | KdPrint (("GUEST_LDTR_SELECTOR 0x%X: 0x%llx\n", GUEST_LDTR_SELECTOR, VmxRead (GUEST_LDTR_SELECTOR))); 19 | KdPrint (("GUEST_TR_SELECTOR 0x%X: 0x%llx\n", GUEST_TR_SELECTOR, VmxRead (GUEST_TR_SELECTOR))); 20 | 21 | KdPrint (("\n/*****16-bit Host-State Fields*****/\n")); 22 | KdPrint (("HOST_ES_SELECTOR 0x%X: 0x%llx\n", HOST_ES_SELECTOR, VmxRead (HOST_ES_SELECTOR))); 23 | KdPrint (("HOST_CS_SELECTOR 0x%X: 0x%llx\n", HOST_CS_SELECTOR, VmxRead (HOST_CS_SELECTOR))); 24 | KdPrint (("HOST_SS_SELECTOR 0x%X: 0x%llx\n", HOST_SS_SELECTOR, VmxRead (HOST_SS_SELECTOR))); 25 | KdPrint (("HOST_DS_SELECTOR 0x%X: 0x%llx\n", HOST_DS_SELECTOR, VmxRead (HOST_DS_SELECTOR))); 26 | KdPrint (("HOST_FS_SELECTOR 0x%X: 0x%llx\n", HOST_FS_SELECTOR, VmxRead (HOST_FS_SELECTOR))); 27 | KdPrint (("HOST_GS_SELECTOR 0x%X: 0x%llx\n", HOST_GS_SELECTOR, VmxRead (HOST_GS_SELECTOR))); 28 | KdPrint (("HOST_TR_SELECTOR 0x%X: 0x%llx\n", HOST_TR_SELECTOR, VmxRead (HOST_TR_SELECTOR))); 29 | 30 | KdPrint (("\n/*****64-bit Control Fields*****/\n")); 31 | KdPrint (("IO_BITMAP_A 0x%X: 0x%llx\n", IO_BITMAP_A, VmxRead (IO_BITMAP_A))); 32 | KdPrint (("IO_BITMAP_A_HIGH 0x%X: 0x%llx\n", IO_BITMAP_A_HIGH, VmxRead (IO_BITMAP_A_HIGH))); 33 | KdPrint (("IO_BITMAP_B 0x%X: 0x%llx\n", IO_BITMAP_B, VmxRead (IO_BITMAP_B))); 34 | KdPrint (("IO_BITMAP_B_HIGH 0x%X: 0x%llx\n", IO_BITMAP_B_HIGH, VmxRead (IO_BITMAP_B_HIGH))); 35 | // 36 | KdPrint (("MSR_BITMAP 0x%X: 0x%llx\n", MSR_BITMAP, VmxRead (MSR_BITMAP))); 37 | KdPrint (("MSR_BITMAP_HIGH 0x%X: 0x%llx\n", MSR_BITMAP_HIGH, VmxRead (MSR_BITMAP_HIGH))); 38 | // 39 | KdPrint (("VM_EXIT_MSR_STORE_ADDR 0x%X: 0x%llx\n", VM_EXIT_MSR_STORE_ADDR, VmxRead (VM_EXIT_MSR_STORE_ADDR))); 40 | KdPrint (("VM_EXIT_MSR_STORE_ADDR_HIGH 0x%X: 0x%llx\n", VM_EXIT_MSR_STORE_ADDR_HIGH, VmxRead (VM_EXIT_MSR_STORE_ADDR_HIGH))); 41 | KdPrint (("VM_EXIT_MSR_LOAD_ADDR 0x%X: 0x%llx\n", VM_EXIT_MSR_LOAD_ADDR, VmxRead (VM_EXIT_MSR_LOAD_ADDR))); 42 | KdPrint (("VM_EXIT_MSR_LOAD_ADDR_HIGH 0x%X: 0x%llx\n", VM_EXIT_MSR_LOAD_ADDR_HIGH, VmxRead (VM_EXIT_MSR_LOAD_ADDR_HIGH))); 43 | KdPrint (("VM_ENTRY_MSR_LOAD_ADDR 0x%X: 0x%llx\n", VM_ENTRY_MSR_LOAD_ADDR, VmxRead (VM_ENTRY_MSR_LOAD_ADDR))); 44 | KdPrint (("VM_ENTRY_MSR_LOAD_ADDR_HIGH 0x%X: 0x%llx\n", VM_ENTRY_MSR_LOAD_ADDR_HIGH, VmxRead (VM_ENTRY_MSR_LOAD_ADDR_HIGH))); 45 | // 46 | KdPrint (("TSC_OFFSET 0x%X: 0x%llx\n", TSC_OFFSET, VmxRead (TSC_OFFSET))); 47 | KdPrint (("TSC_OFFSET_HIGH 0x%X: 0x%llx\n", TSC_OFFSET_HIGH, VmxRead (TSC_OFFSET_HIGH))); 48 | // 49 | KdPrint (("VIRTUAL_APIC_PAGE_ADDR 0x%X: 0x%llx\n", VIRTUAL_APIC_PAGE_ADDR, VmxRead (VIRTUAL_APIC_PAGE_ADDR))); 50 | KdPrint (("VIRTUAL_APIC_PAGE_ADDR_HIGH 0x%X: 0x%llx\n", VIRTUAL_APIC_PAGE_ADDR_HIGH, VmxRead (VIRTUAL_APIC_PAGE_ADDR_HIGH))); 51 | 52 | KdPrint (("\n/*****64-bit Guest-State Fields*****/\n")); 53 | KdPrint (("VMCS_LINK_POINTER 0x%X: 0x%llx\n", VMCS_LINK_POINTER, VmxRead (VMCS_LINK_POINTER))); 54 | KdPrint (("VMCS_LINK_POINTER_HIGH 0x%X: 0x%llx\n", VMCS_LINK_POINTER_HIGH, VmxRead (VMCS_LINK_POINTER_HIGH))); 55 | KdPrint (("GUEST_IA32_DEBUGCTL 0x%X: 0x%llx\n", GUEST_IA32_DEBUGCTL, VmxRead (GUEST_IA32_DEBUGCTL))); 56 | KdPrint (("GUEST_IA32_DEBUGCTL_HIGH 0x%X: 0x%llx\n", GUEST_IA32_DEBUGCTL_HIGH, VmxRead (GUEST_IA32_DEBUGCTL_HIGH))); 57 | 58 | KdPrint (("\n/*****32-bit Control Fields*****/\n")); 59 | KdPrint (("PIN_BASED_VM_EXEC_CONTROL 0x%X: 0x%llx\n", PIN_BASED_VM_EXEC_CONTROL, VmxRead (PIN_BASED_VM_EXEC_CONTROL))); 60 | addr = CPU_BASED_VM_EXEC_CONTROL; 61 | KdPrint (("CPU_BASED_VM_EXEC_CONTROL 0x%X: 0x%llx\n", addr, VmxRead (addr))); 62 | addr = EXCEPTION_BITMAP; 63 | KdPrint (("EXCEPTION_BITMAP 0x%X: 0x%llx\n", addr, VmxRead (addr))); 64 | addr = PAGE_FAULT_ERROR_CODE_MASK; 65 | KdPrint (("PAGE_FAULT_ERROR_CODE_MASK 0x%X: 0x%llx\n", addr, VmxRead (addr))); 66 | addr = PAGE_FAULT_ERROR_CODE_MATCH; 67 | KdPrint (("PAGE_FAULT_ERROR_CODE_MATCH 0x%X: 0x%llx\n", addr, VmxRead (addr))); 68 | addr = CR3_TARGET_COUNT; 69 | KdPrint (("CR3_TARGET_COUNT 0x%X: 0x%llx\n", addr, VmxRead (addr))); 70 | addr = VM_EXIT_CONTROLS; 71 | KdPrint (("VM_EXIT_CONTROLS 0x%X: 0x%llx\n", addr, VmxRead (addr))); 72 | addr = VM_EXIT_MSR_STORE_COUNT; 73 | KdPrint (("VM_EXIT_MSR_STORE_COUNT 0x%X: 0x%llx\n", addr, VmxRead (addr))); 74 | addr = VM_EXIT_MSR_LOAD_COUNT; 75 | KdPrint (("VM_EXIT_MSR_LOAD_COUNT 0x%X: 0x%llx\n", addr, VmxRead (addr))); 76 | addr = VM_ENTRY_CONTROLS; 77 | KdPrint (("VM_ENTRY_CONTROLS 0x%X: 0x%llx\n", addr, VmxRead (addr))); 78 | addr = VM_ENTRY_MSR_LOAD_COUNT; 79 | KdPrint (("VM_ENTRY_MSR_LOAD_COUNT 0x%X: 0x%llx\n", addr, VmxRead (addr))); 80 | addr = VM_ENTRY_INTR_INFO_FIELD; 81 | KdPrint (("VM_ENTRY_INTR_INFO_FIELD 0x%X: 0x%llx\n", addr, VmxRead (addr))); 82 | addr = VM_ENTRY_EXCEPTION_ERROR_CODE; 83 | KdPrint (("VM_ENTRY_EXCEPTION_ERROR_CODE 0x%X: 0x%llx\n", addr, VmxRead (addr))); 84 | addr = VM_ENTRY_INSTRUCTION_LEN; 85 | KdPrint (("VM_ENTRY_INSTRUCTION_LEN 0x%X: 0x%llx\n", addr, VmxRead (addr))); 86 | addr = TPR_THRESHOLD; 87 | KdPrint (("TPR_THRESHOLD 0x%X: 0x%llx\n", addr, VmxRead (addr))); 88 | addr = SECONDARY_VM_EXEC_CONTROL; 89 | KdPrint (("SECONDARY_VM_EXEC_CONTROL 0x%X: 0x%llx\n", addr, VmxRead (addr))); 90 | 91 | KdPrint (("\n\n\n/*****32-bit RO Data Fields*****/\n")); 92 | addr = VM_INSTRUCTION_ERROR; 93 | KdPrint (("VM_INSTRUCTION_ERROR 0x%X: 0x%llx\n", addr, VmxRead (addr))); 94 | addr = VM_EXIT_REASON; 95 | KdPrint (("VM_EXIT_REASON 0x%X: 0x%llx\n", addr, VmxRead (addr))); 96 | addr = VM_EXIT_INTR_INFO; 97 | KdPrint (("VM_EXIT_INTR_INFO 0x%X: 0x%llx\n", addr, VmxRead (addr))); 98 | addr = VM_EXIT_INTR_ERROR_CODE; 99 | KdPrint (("VM_EXIT_INTR_ERROR_CODE 0x%X: 0x%llx\n", addr, VmxRead (addr))); 100 | addr = IDT_VECTORING_INFO_FIELD; 101 | KdPrint (("IDT_VECTORING_INFO_FIELD 0x%X: 0x%llx\n", addr, VmxRead (addr))); 102 | addr = IDT_VECTORING_ERROR_CODE; 103 | KdPrint (("IDT_VECTORING_ERROR_CODE 0x%X: 0x%llx\n", addr, VmxRead (addr))); 104 | addr = VM_EXIT_INSTRUCTION_LEN; 105 | KdPrint (("VM_EXIT_INSTRUCTION_LEN 0x%X: 0x%llx\n", addr, VmxRead (addr))); 106 | addr = VMX_INSTRUCTION_INFO; 107 | KdPrint (("VMX_INSTRUCTION_INFO 0x%X: 0x%llx\n", addr, VmxRead (addr))); 108 | 109 | KdPrint (("\n\n\n/*****32-bit Guest-State Fields*****/\n")); 110 | addr = GUEST_ES_LIMIT; 111 | KdPrint (("GUEST_ES_LIMIT 0x%X: 0x%llx\n", addr, VmxRead (addr))); 112 | addr = GUEST_CS_LIMIT; 113 | KdPrint (("GUEST_CS_LIMIT 0x%X: 0x%llx\n", addr, VmxRead (addr))); 114 | addr = GUEST_SS_LIMIT; 115 | KdPrint (("GUEST_SS_LIMIT 0x%X: 0x%llx\n", addr, VmxRead (addr))); 116 | addr = GUEST_DS_LIMIT; 117 | KdPrint (("GUEST_DS_LIMIT 0x%X: 0x%llx\n", addr, VmxRead (addr))); 118 | addr = GUEST_FS_LIMIT; 119 | KdPrint (("GUEST_FS_LIMIT 0x%X: 0x%llx\n", addr, VmxRead (addr))); 120 | addr = GUEST_GS_LIMIT; 121 | KdPrint (("GUEST_GS_LIMIT 0x%X: 0x%llx\n", addr, VmxRead (addr))); 122 | addr = GUEST_LDTR_LIMIT; 123 | KdPrint (("GUEST_LDTR_LIMIT 0x%X: 0x%llx\n", addr, VmxRead (addr))); 124 | addr = GUEST_TR_LIMIT; 125 | KdPrint (("GUEST_TR_LIMIT 0x%X: 0x%llx\n", addr, VmxRead (addr))); 126 | addr = GUEST_GDTR_LIMIT; 127 | KdPrint (("GUEST_GDTR_LIMIT 0x%X: 0x%llx\n", addr, VmxRead (addr))); 128 | addr = GUEST_IDTR_LIMIT; 129 | KdPrint (("GUEST_IDTR_LIMIT 0x%X: 0x%llx\n", addr, VmxRead (addr))); 130 | addr = GUEST_ES_AR_BYTES; 131 | KdPrint (("GUEST_ES_AR_BYTES 0x%X: 0x%llx\n", addr, VmxRead (addr))); 132 | addr = GUEST_CS_AR_BYTES; 133 | KdPrint (("GUEST_CS_AR_BYTES 0x%X: 0x%llx\n", addr, VmxRead (addr))); 134 | addr = GUEST_SS_AR_BYTES; 135 | KdPrint (("GUEST_SS_AR_BYTES 0x%X: 0x%llx\n", addr, VmxRead (addr))); 136 | addr = GUEST_DS_AR_BYTES; 137 | KdPrint (("GUEST_DS_AR_BYTES 0x%X: 0x%llx\n", addr, VmxRead (addr))); 138 | addr = GUEST_FS_AR_BYTES; 139 | KdPrint (("GUEST_FS_AR_BYTES 0x%X: 0x%llx\n", addr, VmxRead (addr))); 140 | addr = GUEST_GS_AR_BYTES; 141 | KdPrint (("GUEST_GS_AR_BYTES 0x%X: 0x%llx\n", addr, VmxRead (addr))); 142 | addr = GUEST_LDTR_AR_BYTES; 143 | KdPrint (("GUEST_LDTR_AR_BYTES 0x%X: 0x%llx\n", addr, VmxRead (addr))); 144 | addr = GUEST_TR_AR_BYTES; 145 | KdPrint (("GUEST_TR_AR_BYTES 0x%X: 0x%llx\n", addr, VmxRead (addr))); 146 | addr = GUEST_INTERRUPTIBILITY_STATE; 147 | KdPrint (("GUEST_INTERRUPTIBILITY_INFO 0x%X: 0x%llx\n", addr, VmxRead (addr))); 148 | addr = GUEST_ACTIVITY_STATE; 149 | KdPrint (("GUEST_ACTIVITY_STATE 0x%X: 0x%llx\n", addr, VmxRead (addr))); 150 | addr = GUEST_SM_BASE; 151 | KdPrint (("GUEST_SM_BASE 0x%X: 0x%llx\n", addr, VmxRead (addr))); 152 | addr = GUEST_SYSENTER_CS; 153 | KdPrint (("GUEST_SYSENTER_CS 0x%X: 0x%llx\n", addr, VmxRead (addr))); 154 | 155 | KdPrint (("\n\n\n/*****32-bit Host-State Fields*****/\n")); 156 | addr = HOST_IA32_SYSENTER_CS; 157 | KdPrint (("HOST_IA32_SYSENTER_CS 0x%X: 0x%llx\n", addr, VmxRead (addr))); 158 | 159 | KdPrint (("\n\n\n/*****Natural 64-bit Control Fields*****/\n")); 160 | addr = CR0_GUEST_HOST_MASK; 161 | KdPrint (("CR0_GUEST_HOST_MASK 0x%X: 0x%llx\n", addr, VmxRead (addr))); 162 | addr = CR4_GUEST_HOST_MASK; 163 | KdPrint (("CR4_GUEST_HOST_MASK 0x%X: 0x%llx\n", addr, VmxRead (addr))); 164 | addr = CR0_READ_SHADOW; 165 | KdPrint (("CR0_READ_SHADOW 0x%X: 0x%llx\n", addr, VmxRead (addr))); 166 | addr = CR4_READ_SHADOW; 167 | KdPrint (("CR4_READ_SHADOW 0x%X: 0x%llx\n", addr, VmxRead (addr))); 168 | addr = CR3_TARGET_VALUE0; 169 | KdPrint (("CR3_TARGET_VALUE0 0x%X: 0x%llx\n", addr, VmxRead (addr))); 170 | addr = CR3_TARGET_VALUE1; 171 | KdPrint (("CR3_TARGET_VALUE1 0x%X: 0x%llx\n", addr, VmxRead (addr))); 172 | addr = CR3_TARGET_VALUE2; 173 | KdPrint (("CR3_TARGET_VALUE2 0x%X: 0x%llx\n", addr, VmxRead (addr))); 174 | addr = CR3_TARGET_VALUE3; 175 | KdPrint (("CR3_TARGET_VALUE3 0x%X: 0x%llx\n", addr, VmxRead (addr))); 176 | 177 | KdPrint (("\n\n\n/*****Natural 64-bit RO Data Fields*****/\n")); 178 | addr = EXIT_QUALIFICATION; 179 | KdPrint (("EXIT_QUALIFICATION 0x%X: 0x%llx\n", addr, VmxRead (addr))); 180 | addr = GUEST_LINEAR_ADDRESS; 181 | KdPrint (("GUEST_LINEAR_ADDRESS 0x%X: 0x%llx\n", addr, VmxRead (addr))); 182 | 183 | KdPrint (("\n\n\n/*****Natural 64-bit Guest-State Fields*****/\n")); 184 | addr = GUEST_CR0; 185 | KdPrint (("GUEST_CR0 0x%X: 0x%llx\n", addr, VmxRead (addr))); 186 | addr = GUEST_CR3; 187 | KdPrint (("GUEST_CR3 0x%X: 0x%llx\n", addr, VmxRead (addr))); 188 | addr = GUEST_CR4; 189 | KdPrint (("GUEST_CR4 0x%X: 0x%llx\n", addr, VmxRead (addr))); 190 | addr = GUEST_ES_BASE; 191 | KdPrint (("GUEST_ES_BASE 0x%X: 0x%llx\n", addr, VmxRead (addr))); 192 | addr = GUEST_CS_BASE; 193 | KdPrint (("GUEST_CS_BASE 0x%X: 0x%llx\n", addr, VmxRead (addr))); 194 | addr = GUEST_SS_BASE; 195 | KdPrint (("GUEST_SS_BASE 0x%X: 0x%llx\n", addr, VmxRead (addr))); 196 | addr = GUEST_DS_BASE; 197 | KdPrint (("GUEST_DS_BASE 0x%X: 0x%llx\n", addr, VmxRead (addr))); 198 | addr = GUEST_FS_BASE; 199 | KdPrint (("GUEST_FS_BASE 0x%X: 0x%llx\n", addr, VmxRead (addr))); 200 | addr = GUEST_GS_BASE; 201 | KdPrint (("GUEST_GS_BASE 0x%X: 0x%llx\n", addr, VmxRead (addr))); 202 | addr = GUEST_LDTR_BASE; 203 | KdPrint (("GUEST_LDTR_BASE 0x%X: 0x%llx\n", addr, VmxRead (addr))); 204 | addr = GUEST_TR_BASE; 205 | KdPrint (("GUEST_TR_BASE 0x%X: 0x%llx\n", addr, VmxRead (addr))); 206 | addr = GUEST_GDTR_BASE; 207 | KdPrint (("GUEST_GDTR_BASE 0x%X: 0x%llx\n", addr, VmxRead (addr))); 208 | addr = GUEST_IDTR_BASE; 209 | KdPrint (("GUEST_IDTR_BASE 0x%X: 0x%llx\n", addr, VmxRead (addr))); 210 | addr = GUEST_DR7; 211 | KdPrint (("GUEST_DR7 0x%X: 0x%llx\n", addr, VmxRead (addr))); 212 | addr = GUEST_RSP; 213 | KdPrint (("GUEST_RSP 0x%X: 0x%llx\n", addr, VmxRead (addr))); 214 | addr = GUEST_RIP; 215 | KdPrint (("GUEST_RIP 0x%X: 0x%llX\n", addr, VmxRead (addr))); 216 | addr = GUEST_RFLAGS; 217 | KdPrint (("GUEST_RFLAGS 0x%X: 0x%llx\n", addr, VmxRead (addr))); 218 | addr = GUEST_PENDING_DBG_EXCEPTIONS; 219 | KdPrint (("GUEST_PENDING_DBG_EXCEPTIONS 0x%X: 0x%llx\n", addr, VmxRead (addr))); 220 | addr = GUEST_SYSENTER_ESP; 221 | KdPrint (("GUEST_SYSENTER_ESP 0x%X: 0x%llx\n", addr, VmxRead (addr))); 222 | addr = GUEST_SYSENTER_EIP; 223 | KdPrint (("GUEST_SYSENTER_EIP 0x%X: 0x%llx\n", addr, VmxRead (addr))); 224 | 225 | KdPrint (("\n\n\n/*****Natural 64-bit Host-State Fields*****/\n")); 226 | addr = HOST_CR0; 227 | KdPrint (("HOST_CR0 0x%X: 0x%llx\n", addr, VmxRead (addr))); 228 | addr = HOST_CR3; 229 | KdPrint (("HOST_CR3 0x%X: 0x%llx\n", addr, VmxRead (addr))); 230 | addr = HOST_CR4; 231 | KdPrint (("HOST_CR4 0x%X: 0x%llx\n", addr, VmxRead (addr))); 232 | addr = HOST_FS_BASE; 233 | KdPrint (("HOST_FS_BASE 0x%X: 0x%llx\n", addr, VmxRead (addr))); 234 | addr = HOST_GS_BASE; 235 | KdPrint (("HOST_GS_BASE 0x%X: 0x%llx\n", addr, VmxRead (addr))); 236 | addr = HOST_TR_BASE; 237 | KdPrint (("HOST_TR_BASE 0x%X: 0x%llx\n", addr, VmxRead (addr))); 238 | addr = HOST_GDTR_BASE; 239 | KdPrint (("HOST_GDTR_BASE 0x%X: 0x%llx\n", addr, VmxRead (addr))); 240 | addr = HOST_IDTR_BASE; 241 | KdPrint (("HOST_IDTR_BASE 0x%X: 0x%llx\n", addr, VmxRead (addr))); 242 | addr = HOST_IA32_SYSENTER_ESP; 243 | KdPrint (("HOST_IA32_SYSENTER_ESP 0x%X: 0x%llx\n", addr, VmxRead (addr))); 244 | addr = HOST_IA32_SYSENTER_EIP; 245 | KdPrint (("HOST_IA32_SYSENTER_EIP 0x%X: 0x%llx\n", addr, VmxRead (addr))); 246 | addr = HOST_RSP; 247 | KdPrint (("HOST_RSP 0x%X: 0x%llx\n", addr, VmxRead (addr))); 248 | addr = HOST_RIP; 249 | KdPrint (("HOST_RIP 0x%X: 0x%llx\n", addr, VmxRead (addr))); 250 | } 251 | --------------------------------------------------------------------------------