added clang format, its 90% ok

merge-requests/2/head
_xeroxz 3 years ago
parent fc46c63445
commit 4832530dfb

@ -0,0 +1,18 @@
---
BasedOnStyle: Microsoft
AlignAfterOpenBracket: Align
AllowAllArgumentsOnNextLine: 'true'
AllowAllParametersOfDeclarationOnNextLine: 'true'
AllowShortIfStatementsOnASingleLine: Never
BreakBeforeBraces: Allman
IndentWidth: '4'
Language: Cpp
NamespaceIndentation: All
SpacesInAngles: 'true'
SpacesInCStyleCastParentheses: 'true'
SpacesInContainerLiterals: 'true'
SpacesInParentheses: 'true'
SpacesInSquareBrackets: 'true'
UseTab: Never
...

@ -1,8 +1,8 @@
#pragma once
#include <map>
#include <Zydis/Zydis.h>
#include <stdexcept>
#include <functional>
#include <map>
#include <stdexcept>
#include <vmutils.h>
namespace vm
@ -34,17 +34,40 @@ namespace vm
}
// taken from ida...
inline u8 __ROL1__(u8 value, int count) { return __ROL__((u8)value, count); }
inline u16 __ROL2__(u16 value, int count) { return __ROL__((u16)value, count); }
inline u32 __ROL4__(u32 value, int count) { return __ROL__((u32)value, count); }
inline u64 __ROL8__(u64 value, int count) { return __ROL__((u64)value, count); }
inline u8 __ROR1__(u8 value, int count) { return __ROL__((u8)value, -count); }
inline u16 __ROR2__(u16 value, int count) { return __ROL__((u16)value, -count); }
inline u32 __ROR4__(u32 value, int count) { return __ROL__((u32)value, -count); }
inline u64 __ROR8__(u64 value, int count) { return __ROL__((u64)value, -count); }
template <typename T>
using transform_t = std::function<T(T, T)>;
inline u8 __ROL1__( u8 value, int count )
{
return __ROL__( ( u8 )value, count );
}
inline u16 __ROL2__( u16 value, int count )
{
return __ROL__( ( u16 )value, count );
}
inline u32 __ROL4__( u32 value, int count )
{
return __ROL__( ( u32 )value, count );
}
inline u64 __ROL8__( u64 value, int count )
{
return __ROL__( ( u64 )value, count );
}
inline u8 __ROR1__( u8 value, int count )
{
return __ROL__( ( u8 )value, -count );
}
inline u16 __ROR2__( u16 value, int count )
{
return __ROL__( ( u16 )value, -count );
}
inline u32 __ROR4__( u32 value, int count )
{
return __ROL__( ( u32 )value, -count );
}
inline u64 __ROR8__( u64 value, int count )
{
return __ROL__( ( u64 )value, -count );
}
template < typename T > using transform_t = std::function< T( T, T ) >;
enum class type
{
@ -59,8 +82,7 @@ namespace vm
using map_t = std::map< transform::type, zydis_decoded_instr_t >;
template < class T >
inline const auto _bswap = [](T a, T b) -> T
{
inline const auto _bswap = []( T a, T b ) -> T {
if constexpr ( std::is_same_v< T, std::uint64_t > )
return _byteswap_uint64( a );
if constexpr ( std::is_same_v< T, std::uint32_t > )
@ -71,39 +93,18 @@ namespace vm
throw std::invalid_argument( "invalid type size..." );
};
template <class T>
inline const auto _add = [](T a, T b) -> T
{
return a + b;
};
template < class T > inline const auto _add = []( T a, T b ) -> T { return a + b; };
template <class T>
inline const auto _xor = [](T a, T b) -> T
{
return a ^ b;
};
template < class T > inline const auto _xor = []( T a, T b ) -> T { return a ^ b; };
template <class T>
inline const auto _sub = [](T a, T b) -> T
{
return a - b;
};
template < class T > inline const auto _sub = []( T a, T b ) -> T { return a - b; };
template <class T>
inline const auto _neg = [](T a, T b) -> T
{
return a * -1;
};
template < class T > inline const auto _neg = []( T a, T b ) -> T { return a * -1; };
template <class T>
inline const auto _not = [](T a, T b) -> T
{
return ~a;
};
template < class T > inline const auto _not = []( T a, T b ) -> T { return ~a; };
template < class T >
inline const auto _ror = [](T a, T b) -> T
{
inline const auto _ror = []( T a, T b ) -> T {
if constexpr ( std::is_same_v< T, std::uint64_t > )
return __ROR8__( a, b );
if constexpr ( std::is_same_v< T, std::uint32_t > )
@ -117,8 +118,7 @@ namespace vm
};
template < class T >
inline const auto _rol = [](T a, T b) -> T
{
inline const auto _rol = []( T a, T b ) -> T {
if constexpr ( std::is_same_v< T, std::uint64_t > )
return __ROL8__( a, b );
if constexpr ( std::is_same_v< T, std::uint32_t > )
@ -131,46 +131,23 @@ namespace vm
throw std::invalid_argument( "invalid type size..." );
};
template <class T>
inline const auto _inc = [](T a, T b) -> T
{
return a + 1;
};
template < class T > inline const auto _inc = []( T a, T b ) -> T { return a + 1; };
template <class T>
inline const auto _dec = [](T a, T b) -> T
{
return a - 1;
};
template < class T > inline const auto _dec = []( T a, T b ) -> T { return a - 1; };
template < class T >
inline std::map<ZydisMnemonic, transform_t<T>> transforms =
{
{ ZYDIS_MNEMONIC_ADD, _add<T> },
{ ZYDIS_MNEMONIC_XOR, _xor<T> },
{ ZYDIS_MNEMONIC_BSWAP, _bswap<T> },
{ ZYDIS_MNEMONIC_SUB, _sub<T>},
{ ZYDIS_MNEMONIC_NEG, _neg<T>},
{ ZYDIS_MNEMONIC_NOT, _not<T>},
{ ZYDIS_MNEMONIC_ROR, _ror<T>},
{ ZYDIS_MNEMONIC_ROL, _rol<T>},
{ ZYDIS_MNEMONIC_INC, _inc<T>},
{ ZYDIS_MNEMONIC_DEC, _dec<T>}
};
inline std::map<ZydisMnemonic, ZydisMnemonic> inverse =
{
{ZYDIS_MNEMONIC_ADD, ZYDIS_MNEMONIC_SUB},
{ZYDIS_MNEMONIC_XOR, ZYDIS_MNEMONIC_XOR},
{ZYDIS_MNEMONIC_BSWAP, ZYDIS_MNEMONIC_BSWAP},
{ZYDIS_MNEMONIC_SUB, ZYDIS_MNEMONIC_ADD},
{ZYDIS_MNEMONIC_NEG, ZYDIS_MNEMONIC_NEG},
{ZYDIS_MNEMONIC_NOT, ZYDIS_MNEMONIC_NOT},
{ZYDIS_MNEMONIC_ROR, ZYDIS_MNEMONIC_ROL},
{ZYDIS_MNEMONIC_ROL, ZYDIS_MNEMONIC_ROR},
{ZYDIS_MNEMONIC_INC, ZYDIS_MNEMONIC_DEC},
{ZYDIS_MNEMONIC_DEC, ZYDIS_MNEMONIC_INC}
};
inline std::map< ZydisMnemonic, transform_t< T > > transforms = {
{ ZYDIS_MNEMONIC_ADD, _add< T > }, { ZYDIS_MNEMONIC_XOR, _xor< T > }, { ZYDIS_MNEMONIC_BSWAP, _bswap< T > },
{ ZYDIS_MNEMONIC_SUB, _sub< T > }, { ZYDIS_MNEMONIC_NEG, _neg< T > }, { ZYDIS_MNEMONIC_NOT, _not< T > },
{ ZYDIS_MNEMONIC_ROR, _ror< T > }, { ZYDIS_MNEMONIC_ROL, _rol< T > }, { ZYDIS_MNEMONIC_INC, _inc< T > },
{ ZYDIS_MNEMONIC_DEC, _dec< T > } };
inline std::map< ZydisMnemonic, ZydisMnemonic > inverse = {
{ ZYDIS_MNEMONIC_ADD, ZYDIS_MNEMONIC_SUB }, { ZYDIS_MNEMONIC_XOR, ZYDIS_MNEMONIC_XOR },
{ ZYDIS_MNEMONIC_BSWAP, ZYDIS_MNEMONIC_BSWAP }, { ZYDIS_MNEMONIC_SUB, ZYDIS_MNEMONIC_ADD },
{ ZYDIS_MNEMONIC_NEG, ZYDIS_MNEMONIC_NEG }, { ZYDIS_MNEMONIC_NOT, ZYDIS_MNEMONIC_NOT },
{ ZYDIS_MNEMONIC_ROR, ZYDIS_MNEMONIC_ROL }, { ZYDIS_MNEMONIC_ROL, ZYDIS_MNEMONIC_ROR },
{ ZYDIS_MNEMONIC_INC, ZYDIS_MNEMONIC_DEC }, { ZYDIS_MNEMONIC_DEC, ZYDIS_MNEMONIC_INC } };
inline void inverse_transforms( transform::map_t &transforms, transform::map_t &inverse )
{
@ -211,8 +188,7 @@ namespace vm
// max size of a and b is 64 bits, a and b is then converted to
// the number of bits in bitsize, the transformation is applied,
// finally the result is converted back to 64bits... zero extended...
inline auto apply(std::uint8_t bitsize, ZydisMnemonic op,
std::uint64_t a, std::uint64_t b) -> std::uint64_t
inline auto apply( std::uint8_t bitsize, ZydisMnemonic op, std::uint64_t a, std::uint64_t b ) -> std::uint64_t
{
switch ( bitsize )
{
@ -231,8 +207,7 @@ namespace vm
inline bool has_imm( zydis_decoded_instr_t *instr )
{
return instr->operand_count > 1 &&
(instr->operands[1].type & ZYDIS_OPERAND_TYPE_IMMEDIATE);
}
}
return instr->operand_count > 1 && ( instr->operands[ 1 ].type & ZYDIS_OPERAND_TYPE_IMMEDIATE );
}
} // namespace transform
} // namespace vm

@ -69,4 +69,4 @@ namespace vmp2
u8 raw[ 0x100 ];
} vsp;
};
}
} // namespace vmp2

