diff --git a/.gitmodules b/.gitmodules index a574631c..60359032 100644 --- a/.gitmodules +++ b/.gitmodules @@ -2,7 +2,7 @@ path = deps/unicorn url = https://github.com/momo5502/unicorn.git shallow = true - branch = wasm + branch = dev [submodule "deps/reflect"] path = deps/reflect url = https://github.com/qlibs/reflect.git diff --git a/deps/unicorn b/deps/unicorn index f33976a4..79f4f7a5 160000 --- a/deps/unicorn +++ b/deps/unicorn @@ -1 +1 @@ -Subproject commit f33976a41bb06dde7c48b5e6de96157f8334b3d7 +Subproject commit 79f4f7a51eb4e8360ab08a51ce6d68b8ae24cd1b diff --git a/src/backends/unicorn-emulator/unicorn_x86_64_emulator.cpp b/src/backends/unicorn-emulator/unicorn_x86_64_emulator.cpp index d8a4185c..cf4b9087 100644 --- a/src/backends/unicorn-emulator/unicorn_x86_64_emulator.cpp +++ b/src/backends/unicorn-emulator/unicorn_x86_64_emulator.cpp @@ -2,12 +2,13 @@ #include "unicorn_x86_64_emulator.hpp" #include +#include +#include #include "unicorn_memory_regions.hpp" #include "unicorn_hook.hpp" #include "function_wrapper.hpp" -#include namespace unicorn { @@ -214,8 +215,9 @@ namespace unicorn void start(const size_t count) override { - this->has_violation_ = false; - const auto start = this->read_instruction_pointer(); + const auto start = this->violation_ip_.value_or(this->read_instruction_pointer()); + this->violation_ip_ = std::nullopt; + constexpr auto end = std::numeric_limits::max(); const auto res = uc_emu_start(*this, start, end, 0, count); if (res == UC_ERR_OK) @@ -231,7 +233,7 @@ namespace unicorn res == UC_ERR_WRITE_PROT || // res == UC_ERR_FETCH_PROT; - if (!is_violation || !this->has_violation_) + if (!is_violation || !this->has_violation()) { uce(res); } @@ -487,14 +489,22 @@ namespace unicorn const auto resume = c(address, static_cast(size), operation, violation) == memory_violation_continuation::resume; - const auto has_ip_changed = ip != this->read_instruction_pointer(); + const auto new_ip = this->read_instruction_pointer(); + const auto has_ip_changed = ip != new_ip; if (!resume) { return false; } - this->has_violation_ = resume && has_ip_changed; + if (resume && has_ip_changed) + { + this->violation_ip_ = new_ip; + } + else + { + this->violation_ip_ = std::nullopt; + } if (has_ip_changed) { @@ -659,7 +669,7 @@ namespace unicorn bool has_violation() const override { - return this->has_violation_; + return this->violation_ip_.has_value(); } std::string get_name() const override @@ -670,7 +680,7 @@ namespace unicorn private: mutable bool has_snapshots_{false}; uc_engine* uc_{}; - bool has_violation_{false}; + std::optional violation_ip_{}; std::vector> hooks_{}; std::unordered_map mmio_{}; }; diff --git a/src/windows-emulator/windows_emulator.cpp b/src/windows-emulator/windows_emulator.cpp index 7352e915..364352db 100644 --- a/src/windows-emulator/windows_emulator.cpp +++ b/src/windows-emulator/windows_emulator.cpp @@ -459,11 +459,14 @@ void windows_emulator::setup_hooks() const auto ticks = this->clock_->timestamp_counter(); this->emu().reg(x86_register::rax, ticks & 0xFFFFFFFF); this->emu().reg(x86_register::rdx, (ticks >> 32) & 0xFFFFFFFF); + return instruction_hook_continuation::skip_instruction; }); // TODO: Unicorn needs this - This should be handled in the backend this->emu().hook_instruction(x86_hookable_instructions::invalid, [&] { + // TODO: Unify icicle & unicorn handling + dispatch_illegal_instruction_violation(this->emu(), this->process); return instruction_hook_continuation::skip_instruction; // });