From 53f22b26bb8d674c03ab26fb5039e8d4be018f66 Mon Sep 17 00:00:00 2001 From: _xeroxz Date: Mon, 16 Aug 2021 00:58:21 -0700 Subject: [PATCH 1/2] added code to compile... --- CMakeLists.txt | 3 ++ cmake.toml | 3 +- include/devirt_t.hpp | 2 ++ include/devirt_utils.hpp | 18 ++++++++++ src/devirt_t.cpp | 36 ++++++++++++++++++- src/devirt_utils.cpp | 54 +++++++++++++++++++++++++++++ src/main.cpp | 75 ++++++++++------------------------------ 7 files changed, 132 insertions(+), 59 deletions(-) create mode 100644 include/devirt_utils.hpp create mode 100644 src/devirt_utils.cpp diff --git a/CMakeLists.txt b/CMakeLists.txt index 373e5f2..60acd20 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -41,6 +41,7 @@ set(vmdevirt_SOURCES "") list(APPEND vmdevirt_SOURCES "src/devirt_t.cpp" + "src/devirt_utils.cpp" "src/lifters/add.cpp" "src/lifters/div.cpp" "src/lifters/jmp.cpp" @@ -59,6 +60,7 @@ list(APPEND vmdevirt_SOURCES "src/main.cpp" "src/vmp_rtn_t.cpp" "include/devirt_t.hpp" + "include/devirt_utils.hpp" "include/vm_lifters.hpp" "include/vmp_rtn_t.hpp" ) @@ -106,6 +108,7 @@ target_link_libraries(vmdevirt PRIVATE LLVMX86Disassembler LLVMX86Info LLVMAsmParser + LLVMPasses ) unset(CMKR_TARGET) diff --git a/cmake.toml b/cmake.toml index 41fdb54..d4afe36 100644 --- a/cmake.toml +++ b/cmake.toml @@ -28,7 +28,8 @@ link-libraries = [ "LLVMX86Desc", "LLVMX86Disassembler", "LLVMX86Info", - "LLVMAsmParser" + "LLVMAsmParser", + "LLVMPasses" ] compile-definitions = [ "NOMINMAX" diff --git a/include/devirt_t.hpp b/include/devirt_t.hpp index 63bce8f..42549c2 100644 --- a/include/devirt_t.hpp +++ b/include/devirt_t.hpp @@ -18,10 +18,12 @@ #include "llvm/Transforms/InstCombine/InstCombine.h" #include "llvm/Transforms/Scalar.h" #include "llvm/Transforms/Scalar/GVN.h" +#include "llvm/Transforms/Utils.h" #include "X86TargetMachine.h" #include "llvm/Pass.h" #include "llvm/Passes/PassBuilder.h" +#include "llvm/Passes/OptimizationLevel.h" #include "llvm/Support/FileSystem.h" #include "llvm/Support/Host.h" #include "llvm/Support/TargetRegistry.h" diff --git a/include/devirt_utils.hpp b/include/devirt_utils.hpp new file mode 100644 index 0000000..90b122a --- /dev/null +++ b/include/devirt_utils.hpp @@ -0,0 +1,18 @@ +#include + +namespace devirt +{ + namespace util + { + /// + /// helper function to serialize vmp2 file data to vm::instr::code_block's... + /// + /// vector of pairs {vm enter offset, vector of code blocks} which gets filled up with + /// serialized data + /// a vector of bytes containing the vmp2 file... + /// returns true if serialization was successful + bool serialize_vmp2( + std::vector< std::pair< std::uint32_t, std::vector< vm::instrs::code_block_t > > > &virt_rtns, + std::vector< std::uint8_t > &vmp2file ); + } // namespace util +} // namespace devirt \ No newline at end of file diff --git a/src/devirt_t.cpp b/src/devirt_t.cpp index 8b2c5d2..7f7143f 100644 --- a/src/devirt_t.cpp +++ b/src/devirt_t.cpp @@ -67,7 +67,41 @@ namespace vm bool devirt_t::compile( std::vector< std::uint8_t > &obj ) { - return true; + llvm::legacy::FunctionPassManager pass_mgr( llvm_module ); + pass_mgr.add( llvm::createPromoteMemoryToRegisterPass() ); + pass_mgr.add( llvm::createCFGSimplificationPass() ); + pass_mgr.add( llvm::createSROAPass() ); + pass_mgr.add( llvm::createLoopSimplifyCFGPass() ); + pass_mgr.add( llvm::createNewGVNPass() ); + pass_mgr.add( llvm::createReassociatePass() ); + pass_mgr.add( llvm::createPartiallyInlineLibCallsPass() ); + pass_mgr.add( llvm::createDeadCodeEliminationPass() ); + pass_mgr.add( llvm::createCFGSimplificationPass() ); + pass_mgr.add( llvm::createInstructionCombiningPass() ); + pass_mgr.add( llvm::createFlattenCFGPass() ); + + for ( auto vmp_rtn : vmp_rtns ) + pass_mgr.run( *vmp_rtn->llvm_fptr ); + + // compile to native x86_64.... + llvm::TargetOptions opt; + llvm::SmallVector< char, 128 > buff; + llvm::raw_svector_ostream dest( buff ); + llvm::legacy::PassManager pass; + std::string error; + + auto target_triple = llvm::sys::getDefaultTargetTriple(); + llvm_module->setTargetTriple( target_triple ); + + auto target = llvm::TargetRegistry::lookupTarget( target_triple, error ); + auto reloc_model = llvm::Optional< llvm::Reloc::Model >(); + auto target_machine = target->createTargetMachine( target_triple, "generic", "", opt, reloc_model ); + llvm_module->setDataLayout( target_machine->createDataLayout() ); + + target_machine->addPassesToEmitFile( pass, dest, nullptr, llvm::CGFT_ObjectFile ); + auto result = pass.run( *llvm_module ); + obj.insert( obj.begin(), buff.begin(), buff.end() ); + return result; } llvm::Function *devirt_t::lift( std::uintptr_t rtn_begin, std::vector< vm::instrs::code_block_t > code_blocks ) diff --git a/src/devirt_utils.cpp b/src/devirt_utils.cpp new file mode 100644 index 0000000..a810ec2 --- /dev/null +++ b/src/devirt_utils.cpp @@ -0,0 +1,54 @@ +#include + +namespace devirt +{ + namespace util + { + bool serialize_vmp2( + std::vector< std::pair< std::uint32_t, std::vector< vm::instrs::code_block_t > > > &virt_rtns, + std::vector< std::uint8_t > &vmp2file ) + { + const auto file_header = reinterpret_cast< vmp2::v4::file_header * >( vmp2file.data() ); + + if ( file_header->version != vmp2::version_t::v4 ) + { + std::printf( "[!] invalid vmp2 file version... this build uses v3...\n" ); + return false; + } + + auto first_rtn = reinterpret_cast< vmp2::v4::rtn_t * >( reinterpret_cast< std::uintptr_t >( file_header ) + + file_header->rtn_offset ); + + for ( auto [ rtn_block, rtn_idx ] = std::pair{ first_rtn, 0ull }; rtn_idx < file_header->rtn_count; + ++rtn_idx, rtn_block = reinterpret_cast< vmp2::v4::rtn_t * >( + reinterpret_cast< std::uintptr_t >( rtn_block ) + rtn_block->size ) ) + { + virt_rtns.push_back( { rtn_block->vm_enter_offset, {} } ); + for ( auto [ code_block, block_idx ] = std::pair{ &rtn_block->code_blocks[ 0 ], 0ull }; + block_idx < rtn_block->code_block_count; + ++block_idx, code_block = reinterpret_cast< vmp2::v4::code_block_t * >( + reinterpret_cast< std::uintptr_t >( code_block ) + + code_block->next_block_offset ) ) + { + auto block_vinstrs = reinterpret_cast< vm::instrs::virt_instr_t * >( + reinterpret_cast< std::uintptr_t >( code_block ) + sizeof vmp2::v4::code_block_t + + ( code_block->num_block_addrs * 8 ) ); + + vm::instrs::code_block_t _code_block{ code_block->vip_begin }; + _code_block.jcc.has_jcc = code_block->has_jcc; + _code_block.jcc.type = code_block->jcc_type; + + for ( auto idx = 0u; idx < code_block->num_block_addrs; ++idx ) + _code_block.jcc.block_addr.push_back( code_block->branch_addr[ idx ] ); + + for ( auto idx = 0u; idx < code_block->vinstr_count; ++idx ) + _code_block.vinstrs.push_back( block_vinstrs[ idx ] ); + + virt_rtns.back().second.push_back( _code_block ); + } + } + + return true; + } + } // namespace util +} // namespace devirt \ No newline at end of file diff --git a/src/main.cpp b/src/main.cpp index 0e866be..2c25662 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -1,60 +1,9 @@ #include #include #include +#include #include -/// -/// helper function to serialize vmp2 file data to vm::instr::code_block's... -/// -/// vector of pairs {vm enter offset, vector of code blocks} which gets filled up with -/// serialized data -/// a vector of bytes containing the vmp2 file... -/// returns true if serialization was successful -bool serialize_vmp2( std::vector< std::pair< std::uint32_t, std::vector< vm::instrs::code_block_t > > > &virt_rtns, - std::vector< std::uint8_t > &vmp2file ) -{ - const auto file_header = reinterpret_cast< vmp2::v4::file_header * >( vmp2file.data() ); - - if ( file_header->version != vmp2::version_t::v4 ) - { - std::printf( "[!] invalid vmp2 file version... this build uses v3...\n" ); - return false; - } - - auto first_rtn = reinterpret_cast< vmp2::v4::rtn_t * >( reinterpret_cast< std::uintptr_t >( file_header ) + - file_header->rtn_offset ); - - for ( auto [ rtn_block, rtn_idx ] = std::pair{ first_rtn, 0ull }; rtn_idx < file_header->rtn_count; - ++rtn_idx, rtn_block = reinterpret_cast< vmp2::v4::rtn_t * >( - reinterpret_cast< std::uintptr_t >( rtn_block ) + rtn_block->size ) ) - { - virt_rtns.push_back( { rtn_block->vm_enter_offset, {} } ); - for ( auto [ code_block, block_idx ] = std::pair{ &rtn_block->code_blocks[ 0 ], 0ull }; - block_idx < rtn_block->code_block_count; - ++block_idx, code_block = reinterpret_cast< vmp2::v4::code_block_t * >( - reinterpret_cast< std::uintptr_t >( code_block ) + code_block->next_block_offset ) ) - { - auto block_vinstrs = reinterpret_cast< vm::instrs::virt_instr_t * >( - reinterpret_cast< std::uintptr_t >( code_block ) + sizeof vmp2::v4::code_block_t + - ( code_block->num_block_addrs * 8 ) ); - - vm::instrs::code_block_t _code_block{ code_block->vip_begin }; - _code_block.jcc.has_jcc = code_block->has_jcc; - _code_block.jcc.type = code_block->jcc_type; - - for ( auto idx = 0u; idx < code_block->num_block_addrs; ++idx ) - _code_block.jcc.block_addr.push_back( code_block->branch_addr[ idx ] ); - - for ( auto idx = 0u; idx < code_block->vinstr_count; ++idx ) - _code_block.vinstrs.push_back( block_vinstrs[ idx ] ); - - virt_rtns.back().second.push_back( _code_block ); - } - } - - return true; -} - int main( int argc, const char *argv[] ) { argparse::argument_parser_t parser( "vmdevirt", "virtual instruction pseudo code generator" ); @@ -87,7 +36,7 @@ int main( int argc, const char *argv[] ) const auto file_header = reinterpret_cast< vmp2::v4::file_header * >( vmp2file.data() ); std::vector< std::pair< std::uint32_t, std::vector< vm::instrs::code_block_t > > > virt_rtns; - if ( !serialize_vmp2( virt_rtns, vmp2file ) ) + if ( !devirt::util::serialize_vmp2( virt_rtns, vmp2file ) ) { std::printf( "> failed to serialize vmp2 file...\n" ); return false; @@ -97,18 +46,30 @@ int main( int argc, const char *argv[] ) llvm::Module llvm_module( "VMProtect 2 Devirtualization", llvm_ctx ); std::vector< std::uint8_t > compiled_obj; - vm::devirt_t vmp_rtn( &llvm_ctx, &llvm_module ); + vm::devirt_t vmp_devirt( &llvm_ctx, &llvm_module ); for ( auto &[ vm_enter_offset, vmp2_code_blocks ] : virt_rtns ) { - if ( !vmp_rtn.lift( vm_enter_offset + file_header->image_base, vmp2_code_blocks ) ) + if ( !vmp_devirt.lift( vm_enter_offset + file_header->image_base, vmp2_code_blocks ) ) { std::printf( "[!] failed to lift rtn_0x%p, please review the console...\n", vm_enter_offset + file_header->image_base ); return -1; } + + std::printf( "> lifted rtn_0x%p, number of blocks = %d\n", vm_enter_offset + file_header->image_base, + vmp2_code_blocks.size() ); } - vmp_rtn.compile( compiled_obj ); - std::printf( "> compiled obj size = %d\n", compiled_obj.size() ); + llvm::LLVMInitializeX86TargetInfo(); + llvm::LLVMInitializeX86Target(); + llvm::LLVMInitializeX86TargetMC(); + llvm::LLVMInitializeX86AsmParser(); + llvm::LLVMInitializeX86AsmPrinter(); + + vmp_devirt.compile( compiled_obj ); + std::printf( "> compiled all routines... compiled obj size = %d\n", compiled_obj.size() ); + + std::ofstream( "devirt.o", std::ios::binary ) + .write( reinterpret_cast< const char * >( compiled_obj.data() ), compiled_obj.size() ); } \ No newline at end of file From d94ff6126d1f6cb38382d8995cf7be21ce740af6 Mon Sep 17 00:00:00 2001 From: _xeroxz Date: Mon, 16 Aug 2021 02:06:17 -0700 Subject: [PATCH 2/2] added another lifter (POPVSP)... --- CMakeLists.txt | 1 + dependencies/vmprofiler | 2 +- include/devirt_t.hpp | 8 ++++---- include/vm_lifters.hpp | 2 ++ src/devirt_t.cpp | 8 ++++---- src/lifters/add.cpp | 6 +++--- src/lifters/nand.cpp | 6 +++--- src/lifters/popvsp.cpp | 16 ++++++++++++++++ src/lifters/shr.cpp | 8 ++++---- src/main.cpp | 2 ++ src/vmp_rtn_t.cpp | 3 --- 11 files changed, 40 insertions(+), 22 deletions(-) create mode 100644 src/lifters/popvsp.cpp diff --git a/CMakeLists.txt b/CMakeLists.txt index 60acd20..fd248be 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -50,6 +50,7 @@ list(APPEND vmdevirt_SOURCES "src/lifters/lreg.cpp" "src/lifters/mul.cpp" "src/lifters/nand.cpp" + "src/lifters/popvsp.cpp" "src/lifters/pushvsp.cpp" "src/lifters/read.cpp" "src/lifters/sflags.cpp" diff --git a/dependencies/vmprofiler b/dependencies/vmprofiler index 05c98b1..9b5f89f 160000 --- a/dependencies/vmprofiler +++ b/dependencies/vmprofiler @@ -1 +1 @@ -Subproject commit 05c98b1ef57c3375ffd455221a3be1be6110d4eb +Subproject commit 9b5f89f4881862598181163069c69f584257d3f0 diff --git a/include/devirt_t.hpp b/include/devirt_t.hpp index 42549c2..a6184de 100644 --- a/include/devirt_t.hpp +++ b/include/devirt_t.hpp @@ -65,10 +65,10 @@ namespace vm llvm::Value *load_value( std::uint8_t byte_size, llvm::GlobalValue *global ); llvm::Value *load_value( std::uint8_t byte_size, llvm::AllocaInst *var ); - llvm::Value *compute_sf( std::uint8_t byte_size, llvm::Value *val ); - llvm::Value *compute_zf( std::uint8_t byte_size, llvm::Value *val ); - llvm::Value *compute_pf( std::uint8_t byte_size, llvm::Value *val ); - llvm::Value *combine_flags( llvm::Value *cf, llvm::Value *pf, llvm::Value *af, llvm::Value *zf, llvm::Value *sf, + llvm::Value *sf( std::uint8_t byte_size, llvm::Value *val ); + llvm::Value *zf( std::uint8_t byte_size, llvm::Value *val ); + llvm::Value *pf( std::uint8_t byte_size, llvm::Value *val ); + llvm::Value *flags( llvm::Value *cf, llvm::Value *pf, llvm::Value *af, llvm::Value *zf, llvm::Value *sf, llvm::Value *of ); }; } // namespace vm \ No newline at end of file diff --git a/include/vm_lifters.hpp b/include/vm_lifters.hpp index e9b5717..8c4e606 100644 --- a/include/vm_lifters.hpp +++ b/include/vm_lifters.hpp @@ -36,6 +36,7 @@ namespace vm static lifter_callback_t lregq, lregdw; static lifter_callback_t pushvsp; + static lifter_callback_t popvsp; static lifter_callback_t readq, readdw; static lifter_callback_t nandq, nanddw; static lifter_callback_t shrq; @@ -56,6 +57,7 @@ namespace vm { vm::handler::ADDW, &addw }, { vm::handler::SHRQ, &shrq }, { vm::handler::PUSHVSP, &pushvsp }, + { vm::handler::POPVSP, &popvsp }, { vm::handler::SREGQ, &sregq }, { vm::handler::SREGDW, &sregdw }, { vm::handler::LREGQ, &lregq }, diff --git a/src/devirt_t.cpp b/src/devirt_t.cpp index 7f7143f..4804b97 100644 --- a/src/devirt_t.cpp +++ b/src/devirt_t.cpp @@ -129,21 +129,21 @@ namespace vm return vmp_rtn->llvm_fptr; } - llvm::Value *devirt_t::compute_sf( std::uint8_t byte_size, llvm::Value *val ) + llvm::Value *devirt_t::sf( std::uint8_t byte_size, llvm::Value *val ) { auto op_size = llvm::IntegerType::get( *llvm_ctx, byte_size * 8 ); auto msb = ir_builder->CreateLShr( val, ( byte_size * 8 ) - 1 ); return ir_builder->CreateZExt( msb, llvm::IntegerType::get( *llvm_ctx, 64 ) ); } - llvm::Value *devirt_t::compute_zf( std::uint8_t byte_size, llvm::Value *val ) + llvm::Value *devirt_t::zf( std::uint8_t byte_size, llvm::Value *val ) { auto op_size = llvm::IntegerType::get( *llvm_ctx, byte_size * 8 ); auto is_zero = ir_builder->CreateICmpEQ( val, llvm::ConstantInt::get( op_size, 0 ) ); return ir_builder->CreateZExt( is_zero, llvm::IntegerType::get( *llvm_ctx, 64 ) ); } - llvm::Value *devirt_t::compute_pf( std::uint8_t byte_size, llvm::Value *val ) + llvm::Value *devirt_t::pf( std::uint8_t byte_size, llvm::Value *val ) { auto operand_size = llvm::IntegerType::get( *llvm_ctx, byte_size * 8 ); auto popcount_intrinsic = llvm::Intrinsic::getDeclaration( llvm_module, llvm::Intrinsic::ctpop, @@ -154,7 +154,7 @@ namespace vm return ir_builder->CreateCall( popcount_intrinsic, { extended_bits } ); } - llvm::Value *devirt_t::combine_flags( llvm::Value *cf, llvm::Value *pf, llvm::Value *af, llvm::Value *zf, + llvm::Value *devirt_t::flags( llvm::Value *cf, llvm::Value *pf, llvm::Value *af, llvm::Value *zf, llvm::Value *sf, llvm::Value *of ) { auto shifted_pf = ir_builder->CreateShl( pf, 2, "shifted_pf", true, true ); diff --git a/src/lifters/add.cpp b/src/lifters/add.cpp index 1f298f0..9060c1d 100644 --- a/src/lifters/add.cpp +++ b/src/lifters/add.cpp @@ -24,12 +24,12 @@ namespace vm auto s_of_bit = rtn->ir_builder->CreateExtractValue( s_add, { 1 } ); auto of = rtn->ir_builder->CreateZExt( s_of_bit, llvm::IntegerType::get( *rtn->llvm_ctx, 64 ) ); - auto sf = rtn->compute_sf( byte_size, u_sum ); - auto zf = rtn->compute_zf( byte_size, u_sum ); + auto sf = rtn->sf( byte_size, u_sum ); + auto zf = rtn->zf( byte_size, u_sum ); auto pf = llvm::ConstantInt::get( llvm::IntegerType::get( *rtn->llvm_ctx, 64 ), 0 ); // TODO make clean PF bit computation... - auto flags_calc = rtn->combine_flags( + auto flags_calc = rtn->flags( cf, pf, llvm::ConstantInt::get( llvm::IntegerType::get( *rtn->llvm_ctx, 64 ), 0 ), zf, sf, of ); return flags_calc; diff --git a/src/lifters/nand.cpp b/src/lifters/nand.cpp index 8ec8fa0..f2ca24e 100644 --- a/src/lifters/nand.cpp +++ b/src/lifters/nand.cpp @@ -7,11 +7,11 @@ namespace vm auto cf = llvm::ConstantInt::get( llvm::IntegerType::get( *rtn->llvm_ctx, 64 ), 0 ); auto of = llvm::ConstantInt::get( llvm::IntegerType::get( *rtn->llvm_ctx, 64 ), 0 ); - auto sf = rtn->compute_sf( byte_size, result ); - auto zf = rtn->compute_zf( byte_size, result ); + auto sf = rtn->sf( byte_size, result ); + auto zf = rtn->zf( byte_size, result ); auto pf = llvm::ConstantInt::get( llvm::IntegerType::get( *rtn->llvm_ctx, 64 ), 0 ); - return rtn->combine_flags( cf, pf, llvm::ConstantInt::get( llvm::IntegerType::get( *rtn->llvm_ctx, 64 ), 0 ), + return rtn->flags( cf, pf, llvm::ConstantInt::get( llvm::IntegerType::get( *rtn->llvm_ctx, 64 ), 0 ), zf, sf, of ); } diff --git a/src/lifters/popvsp.cpp b/src/lifters/popvsp.cpp new file mode 100644 index 0000000..6d8d600 --- /dev/null +++ b/src/lifters/popvsp.cpp @@ -0,0 +1,16 @@ +#include + +namespace vm +{ + lifters_t::lifter_callback_t lifters_t::popvsp = + [ & ]( vm::devirt_t *rtn, const vm::instrs::code_block_t &vm_code_block, const vm::instrs::virt_instr_t &vinstr, + llvm::IRBuilder<> *ir_builder ) { + auto &vmp_rtn = rtn->vmp_rtns.back(); + auto stack = ir_builder->CreateLoad( vmp_rtn->stack ); + auto stack_ptr_ptr = ir_builder->CreatePointerCast( + stack, llvm::PointerType::get( llvm::PointerType::get( ir_builder->getInt8Ty(), 0ull ), 0ull ) ); + + auto stack_ptr = ir_builder->CreateLoad( stack_ptr_ptr ); + ir_builder->CreateStore( stack_ptr, vmp_rtn->stack ); + }; +} \ No newline at end of file diff --git a/src/lifters/shr.cpp b/src/lifters/shr.cpp index 43e5b7a..03a74f6 100644 --- a/src/lifters/shr.cpp +++ b/src/lifters/shr.cpp @@ -11,12 +11,12 @@ namespace vm auto cf = rtn->ir_builder->CreateZExt( msb, llvm::IntegerType::get( *rtn->llvm_ctx, 64 ) ); auto of = - rtn->compute_sf( byte_size, lhs ); // we reuse the compute_sf helper since the flag expression is the same - auto sf = rtn->compute_sf( byte_size, result ); - auto zf = rtn->compute_zf( byte_size, result ); + rtn->sf( byte_size, lhs ); // we reuse the compute_sf helper since the flag expression is the same + auto sf = rtn->sf( byte_size, result ); + auto zf = rtn->zf( byte_size, result ); auto pf = llvm::ConstantInt::get( llvm::IntegerType::get( *rtn->llvm_ctx, 64 ), 0 ); - return rtn->combine_flags( cf, pf, llvm::ConstantInt::get( llvm::IntegerType::get( *rtn->llvm_ctx, 64 ), 0 ), + return rtn->flags( cf, pf, llvm::ConstantInt::get( llvm::IntegerType::get( *rtn->llvm_ctx, 64 ), 0 ), zf, sf, of ); } diff --git a/src/main.cpp b/src/main.cpp index 2c25662..c300f99 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -8,6 +8,8 @@ int main( int argc, const char *argv[] ) { argparse::argument_parser_t parser( "vmdevirt", "virtual instruction pseudo code generator" ); parser.add_argument().name( "--vmp2file" ).required( true ).description( "path to .vmp2 file..." ); + parser.add_argument().name( "--bin" ).required( true ).description( + "path to the image in which to apply devirtualized code too...\n" ); parser.enable_help(); auto err = parser.parse( argc, argv ); diff --git a/src/vmp_rtn_t.cpp b/src/vmp_rtn_t.cpp index 35c2180..2f7d910 100644 --- a/src/vmp_rtn_t.cpp +++ b/src/vmp_rtn_t.cpp @@ -27,13 +27,10 @@ namespace vm void vmp_rtn_t::create_routine( void ) { - // function has no arguments and returns void... maybe change this in the future as i learn - // more and more LLVM... auto func_ty = llvm::FunctionType::get( llvm::PointerType::getInt8PtrTy( ir_builder->getContext() ), { llvm::PointerType::getInt8PtrTy( ir_builder->getContext() ) }, false ); - // convert the rtn_begin address to a hex string and prepend "rtn_" to it... std::stringstream rtn_name; rtn_name << "rtn_" << std::hex << rtn_begin; llvm_fptr = llvm::Function::Create( func_ty, llvm::GlobalValue::LinkageTypes::ExternalLinkage,