@ -11,15 +11,14 @@ namespace vm
namespace instrs
{
// decrypt transformations for encrypted virtual instruction rva...
bool get_rva_decrypt(const zydis_routine_t& vm_entry,
std::vector<zydis_decoded_instr_t>& transform_instrs);
bool get_rva_decrypt( const zydis_routine_t &vm_entry, std::vector< zydis_decoded_instr_t > &transform_instrs );
std::pair<std::uint64_t, std::uint64_t> decrypt_operand(transform::map_t& transforms,
std::uint64_t operand, std::uint64_t rolling_key);
std::pair< std::uint64_t, std::uint64_t > decrypt_operand( transform::map_t &transforms, std::uint64_t operand,
std::uint64_t rolling_key );
std::pair<std::uint64_t, std::uint64_t> encrypt_operand(transform::map_t& transforms,
std::uint64_t operand, std::uint64_t rolling_key);
}
std::pair< std::uint64_t, std::uint64_t > encrypt_operand( transform::map_t &transforms, std::uint64_t operand,
std::uint64_t rolling_key );
} // namespace instrs
namespace handler
{
@ -97,8 +96,8 @@ namespace vm
bool get( zydis_routine_t &vm_entry, zydis_routine_t &vm_handler, std::uintptr_t handler_addr );
// may throw an exception...
bool get_all(std::uintptr_t module_base, std::uintptr_t image_base,
zydis_routine_t& vm_entry, std::uintptr_t* vm_handler_table, std::vector<handler_t>& vm_handlers);
bool get_all( std::uintptr_t module_base, std::uintptr_t image_base, zydis_routine_t &vm_entry,
std::uintptr_t *vm_handler_table, std::vector< handler_t > &vm_handlers );
// can be used on calc_jmp...
bool get_operand_transforms( const zydis_routine_t &vm_handler, transform::map_t &transforms );
@ -111,7 +110,7 @@ namespace vm
std::uint64_t encrypt( zydis_decoded_instr_t &transform_instr, std::uint64_t val );
std::uint64_t decrypt( zydis_decoded_instr_t &transform_instr, std::uint64_t val );
}
} // namespace table
namespace profile
{
@ -149,24 +148,12 @@ namespace vm
extern vm::handler::profile_t readq;
extern vm::handler::profile_t vmexit;
inline std::vector<vm::handler::profile_t*> all =
{
&sregq, &sregdw, &sregw,
&lregq, &lregdw,
&lconstq, &lconstbzxw, &lconstbsxdw, &lconstdwsxq, &lconstwsxq, &lconstdw,
&addq, &adddw,
&shlq, &shldw,
&writeq, &writedw,
&nandq, &nanddw,
&shrq,
&readq,
&mulq,
&pushvsp,
&divq,
&jmp,
&vmexit
};
}
}
}
inline std::vector< vm::handler::profile_t * > all = {
&sregq, &sregdw, &sregw, &lregq, &lregdw, &lconstq, &lconstbzxw,
&lconstbsxdw, &lconstdwsxq, &lconstwsxq, &lconstdw, &addq, &adddw, &shlq,
&shldw, &writeq, &writedw, &nandq, &nanddw,
&shrq, &readq, &mulq, &pushvsp, &divq, &jmp, &vmexit };
} // namespace profile
} // namespace handler
} // namespace vm

@ -1,7 +1,7 @@
#pragma once
#include <vector>
#include <Zydis/Zydis.h>
#include <Zydis/Utils.h>
#include <Zydis/Zydis.h>
#include <vector>
#include <xmmintrin.h>
using u8 = unsigned char;
@ -31,7 +31,7 @@ namespace vm
// converts say... AL to RAX...
zydis_register_t to64( zydis_register_t reg );
bool compare( zydis_register_t a, zydis_register_t b );
}
} // namespace reg
void print( zydis_routine_t &routine );
void print( const zydis_decoded_instr_t &instr );
@ -39,5 +39,5 @@ namespace vm
bool flatten( zydis_routine_t &routine, std::uintptr_t routine_addr, bool keep_jmps = false );
void deobfuscate( zydis_routine_t &routine );
}
}
} // namespace util
} // namespace vm

@ -6,9 +6,8 @@ namespace vm
{
bool get( const zydis_routine_t &vm_entry, zydis_routine_t &calc_jmp )
{
auto result = std::find_if(vm_entry.begin(), vm_entry.end(),
[](const zydis_instr_t& instr_data) -> bool
{
auto result =
std::find_if( vm_entry.begin(), vm_entry.end(), []( const zydis_instr_t &instr_data ) -> bool {
// mov/movsx/movzx rax/eax/ax/al, [rsi]
if ( instr_data.instr.operand_count > 1 &&
( instr_data.instr.mnemonic == ZYDIS_MNEMONIC_MOV ||
@ -20,8 +19,7 @@ namespace vm
instr_data.instr.operands[ 1 ].mem.base == ZYDIS_REGISTER_RSI )
return true;
return false;
}
);
} );
if ( result == vm_entry.end() )
return false;
@ -29,5 +27,5 @@ namespace vm
calc_jmp.insert( calc_jmp.end(), result, vm_entry.end() );
return true;
}
}
}
} // namespace calc_jmp
} // namespace vm

