diff --git a/include/vmprofiles.hpp b/include/vmprofiles.hpp index 922d798..40872d8 100644 --- a/include/vmprofiles.hpp +++ b/include/vmprofiles.hpp @@ -14,6 +14,7 @@ namespace vm::handler INVALID, LRFLAGS, PUSHVSP, + PUSHVSPDW, MULQ, DIVQ, CALL, diff --git a/src/vminstrs.cpp b/src/vminstrs.cpp index f6cef09..49e1270 100644 --- a/src/vminstrs.cpp +++ b/src/vminstrs.cpp @@ -201,7 +201,7 @@ namespace vm::instrs { // there is no branch for this as this is a vmexit... if ( code_block.vinstrs.back().mnemonic_t == vm::handler::VMEXIT ) - return {}; + return jcc_data{ false, jcc_type::none }; // find the last LCONSTDW... the imm value is the JMP xor decrypt key... // we loop backwards here (using rbegin and rend)... @@ -211,6 +211,9 @@ namespace vm::instrs return profile && profile->mnemonic == vm::handler::LCONSTDW; } ); + if ( result == code_block.vinstrs.rend() ) + return jcc_data{ false, jcc_type::none }; + jcc_data jcc; const auto xor_key = static_cast< std::uint32_t >( result->operand.imm.u ); const auto &last_trace = code_block.vinstrs.back().trace_data; diff --git a/src/vmprofiles/pushvsp.cpp b/src/vmprofiles/pushvsp.cpp index 426b99e..26c1de5 100644 --- a/src/vmprofiles/pushvsp.cpp +++ b/src/vmprofiles/pushvsp.cpp @@ -31,4 +31,35 @@ namespace vm::handler::profile instr.operands[ 1 ].type == ZYDIS_OPERAND_TYPE_REGISTER && instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_RAX; } } } }; + + vm::handler::profile_t pushvspdw = { + // MOV EAX, EBP + // SUB RBP, 0x4 + // MOV [RBP], EAX + "PUSHVSPDW", + PUSHVSPDW, + NULL, + { { // MOV EAX, EBP + []( 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 && + instr.operands[ 1 ].type == ZYDIS_OPERAND_TYPE_REGISTER && + instr.operands[ 1 ].reg.value == ZYDIS_REGISTER_EBP; + }, + // SUB RBP, 0x4 + []( 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 && + instr.operands[ 1 ].type == ZYDIS_OPERAND_TYPE_IMMEDIATE && + instr.operands[ 1 ].imm.value.u == 0x4; + }, + // MOV [RBP], EAX + []( 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 vm::handler::profile \ No newline at end of file