diff --git a/Extension/Assets/loose_files.cpp b/Extension/Assets/loose_files.cpp index 03e414b5..932958b2 100644 --- a/Extension/Assets/loose_files.cpp +++ b/Extension/Assets/loose_files.cpp @@ -47,7 +47,7 @@ struct State { // Hooks and the native mount live until process exit, like the pinned runtime. State& state() { static auto* value = new State; return *value; } -// Supported September 8 build, checked after runtime image validation. +// Supported game build, checked after runtime image validation. bool validate_contract(std::uintptr_t base) { struct Contract { std::uintptr_t rva; std::span bytes; }; const Contract contracts[]{ @@ -58,7 +58,8 @@ bool validate_contract(std::uintptr_t base) { for (const auto& contract : contracts) { std::array actual{}; SIZE_T count{}; - if (!ReadProcessMemory(GetCurrentProcess(), reinterpret_cast(base + contract.rva), + if (contract.bytes.size() > actual.size() || // a longer prefix would overrun actual + !ReadProcessMemory(GetCurrentProcess(), reinterpret_cast(base + contract.rva), actual.data(), contract.bytes.size(), &count) || count != contract.bytes.size() || std::memcmp(actual.data(), contract.bytes.data(), contract.bytes.size())) return false; } diff --git a/Extension/Assets/mod_layers.cpp b/Extension/Assets/mod_layers.cpp index 840d7be2..b3f4e1f8 100644 --- a/Extension/Assets/mod_layers.cpp +++ b/Extension/Assets/mod_layers.cpp @@ -126,7 +126,7 @@ bool read_memory(std::uintptr_t address, void* destination, std::size_t size) no destination, size, &read) && read == size; } -// Supported September 8 build, checked after runtime image validation. +// Supported game build, checked after runtime image validation. bool validate_contract(std::uintptr_t base) noexcept { struct Contract { std::uintptr_t rva; std::span bytes; }; const Contract contracts[]{ @@ -134,7 +134,8 @@ bool validate_contract(std::uintptr_t base) noexcept { {layers::layout_bootstrap, layers::layout_bootstrap_prefix}}; for (const auto& contract : contracts) { std::array actual{}; - if (!read_memory(base + contract.rva, actual.data(), contract.bytes.size()) || + if (contract.bytes.size() > actual.size() || // a longer prefix would overrun actual + !read_memory(base + contract.rva, actual.data(), contract.bytes.size()) || std::memcmp(actual.data(), contract.bytes.data(), contract.bytes.size())) return false; } std::uintptr_t slot{};