@ -11,9 +11,7 @@ namespace vm
vm::util::deobfuscate( vm_handler );
static const auto calc_jmp_check =
[&](std::uintptr_t addr) -> bool
{
static const auto calc_jmp_check = [ & ]( std::uintptr_t addr ) -> bool {
for ( const auto &[ instr, instr_raw, instr_addr ] : calc_jmp )
if ( instr_addr == addr )
return true;
@ -21,10 +19,7 @@ namespace vm
return false;
};
auto result = std::find_if(
vm_handler.begin(), vm_handler.end(),
[](const zydis_instr_t& instr) -> bool
{
auto result = std::find_if( vm_handler.begin(), vm_handler.end(), []( const zydis_instr_t &instr ) -> bool {
if ( instr.instr.mnemonic == ZYDIS_MNEMONIC_LEA &&
instr.instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RAX &&
instr.instr.operands[ 1 ].mem.base == ZYDIS_REGISTER_RDI &&
@ -32,8 +27,7 @@ namespace vm
return true;
return calc_jmp_check( instr.addr );
}
);
} );
// remove calc_jmp from the vm handler vector...
if ( result != vm_handler.end() )
@ -46,10 +40,7 @@ namespace vm
while ( result != vm_handler.end() )
{
result = std::find_if(
++result, vm_handler.end(),
[](const zydis_instr_t& instr_data) -> bool
{
result = std::find_if( ++result, vm_handler.end(), []( const zydis_instr_t &instr_data ) -> bool {
// mov/movsx/movzx rax/eax/ax/al, [rsi]
if ( instr_data.instr.operand_count > 1 &&
( instr_data.instr.mnemonic == ZYDIS_MNEMONIC_MOV ||
@ -61,8 +52,7 @@ namespace vm
instr_data.instr.operands[ 1 ].mem.base == ZYDIS_REGISTER_RSI )
return true;
return false;
}
);
} );
if ( result != vm_handler.end() )
last = result;
@ -74,8 +64,8 @@ namespace vm
return true;
}
bool get_all(std::uintptr_t module_base, std::uintptr_t image_base,
zydis_routine_t& vm_entry, std::uintptr_t* vm_handler_table, std::vector<vm::handler::handler_t>& vm_handlers)
bool get_all( std::uintptr_t module_base, std::uintptr_t image_base, zydis_routine_t &vm_entry,
std::uintptr_t *vm_handler_table, std::vector< vm::handler::handler_t > &vm_handlers )
{
zydis_decoded_instr_t instr;
if ( !vm::handler::table::get_transform( vm_entry, &instr ) )
@ -87,9 +77,7 @@ namespace vm
for ( auto idx = 0u; idx < 256; ++idx )
{
const auto decrypt_val =
vm::handler::table::decrypt(
instr, vm_handler_table[idx]);
const auto decrypt_val = vm::handler::table::decrypt( instr, vm_handler_table[ idx ] );
handler_t vm_handler;
vm::transform::map_t transforms;
@ -98,11 +86,9 @@ namespace vm
if ( !vm::handler::get( calc_jmp, vm_handler_instrs, ( decrypt_val - image_base ) + module_base ) )
return false;
const auto has_imm =
vm::handler::has_imm(vm_handler_instrs);
const auto has_imm = vm::handler::has_imm( vm_handler_instrs );
const auto imm_size =
vm::handler::imm_size(vm_handler_instrs);
const auto imm_size = vm::handler::imm_size( vm_handler_instrs );
if ( has_imm && !vm::handler::get_operand_transforms( vm_handler_instrs, transforms ) )
return false;
@ -120,10 +106,8 @@ namespace vm
bool has_imm( const zydis_routine_t &vm_handler )
{
const auto result = std::find_if(
vm_handler.begin(), vm_handler.end(),
[](const zydis_instr_t& instr_data) -> bool
{
const auto result =
std::find_if( vm_handler.begin(), vm_handler.end(), []( const zydis_instr_t &instr_data ) -> bool {
// mov/movsx/movzx rax/eax/ax/al, [rsi]
if ( instr_data.instr.operand_count > 1 &&
( instr_data.instr.mnemonic == ZYDIS_MNEMONIC_MOV ||
@ -135,18 +119,15 @@ namespace vm
instr_data.instr.operands[ 1 ].mem.base == ZYDIS_REGISTER_RSI )
return true;
return false;
}
);
} );
return result != vm_handler.end();
}
std::uint8_t imm_size( const zydis_routine_t &vm_handler )
{
const auto result = std::find_if(
vm_handler.begin(), vm_handler.end(),
[](const zydis_instr_t& instr_data) -> bool
{
const auto result =
std::find_if( vm_handler.begin(), vm_handler.end(), []( const zydis_instr_t &instr_data ) -> bool {
// mov/movsx/movzx rax/eax/ax/al, [rsi]
if ( instr_data.instr.operand_count > 1 &&
( instr_data.instr.mnemonic == ZYDIS_MNEMONIC_MOV ||
@ -158,8 +139,7 @@ namespace vm
instr_data.instr.operands[ 1 ].mem.base == ZYDIS_REGISTER_RSI )
return true;
return false;
}
);
} );
if ( result == vm_handler.end() )
return 0u;
@ -169,10 +149,8 @@ namespace vm
bool get_operand_transforms( const zydis_routine_t &vm_handler, transform::map_t &transforms )
{
auto imm_fetch = std::find_if(
vm_handler.begin(), vm_handler.end(),
[](const zydis_instr_t& instr_data) -> bool
{
auto imm_fetch =
std::find_if( vm_handler.begin(), vm_handler.end(), []( const zydis_instr_t &instr_data ) -> bool {
// mov/movsx/movzx rax/eax/ax/al, [rsi]
if ( instr_data.instr.operand_count > 1 &&
( instr_data.instr.mnemonic == ZYDIS_MNEMONIC_MOV ||
@ -184,42 +162,34 @@ namespace vm
instr_data.instr.operands[ 1 ].mem.base == ZYDIS_REGISTER_RSI )
return true;
return false;
}
);
} );
if ( imm_fetch == vm_handler.end() )
return false;
// this finds the first transformation which looks like:
// transform rax, rbx <--- note these registers can be smaller so we to64 them...
auto key_transform = std::find_if(imm_fetch, vm_handler.end(),
[](const zydis_instr_t& instr_data) -> bool
{
auto key_transform =
std::find_if( imm_fetch, vm_handler.end(), []( const zydis_instr_t &instr_data ) -> bool {
if ( util::reg::compare( instr_data.instr.operands[ 0 ].reg.value, ZYDIS_REGISTER_RAX ) &&
util::reg::compare( instr_data.instr.operands[ 1 ].reg.value, ZYDIS_REGISTER_RBX ) )
return true;
return false;
}
);
} );
if ( key_transform == vm_handler.end() )
return false;
// look for a primer/instruction that alters RAX prior to the 5 transformations...
auto generic0 = std::find_if(imm_fetch + 1, key_transform,
[](const zydis_instr_t& instr_data) -> bool
{
return util::reg::compare(
instr_data.instr.operands[0].reg.value, ZYDIS_REGISTER_RAX) &&
auto generic0 = std::find_if( imm_fetch + 1, key_transform, []( const zydis_instr_t &instr_data ) -> bool {
return util::reg::compare( instr_data.instr.operands[ 0 ].reg.value, ZYDIS_REGISTER_RAX ) &&
!util::reg::compare( instr_data.instr.operands[ 1 ].reg.value, ZYDIS_REGISTER_RBX );
}
);
} );
zydis_decoded_instr_t nogeneric0;
nogeneric0.mnemonic = ZYDIS_MNEMONIC_INVALID;
transforms[transform::type::generic0] =
generic0 != key_transform ? generic0->instr : nogeneric0;
transforms[ transform::type::generic0 ] = generic0 != key_transform ? generic0->instr : nogeneric0;
// last transformation is the same as the first except src and dest are swwapped...
transforms[ transform::type::rolling_key ] = key_transform->instr;
@ -233,15 +203,13 @@ namespace vm
for ( auto idx = 2u; idx < 5; ++idx )
{
generic_transform = std::find_if(++generic_transform, vm_handler.end(),
[](const zydis_instr_t& instr_data) -> bool
{
generic_transform =
std::find_if( ++generic_transform, vm_handler.end(), []( const zydis_instr_t &instr_data ) -> bool {
if ( util::reg::compare( instr_data.instr.operands[ 0 ].reg.value, ZYDIS_REGISTER_RAX ) )
return true;
return false;
}
);
} );
if ( generic_transform == vm_handler.end() )
return false;
@ -254,22 +222,16 @@ namespace vm
vm::handler::profile_t *get_profile( handler_t &vm_handler )
{
static const auto vcontains =
[](vm::handler::profile_t* vprofile, handler_t* vm_handler) -> bool
{
static const auto vcontains = []( vm::handler::profile_t *vprofile, handler_t *vm_handler ) -> bool {
if ( vprofile->imm_size != vm_handler->imm_size )
return false;
for ( auto &instr : vprofile->signature )
{
const auto contains = std::find_if
(
vm_handler->instrs.begin(),
vm_handler->instrs.end(),
const auto contains = std::find_if(
vm_handler->instrs.begin(), vm_handler->instrs.end(),
[&](zydis_instr_t& instr_data) -> bool
{ return instr(instr_data.instr); }
);
[ & ]( zydis_instr_t &instr_data ) -> bool { return instr( instr_data.instr ); } );
if ( contains == vm_handler->instrs.end() )
return false;
@ -289,10 +251,8 @@ namespace vm
{
std::uintptr_t *get( const zydis_routine_t &vm_entry )
{
const auto result = std::find_if(
vm_entry.begin(), vm_entry.end(),
[](const zydis_instr_t& instr_data) -> bool
{
const auto result =
std::find_if( vm_entry.begin(), vm_entry.end(), []( const zydis_instr_t &instr_data ) -> bool {
const auto instr = &instr_data.instr;
// lea r12, vm_handlers... (always r12)...
if ( instr->mnemonic == ZYDIS_MNEMONIC_LEA &&
@ -302,15 +262,13 @@ namespace vm
return true;
return false;
}
);
} );
if ( result == vm_entry.end() )
return nullptr;
std::uintptr_t ptr = 0u;
ZydisCalcAbsoluteAddress(&result->instr,
&result->instr.operands[1], result->addr, &ptr);
ZydisCalcAbsoluteAddress( &result->instr, &result->instr.operands[ 1 ], result->addr, &ptr );
return reinterpret_cast< std::uintptr_t * >( ptr );
}
@ -319,13 +277,10 @@ namespace vm
{
zydis_register_t rcx_or_rdx = ZYDIS_REGISTER_NONE;
auto handler_fetch = std::find_if(
vm_entry.begin(), vm_entry.end(),
[&](const zydis_instr_t& instr_data) -> bool
{
auto handler_fetch =
std::find_if( vm_entry.begin(), vm_entry.end(), [ & ]( const zydis_instr_t &instr_data ) -> bool {
const auto instr = &instr_data.instr;
if (instr->mnemonic == ZYDIS_MNEMONIC_MOV &&
instr->operand_count == 2 &&
if ( instr->mnemonic == ZYDIS_MNEMONIC_MOV && instr->operand_count == 2 &&
instr->operands[ 1 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr->operands[ 1 ].mem.base == ZYDIS_REGISTER_R12 &&
instr->operands[ 1 ].mem.index == ZYDIS_REGISTER_RAX &&
@ -339,8 +294,7 @@ namespace vm
}
return false;
}
);
} );
// check to see if we found the fetch instruction and if the next instruction
// is not the end of the vector...
@ -351,16 +305,13 @@ namespace vm
// find the next instruction that writes to RCX or RDX...
// the register is determined by the vm handler fetch above...
auto handler_transform = std::find_if(
handler_fetch, vm_entry.end(),
[&](const zydis_instr_t& instr_data) -> bool
{
auto handler_transform =
std::find_if( handler_fetch, vm_entry.end(), [ & ]( const zydis_instr_t &instr_data ) -> bool {
if ( instr_data.instr.operands[ 0 ].reg.value == rcx_or_rdx &&
instr_data.instr.operands[ 0 ].actions & ZYDIS_OPERAND_ACTION_WRITE )
return true;
return false;
}
);
} );
if ( handler_transform == vm_entry.end() )
return false;
@ -376,8 +327,8 @@ namespace vm
const auto operation = vm::transform::inverse[ transform_instr.mnemonic ];
const auto bitsize = transform_instr.operands[ 0 ].size;
const auto imm = vm::transform::has_imm(&transform_instr) ?
transform_instr.operands[1].imm.value.u : 0u;
const auto imm =
vm::transform::has_imm( &transform_instr ) ? transform_instr.operands[ 1 ].imm.value.u : 0u;
return vm::transform::apply( bitsize, operation, val, imm );
}
@ -389,11 +340,11 @@ namespace vm
const auto operation = transform_instr.mnemonic;
const auto bitsize = transform_instr.operands[ 0 ].size;
const auto imm = vm::transform::has_imm(&transform_instr) ?
transform_instr.operands[1].imm.value.u : 0u;
const auto imm =
vm::transform::has_imm( &transform_instr ) ? transform_instr.operands[ 1 ].imm.value.u : 0u;
return vm::transform::apply( bitsize, operation, val, imm );
}
}
}
}
} // namespace table
} // namespace handler
} // namespace vm

@ -4,8 +4,8 @@ namespace vm
{
namespace instrs
{
std::pair<std::uint64_t, std::uint64_t> decrypt_operand(transform::map_t& transforms,
std::uint64_t operand, std::uint64_t rolling_key)
std::pair< std::uint64_t, std::uint64_t > decrypt_operand( transform::map_t &transforms, std::uint64_t operand,
std::uint64_t rolling_key )
{
const auto generic_decrypt_0 = &transforms[ transform::type::generic0 ];
const auto key_decrypt = &transforms[ transform::type::rolling_key ];
@ -17,44 +17,35 @@ namespace vm
if ( generic_decrypt_0->mnemonic != ZYDIS_MNEMONIC_INVALID )
{
operand = transform::apply(
generic_decrypt_0->operands[0].size,
generic_decrypt_0->mnemonic, operand,
generic_decrypt_0->operands[ 0 ].size, generic_decrypt_0->mnemonic, operand,
// check to see if this instruction has an IMM...
transform::has_imm(generic_decrypt_0) ?
generic_decrypt_0->operands[1].imm.value.u : 0);
transform::has_imm( generic_decrypt_0 ) ? generic_decrypt_0->operands[ 1 ].imm.value.u : 0 );
}
// apply transformation with rolling decrypt key...
operand = transform::apply(key_decrypt->operands[0].size,
key_decrypt->mnemonic, operand, rolling_key);
operand = transform::apply( key_decrypt->operands[ 0 ].size, key_decrypt->mnemonic, operand, rolling_key );
// apply three generic transformations...
{
operand = transform::apply(
generic_decrypt_1->operands[0].size,
generic_decrypt_1->mnemonic, operand,
generic_decrypt_1->operands[ 0 ].size, generic_decrypt_1->mnemonic, operand,
// check to see if this instruction has an IMM...
transform::has_imm(generic_decrypt_1) ?
generic_decrypt_1->operands[1].imm.value.u : 0);
transform::has_imm( generic_decrypt_1 ) ? generic_decrypt_1->operands[ 1 ].imm.value.u : 0 );
operand = transform::apply(
generic_decrypt_2->operands[0].size,
generic_decrypt_2->mnemonic, operand,
generic_decrypt_2->operands[ 0 ].size, generic_decrypt_2->mnemonic, operand,
// check to see if this instruction has an IMM...
transform::has_imm(generic_decrypt_2) ?
generic_decrypt_2->operands[1].imm.value.u : 0);
transform::has_imm( generic_decrypt_2 ) ? generic_decrypt_2->operands[ 1 ].imm.value.u : 0 );
operand = transform::apply(
generic_decrypt_3->operands[0].size,
generic_decrypt_3->mnemonic, operand,
generic_decrypt_3->operands[ 0 ].size, generic_decrypt_3->mnemonic, operand,
// check to see if this instruction has an IMM...
transform::has_imm(generic_decrypt_3) ?
generic_decrypt_3->operands[1].imm.value.u : 0);
transform::has_imm( generic_decrypt_3 ) ? generic_decrypt_3->operands[ 1 ].imm.value.u : 0 );
}
// update rolling key...
auto result = transform::apply(update_key->operands[0].size,
update_key->mnemonic, rolling_key, operand);
auto result =
transform::apply( update_key->operands[ 0 ].size, update_key->mnemonic, rolling_key, operand );
// update decryption key correctly...
switch ( update_key->operands[ 0 ].size )
@ -73,8 +64,8 @@ namespace vm
return { operand, rolling_key };
}
std::pair<std::uint64_t, std::uint64_t> encrypt_operand(transform::map_t& transforms,
std::uint64_t operand, std::uint64_t rolling_key)
std::pair< std::uint64_t, std::uint64_t > encrypt_operand( transform::map_t &transforms, std::uint64_t operand,
std::uint64_t rolling_key )
{
transform::map_t inverse;
inverse_transforms( transforms, inverse );
@ -86,8 +77,8 @@ namespace vm
const auto generic_decrypt_3 = &inverse[ transform::type::generic3 ];
const auto update_key = &inverse[ transform::type::update_key ];
auto result = transform::apply(update_key->operands[0].size,
update_key->mnemonic, rolling_key, operand);
auto result =
transform::apply( update_key->operands[ 0 ].size, update_key->mnemonic, rolling_key, operand );
// make sure we update the rolling decryption key correctly...
switch ( update_key->operands[ 0 ].size )
@ -105,63 +96,50 @@ namespace vm
{
operand = transform::apply(
generic_decrypt_3->operands[0].size,
generic_decrypt_3->mnemonic, operand,
generic_decrypt_3->operands[ 0 ].size, generic_decrypt_3->mnemonic, operand,
// check to see if this instruction has an IMM...
transform::has_imm(generic_decrypt_3) ?
generic_decrypt_3->operands[1].imm.value.u : 0);
transform::has_imm( generic_decrypt_3 ) ? generic_decrypt_3->operands[ 1 ].imm.value.u : 0 );
operand = transform::apply(
generic_decrypt_2->operands[0].size,
generic_decrypt_2->mnemonic, operand,
generic_decrypt_2->operands[ 0 ].size, generic_decrypt_2->mnemonic, operand,
// check to see if this instruction has an IMM...
transform::has_imm(generic_decrypt_2) ?
generic_decrypt_2->operands[1].imm.value.u : 0);
transform::has_imm( generic_decrypt_2 ) ? generic_decrypt_2->operands[ 1 ].imm.value.u : 0 );
operand = transform::apply(
generic_decrypt_1->operands[0].size,
generic_decrypt_1->mnemonic, operand,
generic_decrypt_1->operands[ 0 ].size, generic_decrypt_1->mnemonic, operand,
// check to see if this instruction has an IMM...
transform::has_imm(generic_decrypt_1) ?
generic_decrypt_1->operands[1].imm.value.u : 0);
transform::has_imm( generic_decrypt_1 ) ? generic_decrypt_1->operands[ 1 ].imm.value.u : 0 );
}
operand = transform::apply(key_decrypt->operands[0].size,
key_decrypt->mnemonic, operand, rolling_key);
operand = transform::apply( key_decrypt->operands[ 0 ].size, key_decrypt->mnemonic, operand, rolling_key );
if ( generic_decrypt_0->mnemonic != ZYDIS_MNEMONIC_INVALID )
{
operand = transform::apply(
generic_decrypt_0->operands[0].size,
generic_decrypt_0->mnemonic, operand,
generic_decrypt_0->operands[ 0 ].size, generic_decrypt_0->mnemonic, operand,
// check to see if this instruction has an IMM...
transform::has_imm(generic_decrypt_0) ?
generic_decrypt_0->operands[1].imm.value.u : 0);
transform::has_imm( generic_decrypt_0 ) ? generic_decrypt_0->operands[ 1 ].imm.value.u : 0 );
}
return { operand, rolling_key };
}
bool get_rva_decrypt(
const zydis_routine_t& vm_entry, std::vector<zydis_decoded_instr_t>& transform_instrs)
bool get_rva_decrypt( const zydis_routine_t &vm_entry, std::vector< zydis_decoded_instr_t > &transform_instrs )
{
//
// find mov esi, [rsp+0xA0]
//
auto result = std::find_if(vm_entry.begin(), vm_entry.end(),
[](const zydis_instr_t& instr_data) -> bool
{
if (instr_data.instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr_data.instr.operand_count == 2 &&
auto result =
std::find_if( vm_entry.begin(), vm_entry.end(), []( const zydis_instr_t &instr_data ) -> bool {
if ( instr_data.instr.mnemonic == ZYDIS_MNEMONIC_MOV && instr_data.instr.operand_count == 2 &&
instr_data.instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_ESI &&
instr_data.instr.operands[ 1 ].mem.base == ZYDIS_REGISTER_RSP &&
instr_data.instr.operands[ 1 ].mem.disp.has_displacement &&
instr_data.instr.operands[ 1 ].mem.disp.value == 0xA0 )
return true;
return false;
}
);
} );
if ( result == vm_entry.end() )
return false;
@ -172,12 +150,9 @@ namespace vm
for ( auto idx = 0u; idx < 3; ++idx )
{
result = std::find_if(++result, vm_entry.end(),
[](const zydis_instr_t& instr_data) -> bool
{
result = std::find_if( ++result, vm_entry.end(), []( const zydis_instr_t &instr_data ) -> bool {
return instr_data.instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_ESI;
}
);
} );
if ( result == vm_entry.end() )
return false;
@ -187,5 +162,5 @@ namespace vm
return true;
}
}
}
} // namespace instrs
} // namespace vm

@ -172,6 +172,9 @@
<Project>{88a23124-5640-35a0-b890-311d7a67a7d2}</Project>
</ProjectReference>
</ItemGroup>
<ItemGroup>
<None Include="..\.clang-format" />
</ItemGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
<ImportGroup Label="ExtensionTargets">
</ImportGroup>

@ -27,6 +27,9 @@
<Filter Include="Source Files\vmprofiles">
<UniqueIdentifier>{388154c1-cb08-493f-88fb-7e16cfffa010}</UniqueIdentifier>
</Filter>
<Filter Include="Resources">
<UniqueIdentifier>{5bb0ecc9-da37-4a13-8958-3c8eef2ceab5}</UniqueIdentifier>
</Filter>
</ItemGroup>
<ItemGroup>
<ClCompile Include="vmutils.cpp">
@ -224,4 +227,9 @@
<Filter>Header Files</Filter>
</ClInclude>
</ItemGroup>
<ItemGroup>
<None Include="..\.clang-format">
<Filter>Resources</Filter>
</None>
</ItemGroup>
</Project>

@ -6,17 +6,15 @@ namespace vm
{
namespace profile
{
vm::handler::profile_t addq =
{
vm::handler::profile_t addq = {
// ADD [RBP+8], RAX
// PUSHFQ
// POP [RBP]
"ADDQ", ADDQ, NULL,
{
{
// ADD [RBP+8], RAX
[](const zydis_decoded_instr_t& instr) -> bool
{
"ADDQ",
ADDQ,
NULL,
{ { // ADD [RBP+8], RAX
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_ADD &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 1 ].mem.base == ZYDIS_REGISTER_RBP &&
@ -24,32 +22,25 @@ namespace vm
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_RAX;
},
// PUSHFQ
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_PUSHFQ;
},
// POP [RBP]
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_POP &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP;
}
}
}
};
} } } };
vm::handler::profile_t adddw =
{
vm::handler::profile_t adddw = {
// ADD [RBP+8], EAX
// PUSHFQ
// POP [RBP]
"ADDDW", ADDDW, NULL,
{
{
// ADD [RBP+8], EAX
[](const zydis_decoded_instr_t& instr) -> bool
{
"ADDDW",
ADDDW,
NULL,
{ { // ADD [RBP+8], EAX
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_ADD &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 1 ].mem.base == ZYDIS_REGISTER_RBP &&
@ -57,20 +48,15 @@ namespace vm
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_EAX;
},
// PUSHFQ
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_PUSHFQ;
},
// POP [RBP]
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_POP &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP;
}
}
}
};
}
}
}
} } } };
} // namespace profile
} // namespace handler
} // namespace vm

