Skip to content

Commit 3f5a497

Browse files
committed
Pak: More stable/consistent way of finding sha3 start block
1 parent e83aeb5 commit 3f5a497

1 file changed

Lines changed: 67 additions & 12 deletions

File tree

src/mods/IntegrityCheckBypass.cpp

Lines changed: 67 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -916,21 +916,76 @@ void IntegrityCheckBypass::restore_unencrypted_paks() {
916916

917917
// If this breaks... we'll fix it!
918918
const auto game = utility::get_executable();
919+
const auto pak_load_fn = utility::find_function_from_string_ref(game, L"_chunk_", true);
920+
921+
std::optional<uintptr_t> sha3_code_start{};
922+
923+
// The usual path we'll use. Easily identifies the func via string ref.
924+
// looks for a basic block containing a bunch of vmovups instructions
925+
// set the sha3_code_start to that block.
926+
if (pak_load_fn) {
927+
spdlog::info("[IntegrityCheckBypass]: Found pak_load_fn @ 0x{:X}, using it as reference to find sha3_code_start!", *pak_load_fn);
928+
const auto bounds = utility::determine_function_bounds(*pak_load_fn);
929+
930+
if (bounds) {
931+
const auto blocks = utility::collect_linear_blocks(bounds->start, bounds->end);
932+
const utility::LinearBlock* found_block = nullptr;
933+
934+
for (const auto& block : blocks) {
935+
// Look for sequences of vmovups instructions using disasm.
936+
size_t vmovups_sequence_length = 0;
937+
utility::linear_decode((uint8_t*)block.start, 100, [&](utility::ExhaustionContext& ctx) -> bool {
938+
if (ctx.addr > block.end) {
939+
return false;
940+
}
919941

920-
std::vector<std::string> possible_patterns = {
921-
"C5 F8 57 C0 C5 FC 11 84 24 ? ? ? ? C5 FC 11 84 24 ? ? ? ? C5 FC 11 84 24 ? ? ? ? C5 FC 11 84 24 ? ? ? ? C5 FC 11 44 24 ? 48",
922-
"C5 F8 57 C0 C5 FC 11 84 24 ? ? ? ? C5 FC 11 84 24 ? ? ? ? C5 FC 11 84 24 ? ? ? ? C5 FC 11 84 24 ? ? ? ? C5 FC 11 84 24 ? ? ? ? 48 C1 ? 10", // MHWILDS v1.041
923-
"C5 F8 57 C0 C5 FC 11 84 24 ? ? ? ? C5 FC 11 84 24 ? ? ? ? C5 FC 11 84 24 ? ? ? ? C5 FC 11 84 24 ? ? ? ? C5 FC 11 84 24 ? ? ? ? 48 8B ? ? 00 00 00 48 C1 ? 10", // MHSTORIES3
924-
"48 8B 05 ? ? ? ? 49 33 ? C0 00 00 00 C5 F1 EF C9 C5 F9 EF C0 C5 FC 11 45 ? C5 FC 11 4D ? C5 FC 11 4D ? C5 FC 11 4D ? C5 FC 11 4D ? 48 A9 00 00 F8 FF", // PRAGMATA
925-
"C5 F8 57 C0 C5 FC 11 45 ? C5 FC 11 45 ? C5 FC 11 45 ? C5 FC 11 45 ? C5 FC 11 45 ? 48 C1 E9 10" // RE9 v1.0.0.0
926-
};
942+
if (std::string_view{ctx.instrux.Mnemonic}.starts_with("VMOVUPS")) {
943+
vmovups_sequence_length++;
944+
} else {
945+
if (vmovups_sequence_length >= 4) { // The decryption code has a long sequence of vmovups instructions, so we look for sequences of 4 or more.
946+
spdlog::info("[IntegrityCheckBypass]: Found vmovups sequence of length {} at 0x{:X}, likely sha3_code_start!", vmovups_sequence_length, ctx.addr);
947+
found_block = &block;
948+
return false;
949+
}
950+
951+
vmovups_sequence_length = 0;
952+
}
953+
954+
return true;
955+
});
956+
957+
if (found_block != nullptr) {
958+
break;
959+
}
960+
}
961+
962+
if (found_block) {
963+
// The start of the vmovups isn't always the correct spot. The start of the block is actually the correct spot.
964+
sha3_code_start = found_block->start;
965+
spdlog::info("[IntegrityCheckBypass]: Found sha3_code_start @ 0x{:X} using vmovups sequence!", *sha3_code_start);
966+
} else {
967+
spdlog::error("[IntegrityCheckBypass]: Could not find vmovups sequence in blocks of pak_load_fn, cannot find sha3_code_start!");
968+
}
969+
} else {
970+
spdlog::error("[IntegrityCheckBypass]: Could not determine function bounds for pak_load_fn, cannot find sha3_code_start!");
971+
}
972+
}
927973

928-
std::optional<uintptr_t> sha3_code_start;
974+
// Fall back to old stuff.
975+
if (!sha3_code_start) {
976+
std::vector<std::string> possible_patterns = {
977+
"C5 F8 57 C0 C5 FC 11 84 24 ? ? ? ? C5 FC 11 84 24 ? ? ? ? C5 FC 11 84 24 ? ? ? ? C5 FC 11 84 24 ? ? ? ? C5 FC 11 44 24 ? 48",
978+
"C5 F8 57 C0 C5 FC 11 84 24 ? ? ? ? C5 FC 11 84 24 ? ? ? ? C5 FC 11 84 24 ? ? ? ? C5 FC 11 84 24 ? ? ? ? C5 FC 11 84 24 ? ? ? ? 48 C1 ? 10", // MHWILDS v1.041
979+
"C5 F8 57 C0 C5 FC 11 84 24 ? ? ? ? C5 FC 11 84 24 ? ? ? ? C5 FC 11 84 24 ? ? ? ? C5 FC 11 84 24 ? ? ? ? C5 FC 11 84 24 ? ? ? ? 48 8B ? ? 00 00 00 48 C1 ? 10", // MHSTORIES3
980+
"48 8B 05 ? ? ? ? 49 33 ? C0 00 00 00 C5 F1 EF C9 C5 F9 EF C0 C5 FC 11 45 ? C5 FC 11 4D ? C5 FC 11 4D ? C5 FC 11 4D ? C5 FC 11 4D ? 48 A9 00 00 F8 FF", // PRAGMATA
981+
"C5 F8 57 C0 C5 FC 11 45 ? C5 FC 11 45 ? C5 FC 11 45 ? C5 FC 11 45 ? C5 FC 11 45 ? 48 C1 E9 10" // RE9 v1.0.0.0
982+
};
929983

930-
for (const auto& pattern : possible_patterns) {
931-
sha3_code_start = utility::scan(game, pattern);
932-
if (sha3_code_start) {
933-
break;
984+
for (const auto& pattern : possible_patterns) {
985+
sha3_code_start = utility::scan(game, pattern);
986+
if (sha3_code_start) {
987+
break;
988+
}
934989
}
935990
}
936991

0 commit comments

Comments
 (0)