From df7d604169085c375c23bfc82184149ce4ad2e46 Mon Sep 17 00:00:00 2001 From: Amrsatrio Date: Sun, 2 Nov 2025 03:20:47 +0700 Subject: [PATCH] File Explorer: On TIFE-equipped builds, fix 7 command bar menu bar behavior and fix 10 ribbon window saving - ARM64 (#2243, #2676) --- ExplorerPatcher/dllmain.c | 59 ++++++++++++++++++++++++++++++++++++--- ExplorerPatcher/utility.h | 18 ++++++++++++ 2 files changed, 73 insertions(+), 4 deletions(-) diff --git a/ExplorerPatcher/dllmain.c b/ExplorerPatcher/dllmain.c index eebb71f..e0825b8 100644 --- a/ExplorerPatcher/dllmain.c +++ b/ExplorerPatcher/dllmain.c @@ -8180,7 +8180,7 @@ void FixTIFEBreakagesForLegacyControlInterfaces(const MODULEINFO* pmi) ); if (match) { - match += 27; // Align to jump + match += 27; // Point to jump } else { @@ -8195,10 +8195,10 @@ void FixTIFEBreakagesForLegacyControlInterfaces(const MODULEINFO* pmi) ); if (match) { - match += 8; // Align to jump + match += 8; // Point to jump } } - if (match) // Should be aligned to jump at this point + if (match) // Should be pointed to jump at this point { PBYTE target = NULL; DWORD jmpInstrSize = 0; @@ -8239,7 +8239,58 @@ void FixTIFEBreakagesForLegacyControlInterfaces(const MODULEINFO* pmi) } } #elif defined(_M_ARM64) - // ARM64 implementation not done yet + // No TIFE feature flag + // 69 ?? ?? B9 68 ?? ?? B9 69 ?? ?? 29 + // Ref: CInternetToolbar::_CreateBands() + PBYTE match = FindPattern( + pmi->lpBaseOfDll, + pmi->SizeOfImage, + "\x69\x00\x00\xB9\x68\x00\x00\xB9\x69\x00\x00\x29", + "x??xx??xx??x" + ); + if (match) + { + match += 12; // Point to TBZ/TBNZ + } + else + { + // TIFE feature flag present + // 68 ?? ?? B9 68 00 20 36 08 79 1B 12 68 ?? ?? B9 + // ^^^^^^^^^^^ + // Ref: CInternetToolbar::_CreateBands() + match = FindPattern( + pmi->lpBaseOfDll, + pmi->SizeOfImage, + "\x68\x00\x00\xB9\x68\x00\x20\x36\x08\x79\x1B\x12\x68\x00\x00\xB9", + "x??xxxxxxxxxx??x" + ); + if (match) + { + match += 4; // Point to TBZ + } + } + if (match) // Should be pointed to TBZ/TBNZ at this point + { + DWORD insnCurrent = *(DWORD*)match; + DWORD insnNew = 0; + if (ARM64_IsTBZ(insnCurrent)) + { + insnNew = ARM64_TBZToB(insnCurrent); + } + else if (ARM64_IsTBNZ(insnCurrent)) + { + insnNew = 0xD503201F; // NOP + } + if (insnNew != 0) + { + DWORD dwOldProtect; + if (VirtualProtect(match, 4, PAGE_EXECUTE_READWRITE, &dwOldProtect)) + { + *(DWORD*)match = insnNew; + VirtualProtect(match, 4, dwOldProtect, &dwOldProtect); + } + } + } #endif } #pragma endregion diff --git a/ExplorerPatcher/utility.h b/ExplorerPatcher/utility.h index ade6781..052d90b 100644 --- a/ExplorerPatcher/utility.h +++ b/ExplorerPatcher/utility.h @@ -709,6 +709,8 @@ __forceinline UINT_PTR ARM64_Align(UINT_PTR value, UINT_PTR alignment) __forceinline BOOL ARM64_IsCBZW(DWORD insn) { return ARM64_ReadBits(insn, 31, 24) == 0b00110100; } __forceinline BOOL ARM64_IsCBNZW(DWORD insn) { return ARM64_ReadBits(insn, 31, 24) == 0b00110101; } +__forceinline BOOL ARM64_IsTBZ(DWORD insn) { return ARM64_ReadBits(insn, 31, 24) == 0b00110110; } +__forceinline BOOL ARM64_IsTBNZ(DWORD insn) { return ARM64_ReadBits(insn, 31, 24) == 0b00110111; } __forceinline BOOL ARM64_IsBL(DWORD insn) { return ARM64_ReadBits(insn, 31, 26) == 0b100101; } __forceinline BOOL ARM64_IsADRP(DWORD insn) { return (ARM64_ReadBits(insn, 31, 24) & ~0b01100000) == 0b10010000; } __forceinline BOOL ARM64_IsMOVZW(DWORD insn) { return ARM64_ReadBits(insn, 31, 23) == 0b010100101; } @@ -755,6 +757,22 @@ __forceinline DWORD ARM64_CBNZWToB(DWORD insnCBNZW) return ARM64_MakeB(imm19); } +__forceinline DWORD ARM64_TBZToB(DWORD insnTBZ) +{ + if (!ARM64_IsTBZ(insnTBZ)) + return 0; + int imm14 = ARM64_ReadBitsSignExtend(insnTBZ, 18, 5); + return ARM64_MakeB(imm14); +} + +__forceinline DWORD ARM64_TBNZToB(DWORD insnTBNZ) +{ + if (!ARM64_IsTBNZ(insnTBNZ)) + return 0; + int imm14 = ARM64_ReadBitsSignExtend(insnTBNZ, 18, 5); + return ARM64_MakeB(imm14); +} + __forceinline DWORD ARM64_DecodeADD(DWORD insnADD) { DWORD imm12 = ARM64_ReadBits(insnADD, 21, 10);