@ -6,8 +6,7 @@ namespace vm
{
namespace profile
{
vm::handler::profile_t divq =
{
vm::handler::profile_t divq = {
// MOV RDX, [RBP]
// MOV RAX, [RBP+0x8]
// DIV [RBP+0x10]
@ -15,12 +14,11 @@ namespace vm
// MOV [RBP+0x10], RAX
// PUSHFQ
// POP [RBP]
"DIVQ", DIVQ, NULL,
{
{
// MOV RDX, [RBP]
[](const zydis_decoded_instr_t& instr) -> bool
{
"DIVQ",
DIVQ,
NULL,
{ { // MOV RDX, [RBP]
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RDX &&
@ -28,8 +26,7 @@ namespace vm
instr.operands[ 1 ].mem.base == ZYDIS_REGISTER_RBP;
},
// MOV RAX, [RBP+0x8]
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RAX &&
@ -38,16 +35,14 @@ namespace vm
instr.operands[ 1 ].mem.index == 0x8;
},
// DIV [RBP+0x10]
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_DIV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP &&
instr.operands[ 0 ].mem.index == 0x10;
},
// MOV [RBP+0x8], RDX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP &&
@ -56,8 +51,7 @@ namespace vm
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_RDX;
},
// MOV [RBP+0x10], RAX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP &&
@ -66,20 +60,15 @@ namespace vm
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_RAX;
},
// PUSHFQ
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_PUSHFQ;
},
// POP [RBP]
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_POP &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP;
} } } };
}
}
}
};
}
}
}
} // namespace handler
} // namespace vm

@ -6,18 +6,16 @@ namespace vm
{
namespace profile
{
vm::handler::profile_t jmp =
{
vm::handler::profile_t jmp = {
// MOV ESI, [RBP]
// ADD RSI, RAX
// MOV RBX, RSI
// ADD RSI, [RBP]
"JMP", JMP, NULL,
{
{
// MOV ESI, [RBP]
[](const zydis_decoded_instr_t& instr) -> bool
{
"JMP",
JMP,
NULL,
{ { // MOV ESI, [RBP]
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_ESI &&
@ -25,8 +23,7 @@ namespace vm
instr.operands[ 1 ].mem.base == ZYDIS_REGISTER_RBP;
},
// ADD RSI, RAX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_ADD &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RSI &&
@ -34,8 +31,7 @@ namespace vm
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_RAX;
},
// MOV RBX, RSI
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RBX &&
@ -43,17 +39,13 @@ namespace vm
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_RSI;
},
// ADD RSI, [RBP]
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_ADD &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RSI &&
instr.operands[ 1 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 1 ].mem.base == ZYDIS_REGISTER_RBP;
} } } };
}
}
}
};
}
}
}
} // namespace handler
} // namespace vm

@ -6,17 +6,15 @@ namespace vm
{
namespace profile
{
vm::handler::profile_t lconstq =
{
vm::handler::profile_t lconstq = {
// MOV RAX, [RSI]
// SUB RBP, 8
// MOV [RBP], RAX
"LCONSTQ", LCONSTQ, 64,
{
{
// SUB RBP, 8
[](const zydis_decoded_instr_t& instr) -> bool
{
"LCONSTQ",
LCONSTQ,
64,
{ { // SUB RBP, 8
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_SUB &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RBP &&
@ -24,29 +22,23 @@ namespace vm
instr.operands[ 1 ].imm.value.u == 0x8;
},
// MOV [RBP], RAX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP &&
instr.operands[ 1 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_RAX;
}
}
}
};
} } } };
vm::handler::profile_t lconstbzxw =
{
vm::handler::profile_t lconstbzxw = {
// MOV AL, [RSI]
// SUB RBP, 2
// MOV [RBP], AX
"LCONSTBZXW", LCONSTBZXW, 8,
{
{
// SUB RBP, 2
[](const zydis_decoded_instr_t& instr) -> bool
{
"LCONSTBZXW",
LCONSTBZXW,
8,
{ { // SUB RBP, 2
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_SUB &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RBP &&
@ -54,34 +46,25 @@ namespace vm
instr.operands[ 1 ].imm.value.u == 0x2;
},
// MOV [RBP], AX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP &&
instr.operands[ 1 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_AX;
}
}
}
};
} } } };
vm::handler::profile_t lconstbsxdw =
{
vm::handler::profile_t lconstbsxdw = {
// CWDE
// SUB RBP, 4
// MOV [RBP], EAX
"LCONSTBSXDW", LCONSTBSXDW, 8,
{
{
// CWDE
[](const zydis_decoded_instr_t& instr) -> bool
{
return instr.mnemonic == ZYDIS_MNEMONIC_CWDE;
},
"LCONSTBSXDW",
LCONSTBSXDW,
8,
{ { // CWDE
[]( const zydis_decoded_instr_t &instr ) -> bool { return instr.mnemonic == ZYDIS_MNEMONIC_CWDE; },
// SUB RBP, 4
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_SUB &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RBP &&
@ -89,34 +72,26 @@ namespace vm
instr.operands[ 1 ].imm.value.u == 0x4;
},
// MOV [RBP], EAX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP &&
instr.operands[ 1 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_EAX;
}
}
},
vm::handler::extention_t::sign_extend
};
} } },
vm::handler::extention_t::sign_extend };
vm::handler::profile_t lconstdwsxq =
{
vm::handler::profile_t lconstdwsxq = {
// CDQE
// SUB RBP, 8
// MOV [RBP], RAX
"LCONSTDWSXQ", LCONSTDWSXQ, 32,
{
// CDQE
[](const zydis_decoded_instr_t& instr) -> bool
{
return instr.mnemonic == ZYDIS_MNEMONIC_CDQE;
},
"LCONSTDWSXQ",
LCONSTDWSXQ,
32,
{ // CDQE
[]( const zydis_decoded_instr_t &instr ) -> bool { return instr.mnemonic == ZYDIS_MNEMONIC_CDQE; },
// SUB RBP, 8
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_SUB &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RBP &&
@ -124,34 +99,26 @@ namespace vm
instr.operands[ 1 ].imm.value.u == 0x8;
},
// MOV [RBP], RAX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP &&
instr.operands[ 1 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_RAX;
}
},
vm::handler::extention_t::sign_extend
};
} },
vm::handler::extention_t::sign_extend };
vm::handler::profile_t lconstwsxq =
{
vm::handler::profile_t lconstwsxq = {
// CDQE
// SUB RBP, 8
// MOV [RBP], RAX
"LCONSTWSXQ", LCONSTWSXQ, 16,
{
{
// CDQE
[](const zydis_decoded_instr_t& instr) -> bool
{
return instr.mnemonic == ZYDIS_MNEMONIC_CDQE;
},
"LCONSTWSXQ",
LCONSTWSXQ,
16,
{ { // CDQE
[]( const zydis_decoded_instr_t &instr ) -> bool { return instr.mnemonic == ZYDIS_MNEMONIC_CDQE; },
// SUB RBP, 8
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_SUB &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RBP &&
@ -159,29 +126,23 @@ namespace vm
instr.operands[ 1 ].imm.value.u == 0x8;
},
// MOV [RBP], RAX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP &&
instr.operands[ 1 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_RAX;
}
}
},
vm::handler::extention_t::sign_extend
};
} } },
vm::handler::extention_t::sign_extend };
vm::handler::profile_t lconstdw =
{
vm::handler::profile_t lconstdw = {
// SUB RBP, 4
// MOV [RBP], EAX
"LCONSTDW", LCONSTDW, 32,
{
{
// SUB RBP, 4
[](const zydis_decoded_instr_t& instr) -> bool
{
"LCONSTDW",
LCONSTDW,
32,
{ { // SUB RBP, 4
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_SUB &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RBP &&
@ -189,17 +150,13 @@ namespace vm
instr.operands[ 1 ].imm.value.u == 0x4;
},
// MOV [RBP], EAX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP &&
instr.operands[ 1 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_EAX;
}
}
}
};
}
}
}
} } } };
} // namespace profile
} // namespace handler
} // namespace vm

@ -6,17 +6,15 @@ namespace vm
{
namespace profile
{
vm::handler::profile_t lregq =
{
vm::handler::profile_t lregq = {
// MOV RDX, [RAX+RDI]
// SUB RBP, 8
// MOV [RBP], RDX
"LREGQ", LREGQ, 8,
{
{
// MOV RDX, [RAX+RDI] or MOV RDX, [RDI+RAX]
[](const zydis_decoded_instr_t& instr) -> bool
{
"LREGQ",
LREGQ,
8,
{ { // MOV RDX, [RAX+RDI] or MOV RDX, [RDI+RAX]
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RDX &&
@ -27,8 +25,7 @@ namespace vm
instr.operands[ 1 ].mem.index == ZYDIS_REGISTER_RAX );
},
// SUB RBP, 8
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_SUB &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RBP &&
@ -36,30 +33,24 @@ namespace vm
instr.operands[ 1 ].imm.value.u == 0x8;
},
// MOV [RBP], RDX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP &&
instr.operands[ 1 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_RDX;
}
}
}
};
} } } };
vm::handler::profile_t lregdw =
{
vm::handler::profile_t lregdw = {
// MOVZX AL, [RSI]
// MOV RDX, [RAX + RDI]
// SUB RBP, 0x4
// MOV [RBP], EDX
"LREGDW", LREGDW, 8,
{
{
// MOV RDX, [RAX + RDI] or MOV RDX, [RDI + RAX]
[](const zydis_decoded_instr_t& instr) -> bool
{
"LREGDW",
LREGDW,
8,
{ { // MOV RDX, [RAX + RDI] or MOV RDX, [RDI + RAX]
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_EDX &&
@ -70,8 +61,7 @@ namespace vm
instr.operands[ 1 ].mem.index == ZYDIS_REGISTER_RDI );
},
// SUB RBP, 0x4
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_SUB &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RBP &&
@ -79,17 +69,13 @@ namespace vm
instr.operands[ 1 ].imm.value.u == 0x4;
},
// MOV [RBP], EDX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP &&
instr.operands[ 1 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_EDX;
}
}
}
};
}
}
}
} } } };
} // namespace profile
} // namespace handler
} // namespace vm

@ -6,8 +6,7 @@ namespace vm
{
namespace profile
{
vm::handler::profile_t mulq =
{
vm::handler::profile_t mulq = {
// MOV RAX, [RBP+0x8]
// SUB RBP, 0x8
// MUL RDX
@ -15,12 +14,11 @@ namespace vm
// MOV [RBP+0x10], RAX
// PUSHFQ
// POP [RBP]
"MULQ", MULQ, NULL,
{
{
// MOV RAX, [RBP+0x8]
[](const zydis_decoded_instr_t& instr) -> bool
{
"MULQ",
MULQ,
NULL,
{ { // MOV RAX, [RBP+0x8]
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RAX &&
@ -29,8 +27,7 @@ namespace vm
instr.operands[ 1 ].mem.index == 0x8;
},
// SUB RBP, 0x8
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_SUB &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RBP &&
@ -38,15 +35,13 @@ namespace vm
instr.operands[ 1 ].imm.value.u == 0x8;
},
// MUL RDX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MUL &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RDX;
},
// MOV [RBP+0x8], RDX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP &&
@ -55,8 +50,7 @@ namespace vm
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_RDX;
},
// MOV [RBP+0x10], RAX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP &&
@ -65,20 +59,15 @@ namespace vm
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_RAX;
},
// PUSHFQ
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_PUSHFQ;
},
// POP [RBP]
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_POP &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP;
} } } };
}
}
}
};
}
}
}
} // namespace handler
} // namespace vm

@ -6,8 +6,7 @@ namespace vm
{
namespace profile
{
vm::handler::profile_t nandq =
{
vm::handler::profile_t nandq = {
// MOV RAX, [RBP]
// MOV RDX, [RBP+8]
// NOT RAX
@ -16,12 +15,11 @@ namespace vm
// MOV [RBP], RAX
// PUSHFQ
// POP [RBP]
"NANDQ", NANDQ, NULL,
{
{
// MOV RAX, [RBP]
[](const zydis_decoded_instr_t& instr) -> bool
{
"NANDQ",
NANDQ,
NULL,
{ { // MOV RAX, [RBP]
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RAX &&
@ -29,8 +27,7 @@ namespace vm
instr.operands[ 1 ].mem.base == ZYDIS_REGISTER_RBP;
},
// MOV RDX, [RBP+8]
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RDX &&
@ -39,22 +36,19 @@ namespace vm
instr.operands[ 1 ].mem.index == 0x8;
},
// NOT RAX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_NOT &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RAX;
},
// NOT RDX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_NOT &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RDX;
},
// AND RAX, RDX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_AND &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RAX &&
@ -62,8 +56,7 @@ namespace vm
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_RDX;
},
// MOV [RBP], RAX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP &&
@ -71,43 +64,34 @@ namespace vm
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_RAX;
},
// PUSHFQ
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_PUSHFQ;
},
// POP [RBP]
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_POP &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP;
}
}
}
};
} } } };
vm::handler::profile_t nanddw =
{
vm::handler::profile_t nanddw = {
// NOT DWORD PTR [RBP]
// MOV AX, [RBP]
// SUB RBP, 0x6
// AND [RBP+0x8], AX
// PUSHFQ
// POP [RBP]
"NANDDW", NANDDW, NULL,
{
{
// NOT DWORD PTR [RBP]
[](const zydis_decoded_instr_t& instr) -> bool
{
"NANDDW",
NANDDW,
NULL,
{ { // NOT DWORD PTR [RBP]
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_NOT &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[0].size == 32 &&
instr.operands[0].mem.base == ZYDIS_REGISTER_RBP;
instr.operands[ 0 ].size == 32 && instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP;
},
// MOV AX, [RBP]
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_AX &&
@ -115,8 +99,7 @@ namespace vm
instr.operands[ 1 ].mem.base == ZYDIS_REGISTER_RBP;
},
// SUB RBP, 0x6
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_SUB &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RBP &&
@ -124,8 +107,7 @@ namespace vm
instr.operands[ 1 ].imm.value.u == 0x6;
},
// AND [RBP+0x8], AX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_AND &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP &&
@ -134,20 +116,15 @@ namespace vm
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_AX;
},
// PUSHFQ
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_PUSHFQ;
},
// POP [RBP]
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_POP &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP;
}
}
}
};
}
}
}
} } } };
} // namespace profile
} // namespace handler
} // namespace vm

@ -6,16 +6,14 @@ namespace vm
{
namespace profile
{
vm::handler::profile_t pushvsp =
{
vm::handler::profile_t pushvsp = {
// MOV RAX, RBP
// SUB RBP, 8
"PUSHVSP", PUSHVSP, NULL,
{
{
// MOV RAX, RBP
[](const zydis_decoded_instr_t& instr) -> bool
{
"PUSHVSP",
PUSHVSP,
NULL,
{ { // MOV RAX, RBP
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RAX &&
@ -23,8 +21,7 @@ namespace vm
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_RBP;
},
// SUB RBP, 8
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_SUB &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RBP &&
@ -32,17 +29,13 @@ namespace vm
instr.operands[ 1 ].imm.value.u == 0x8;
},
// MOV [RBP], RAX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP &&
instr.operands[ 1 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_RAX;
} } } };
}
}
}
};
}
}
}
} // namespace handler
} // namespace vm

@ -6,17 +6,15 @@ namespace vm
{
namespace profile
{
vm::handler::profile_t readq =
{
vm::handler::profile_t readq = {
// MOV RAX, [RBP]
// MOV RAX, [RAX]
// MOV [RBP], RAX
"READQ", READQ, NULL,
{
{
// MOV RAX, [RBP]
[](const zydis_decoded_instr_t& instr) -> bool
{
"READQ",
READQ,
NULL,
{ { // MOV RAX, [RBP]
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RAX &&
@ -24,8 +22,7 @@ namespace vm
instr.operands[ 1 ].mem.base == ZYDIS_REGISTER_RBP;
},
// MOV RAX, [RAX]
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RAX &&
@ -33,17 +30,13 @@ namespace vm
instr.operands[ 1 ].mem.base == ZYDIS_REGISTER_RAX;
},
// MOV [RBP], RAX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP &&
instr.operands[ 1 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_RAX;
} } } };
}
}
}
};
}
}
}
} // namespace handler
} // namespace vm

@ -6,8 +6,7 @@ namespace vm
{
namespace profile
{
vm::handler::profile_t shlq =
{
vm::handler::profile_t shlq = {
// MOV RAX, [RBP]
// MOV CL, [RBP+0x8]
// SUB RBP, 0x6
@ -15,12 +14,11 @@ namespace vm
// MOV [RBP+0x8], RAX
// PUSHFQ
// POP [RBP]
"SHLQ", SHLQ, NULL,
{
{
// MOV RAX, [RBP]
[](const zydis_decoded_instr_t& instr) -> bool
{
"SHLQ",
SHLQ,
NULL,
{ { // MOV RAX, [RBP]
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RAX &&
@ -28,8 +26,7 @@ namespace vm
instr.operands[ 1 ].mem.base == ZYDIS_REGISTER_RBP;
},
// MOV CL, [RBP+0x8]
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_CL &&
@ -38,8 +35,7 @@ namespace vm
instr.operands[ 1 ].mem.index == 0x8;
},
// SUB RBP, 0x6
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_SUB &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RBP &&
@ -47,8 +43,7 @@ namespace vm
instr.operands[ 1 ].imm.value.u == 0x6;
},
// SHL RAX, CL
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_SHL &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RAX &&
@ -56,8 +51,7 @@ namespace vm
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_CL;
},
// MOV [RBP+0x8], RAX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP &&
@ -66,23 +60,17 @@ namespace vm
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_RAX;
},
// PUSHFQ
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_PUSHFQ;
},
// POP [RBP]
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_POP &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP;
}
}
}
};
} } } };
vm::handler::profile_t shldw =
{
vm::handler::profile_t shldw = {
// MOV EAX, [RBP]
// MOV CL, [RBP+0x4]
// SUB RBP, 0x6
@ -90,12 +78,11 @@ namespace vm
// MOV [RBP+0x8], EAX
// PUSHFQ
// POP [RBP]
"SHLQ", SHLQ, NULL,
{
{
// MOV EAX, [RBP]
[](const zydis_decoded_instr_t& instr) -> bool
{
"SHLQ",
SHLQ,
NULL,
{ { // MOV EAX, [RBP]
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_EAX &&
@ -103,8 +90,7 @@ namespace vm
instr.operands[ 1 ].mem.base == ZYDIS_REGISTER_RBP;
},
// MOV CL, [RBP+0x4]
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_CL &&
@ -113,8 +99,7 @@ namespace vm
instr.operands[ 1 ].mem.index == 0x4;
},
// SUB RBP, 0x6
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_SUB &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RBP &&
@ -122,8 +107,7 @@ namespace vm
instr.operands[ 1 ].imm.value.u == 0x6;
},
// SHL EAX, CL
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_SHL &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_EAX &&
@ -131,8 +115,7 @@ namespace vm
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_CL;
},
// MOV [RBP+0x8], EAX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP &&
@ -141,20 +124,15 @@ namespace vm
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_EAX;
},
// PUSHFQ
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_PUSHFQ;
},
// POP [RBP]
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_POP &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP;
}
}
}
};
}
}
}
} } } };
} // namespace profile
} // namespace handler
} // namespace vm

@ -6,8 +6,7 @@ namespace vm
{
namespace profile
{
vm::handler::profile_t shrq =
{
vm::handler::profile_t shrq = {
// MOV RAX, [RBP]
// MOV CL, [RBP+0x8]
// SUB RBP, 0x6
@ -15,12 +14,11 @@ namespace vm
// MOV [RBP+0x8], RAX
// PUSHFQ
// POP [RBP]
"SHRQ", SHRQ, NULL,
{
{
// MOV RAX, [RBP]
[](const zydis_decoded_instr_t& instr) -> bool
{
"SHRQ",
SHRQ,
NULL,
{ { // MOV RAX, [RBP]
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RAX &&
@ -28,8 +26,7 @@ namespace vm
instr.operands[ 1 ].mem.base == ZYDIS_REGISTER_RBP;
},
// MOV CL, [RBP+0x8]
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_CL &&
@ -38,8 +35,7 @@ namespace vm
instr.operands[ 1 ].mem.index == 0x8;
},
// SUB RBP, 0x6
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_SUB &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RBP &&
@ -47,8 +43,7 @@ namespace vm
instr.operands[ 1 ].imm.value.u == 0x6;
},
// SHR RAX, CL
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_SHR &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RAX &&
@ -56,8 +51,7 @@ namespace vm
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_CL;
},
// MOV [RBP+0x8], RAX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP &&
@ -66,20 +60,15 @@ namespace vm
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_RAX;
},
// PUSHFQ
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_PUSHFQ;
},
// POP [RBP]
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_POP &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RBP;
} } } };
}
}
}
};
}
}
}
} // namespace handler
} // namespace vm

@ -6,17 +6,15 @@ namespace vm
{
namespace profile
{
vm::handler::profile_t sregq =
{
vm::handler::profile_t sregq = {
// MOV RDX, [RBP]
// ADD RBP, 8
// MOV [RAX+RDI], RDX
"SREGQ", SREGQ, 8,
{
{
// MOV RDX, [RBP]
[](const zydis_decoded_instr_t& instr) -> bool
{
"SREGQ",
SREGQ,
8,
{ { // MOV RDX, [RBP]
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RDX &&
@ -24,8 +22,7 @@ namespace vm
instr.operands[ 1 ].mem.base == ZYDIS_REGISTER_RBP;
},
// ADD RBP, 8
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_ADD &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RBP &&
@ -33,8 +30,7 @@ namespace vm
instr.operands[ 1 ].imm.value.u == 8;
},
// MOV [RAX+RDI], RDX or MOV [RDI+RAX], RDX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
( instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RAX ||
@ -43,22 +39,17 @@ namespace vm
instr.operands[ 0 ].mem.index == ZYDIS_REGISTER_RAX ) &&
instr.operands[ 1 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_RDX;
}
}
}
};
} } } };
vm::handler::profile_t sregdw =
{
vm::handler::profile_t sregdw = {
// MOV EDX, [RBP]
// ADD RBP, 0x4
// MOV [RAX+RDI], EDX
"SREGDW", SREGDW, 8,
{
{
// MOV EDX, [RBP]
[](const zydis_decoded_instr_t& instr) -> bool
{
"SREGDW",
SREGDW,
8,
{ { // MOV EDX, [RBP]
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_EDX &&
@ -66,8 +57,7 @@ namespace vm
instr.operands[ 1 ].mem.base == ZYDIS_REGISTER_RBP;
},
// ADD RBP, 0x4
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_ADD &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RBP &&
@ -75,8 +65,7 @@ namespace vm
instr.operands[ 1 ].imm.value.u == 0x4;
},
// MOV [RAX+RDI], EDX or MOV [RDI+RAX], EDX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
( instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RAX ||
@ -85,22 +74,17 @@ namespace vm
instr.operands[ 0 ].mem.index == ZYDIS_REGISTER_RDI ) &&
instr.operands[ 1 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_EDX;
}
}
}
};
} } } };
vm::handler::profile_t sregw =
{
vm::handler::profile_t sregw = {
// MOV DX, [RBP]
// ADD RBP, 0x2
// MOV [RAX+RDI], DX
"SREGW", SREGW, 8,
{
{
// MOV DX, [RBP]
[](const zydis_decoded_instr_t& instr) -> bool
{
"SREGW",
SREGW,
8,
{ { // MOV DX, [RBP]
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_DX &&
@ -108,8 +92,7 @@ namespace vm
instr.operands[ 1 ].mem.base == ZYDIS_REGISTER_RBP;
},
// ADD RBP, 0x2
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_ADD &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RBP &&
@ -117,8 +100,7 @@ namespace vm
instr.operands[ 1 ].imm.value.u == 0x2;
},
// MOV [RAX+RDI], DX or MOV [RDI+RAX], DX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
( instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RAX ||
@ -127,10 +109,7 @@ namespace vm
instr.operands[ 0 ].mem.index == ZYDIS_REGISTER_RAX ) &&
instr.operands[ 1 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_DX;
}
}
}
};
}
}
}
} } } };
} // namespace profile
} // namespace handler
} // namespace vm

@ -6,17 +6,15 @@ namespace vm
{
namespace profile
{
vm::handler::profile_t vmexit =
{
vm::handler::profile_t vmexit = {
// MOV RAX, RBP
// POPFQ
// RET
"VMEXIT", VMEXIT, NULL,
{
{
// MOV RAX, RBP
[](const zydis_decoded_instr_t& instr) -> bool
{
"VMEXIT",
VMEXIT,
NULL,
{ { // MOV RAX, RBP
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RAX &&
@ -24,14 +22,11 @@ namespace vm
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_RBP;
},
// POPFQ
[](const zydis_decoded_instr_t& instr) -> bool
{ return instr.mnemonic == ZYDIS_MNEMONIC_POPFQ; },
[]( const zydis_decoded_instr_t &instr ) -> bool { return instr.mnemonic == ZYDIS_MNEMONIC_POPFQ; },
// RET
[](const zydis_decoded_instr_t& instr) -> bool
{ return instr.mnemonic == ZYDIS_MNEMONIC_RET; }
}
}
};
}
}
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_RET;
} } } };
}
} // namespace handler
} // namespace vm

@ -6,18 +6,16 @@ namespace vm
{
namespace profile
{
vm::handler::profile_t writeq =
{
vm::handler::profile_t writeq = {
// MOV RAX, [RBP]
// MOV RDX, [RBP+0x8]
// ADD RBP, 0x10
// MOV [RAX], RDX
"WRITEQ", WRITEQ, NULL,
{
{
// MOV RAX, [RBP]
[](const zydis_decoded_instr_t& instr) -> bool
{
"WRITEQ",
WRITEQ,
NULL,
{ { // MOV RAX, [RBP]
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RAX &&
@ -25,8 +23,7 @@ namespace vm
instr.operands[ 1 ].mem.base == ZYDIS_REGISTER_RBP;
},
// MOV RDX, [RBP+0x8]
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RDX &&
@ -35,8 +32,7 @@ namespace vm
instr.operands[ 1 ].mem.index == 0x8;
},
// ADD RBP, 0x10
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_ADD &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RBP &&
@ -44,30 +40,24 @@ namespace vm
instr.operands[ 1 ].imm.value.u == 0x10;
},
// MOV [RAX], RDX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RAX &&
instr.operands[ 1 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_RDX;
}
}
}
};
} } } };
vm::handler::profile_t writedw =
{
vm::handler::profile_t writedw = {
// MOV RAX, [RBP]
// MOV EDX, [RBP+0x8]
// ADD RBP, 0xC
// MOV [RAX], EDX
"WRITEDW", WRITEDW, NULL,
{
{
// MOV RAX, [RBP]
[](const zydis_decoded_instr_t& instr) -> bool
{
"WRITEDW",
WRITEDW,
NULL,
{ { // MOV RAX, [RBP]
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RAX &&
@ -75,8 +65,7 @@ namespace vm
instr.operands[ 1 ].mem.base == ZYDIS_REGISTER_RBP;
},
// MOV EDX, [RBP+0x8]
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_EDX &&
@ -85,8 +74,7 @@ namespace vm
instr.operands[ 1 ].mem.index == 0x8;
},
// ADD RBP, 0xC
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_ADD &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 0 ].reg.value == ZYDIS_REGISTER_RBP &&
@ -94,17 +82,13 @@ namespace vm
instr.operands[ 1 ].imm.value.u == 0xC;
},
// MOV [RAX], EDX
[](const zydis_decoded_instr_t& instr) -> bool
{
[]( const zydis_decoded_instr_t &instr ) -> bool {
return instr.mnemonic == ZYDIS_MNEMONIC_MOV &&
instr.operands[ 0 ].type == ZYDIS_OPERAND_TYPE_MEMORY &&
instr.operands[ 0 ].mem.base == ZYDIS_REGISTER_RAX &&
instr.operands[ 1 ].type == ZYDIS_OPERAND_TYPE_REGISTER &&
instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_EDX;
}
}
}
};
}
}
}
} } } };
} // namespace profile
} // namespace handler
} // namespace vm

@ -9,23 +9,21 @@ namespace vm
{
zydis_register_t to64( zydis_register_t reg )
{
return ZydisRegisterGetLargestEnclosing(
ZYDIS_MACHINE_MODE_LONG_64, reg);
return ZydisRegisterGetLargestEnclosing( ZYDIS_MACHINE_MODE_LONG_64, reg );
}
bool compare( zydis_register_t a, zydis_register_t b )
{
return to64( a ) == to64( b );
}
}
} // namespace reg
void print( const zydis_decoded_instr_t &instr )
{
char buffer[ 256 ];
ZydisFormatter formatter;
ZydisFormatterInit( &formatter, ZYDIS_FORMATTER_STYLE_INTEL );
ZydisFormatterFormatInstruction(&formatter, &instr,
buffer, sizeof(buffer), 0u);
ZydisFormatterFormatInstruction( &formatter, &instr, buffer, sizeof( buffer ), 0u );
puts( buffer );
}
@ -39,8 +37,7 @@ namespace vm
for ( auto [ instr, raw, addr ] : routine )
{
std::printf( "> 0x%p ", addr );
ZydisFormatterFormatInstruction(&formatter, &instr,
buffer, sizeof(buffer), addr);
ZydisFormatterFormatInstruction( &formatter, &instr, buffer, sizeof( buffer ), addr );
puts( buffer );
}
@ -85,13 +82,11 @@ namespace vm
zydis_decoded_instr_t instr;
ZydisDecoderInit( &decoder, ZYDIS_MACHINE_MODE_LONG_64, ZYDIS_ADDRESS_WIDTH_64 );
while (ZYAN_SUCCESS(ZydisDecoderDecodeBuffer(&decoder, reinterpret_cast<void*>(
routine_addr), 0x1000, &instr)))
while ( ZYAN_SUCCESS(
ZydisDecoderDecodeBuffer( &decoder, reinterpret_cast< void * >( routine_addr ), 0x1000, &instr ) ) )
{
std::vector< u8 > raw_instr;
raw_instr.insert(raw_instr.begin(),
(u8*)routine_addr,
(u8*)routine_addr + instr.length);
raw_instr.insert( raw_instr.begin(), ( u8 * )routine_addr, ( u8 * )routine_addr + instr.length );
if ( is_jmp( instr ) )
{
@ -122,9 +117,7 @@ namespace vm
void deobfuscate( zydis_routine_t &routine )
{
static const auto _uses =
[](ZydisDecodedOperand& op, zydis_register_t reg) -> bool
{
static const auto _uses = []( ZydisDecodedOperand &op, zydis_register_t reg ) -> bool {
switch ( op.type )
{
case ZYDIS_OPERAND_TYPE_MEMORY:
@ -140,9 +133,7 @@ namespace vm
return false;
};
static const auto _writes =
[](zydis_decoded_instr_t& inst) -> bool
{
static const auto _writes = []( zydis_decoded_instr_t &inst ) -> bool {
for ( auto idx = 0; idx < inst.operand_count; ++idx )
if ( inst.operands[ idx ].actions & ZYDIS_OPERAND_ACTION_MASK_WRITE )
return true;
@ -150,10 +141,8 @@ namespace vm
return false;
};
static const auto _remove =
[](zydis_routine_t& routine, zydis_routine_t::iterator itr,
zydis_register_t reg, u32 opcode_size) -> void
{
static const auto _remove = []( zydis_routine_t &routine, zydis_routine_t::iterator itr,
zydis_register_t reg, u32 opcode_size ) -> void {
for ( ; itr >= routine.begin(); --itr )
{
const auto instruction = &itr->instr;
@ -180,26 +169,26 @@ namespace vm
if ( op->actions & ZYDIS_OPERAND_ACTION_MASK_WRITE )
op->actions &= ~ZYDIS_OPERAND_ACTION_MASK_WRITE;
else stop = true;
else
stop = true;
}
if ( !_writes( *instruction ) )
routine.erase( itr );
else if (stop) break;
else if ( stop )
break;
}
};
for ( const auto &instr_data : routine )
{
if (routine.empty() || routine.size() == 1 ||
instr_data.instr.mnemonic == ZYDIS_MNEMONIC_JMP)
if ( routine.empty() || routine.size() == 1 || instr_data.instr.mnemonic == ZYDIS_MNEMONIC_JMP )
continue;
for ( auto itr = routine.begin() + 1; itr != routine.end(); itr++ )
{
if (itr->instr.mnemonic == ZYDIS_MNEMONIC_JMP ||
itr->instr.mnemonic == ZYDIS_MNEMONIC_RET)
if ( itr->instr.mnemonic == ZYDIS_MNEMONIC_JMP || itr->instr.mnemonic == ZYDIS_MNEMONIC_RET )
break;
// find the write operations that happen...
@ -224,5 +213,5 @@ namespace vm
}
}
}
}
}
} // namespace util
} // namespace vm
Loading…
Cancel
Save