Skip to content

Commit

Permalink
Taskbar11: Fixed a bug that crashed explorer.exe when right clickin…
Browse files Browse the repository at this point in the history
…g the new taskbar on Windows 11 builds with "Never combine" on the new taskbar
  • Loading branch information
Amrsatrio committed Sep 24, 2023
1 parent bc3bbc7 commit 6023718
Showing 1 changed file with 50 additions and 28 deletions.
78 changes: 50 additions & 28 deletions ExplorerPatcher/dllmain.c
Original file line number Diff line number Diff line change
Expand Up @@ -2411,6 +2411,8 @@ LRESULT CALLBACK Shell_TrayWndMouseProc(
return CallNextHookEx(Shell_TrayWndMouseHook, nCode, wParam, lParam);
}

PBYTE g_pTrayUIHost;

INT64 Shell_TrayWndSubclassProc(
_In_ HWND hWnd,
_In_ UINT uMsg,
Expand Down Expand Up @@ -2492,29 +2494,25 @@ INT64 Shell_TrayWndSubclassProc(
}
DeleteMenu(hSubMenu, 424, MF_BYCOMMAND); // Lock the taskbar
DeleteMenu(hSubMenu, 425, MF_BYCOMMAND); // Lock all taskbars
HWND hShellTray_Wnd = FindWindowExW(NULL, NULL, L"Shell_TrayWnd", NULL);
INT64* CTrayInstance = (BYTE*)(GetWindowLongPtrW(hShellTray_Wnd, 0)); // -> CTray
const unsigned int TRAYUI_OFFSET_IN_CTRAY = 110;
uintptr_t TrayUIInstance = *((INT64*)CTrayInstance + TRAYUI_OFFSET_IN_CTRAY) + 8;
if (TrayUIInstance)
if (g_pTrayUIHost)
{
int offset = 656;
if (IsWindows11Version22H2OrHigher()) offset = 640;
if (IsWindows11Version22H2Build2134OrHigher()) offset = 648;
if ((*(unsigned __int8(__fastcall**)(INT64))(**(INT64**)(TrayUIInstance + offset) + 104i64))(*(INT64*)(TrayUIInstance + offset)))
void** pTrayUIHostVtbl = *(void***)g_pTrayUIHost;
BOOL (*ShouldDeleteContextMenuUndo)(PBYTE) = pTrayUIHostVtbl[13];
UINT (*GetContextMenuUndoResourceId)(PBYTE) = pTrayUIHostVtbl[14];

if (ShouldDeleteContextMenuUndo(g_pTrayUIHost))
{
DeleteMenu(hSubMenu, 0x1A0u, 0);
DeleteMenu(hSubMenu, 416, MF_BYCOMMAND);
}
else
{
WCHAR Buffer[MAX_PATH];
WCHAR v40[MAX_PATH];
WCHAR NewItem[MAX_PATH];
LoadStringW(GetModuleHandleW(NULL), 0x216u, Buffer, 64);
UINT v22 = (*(__int64(__fastcall**)(INT64))(**(INT64**)(TrayUIInstance + offset) + 112i64))(*(INT64*)(TrayUIInstance + offset));
LoadStringW(GetModuleHandleW(NULL), v22, v40, 96);
swprintf_s(NewItem, 0xA0ui64, Buffer, v40);
ModifyMenuW(hSubMenu, 0x1A0u, 0, 0x1A0ui64, NewItem);
WCHAR wszTemplate[64];
WCHAR wszCommand[96];
WCHAR wszMenu[160];
LoadStringW(GetModuleHandleW(NULL), 534, wszTemplate, 64);
LoadStringW(GetModuleHandleW(NULL), GetContextMenuUndoResourceId(g_pTrayUIHost), wszCommand, 96);
swprintf_s(wszMenu, 160, wszTemplate, wszCommand);
ModifyMenuW(hSubMenu, 416, MF_BYCOMMAND, 416, wszMenu);
}
}
else
Expand Down Expand Up @@ -10715,6 +10713,8 @@ DWORD Inject(BOOL bIsExplorer)


HANDLE hExplorer = GetModuleHandleW(NULL);
MODULEINFO miExplorer;
GetModuleInformation(GetCurrentProcess(), hExplorer, &miExplorer, sizeof(MODULEINFO));
SetChildWindowNoActivateFunc = GetProcAddress(GetModuleHandleW(L"user32.dll"), (LPCSTR)2005);
if (bOldTaskbar)
{
Expand Down Expand Up @@ -10784,7 +10784,29 @@ DWORD Inject(BOOL bIsExplorer)
VnPatchIAT(hExplorer, "dwmapi.dll", "DwmUpdateThumbnailProperties", explorer_DwmUpdateThumbnailPropertiesHook);
PatchExplorer_UpdateWindowAccentProperties();
}

if (IsWindows11())
{
// Find a pointer to ITrayUIHost needed to have a working Windows 10 taskbar context menu on Windows 11 taskbar
// Ref: CTray::Init()
// 4C 8D 05 ? ? ? ? 48 8D 0D ? ? ? ? E8 ? ? ? ? 48 8B 8D
// ^^^^^^^
PBYTE match = FindPattern(
hExplorer,
miExplorer.SizeOfImage,
"\x4C\x8D\x05\x00\x00\x00\x00\x48\x8D\x0D\x00\x00\x00\x00\xE8\x00\x00\x00\x00\x48\x8B\x8D",
"xxx????xxx????x????xxx"
);
if (match)
{
match += 7;
g_pTrayUIHost = match + 7 + *(int*)(match + 3);
printf("ITrayUIHost = %llX\n", g_pTrayUIHost - (PBYTE)hExplorer);
}
else
{
printf("Failed to find ITrayUIHost, the custom Windows 11 taskbar context menu will not have the undo function\n");
}
}

HANDLE hShcore = LoadLibraryW(L"shcore.dll");
SHWindowsPolicy = GetProcAddress(hShcore, (LPCSTR)190);
Expand Down Expand Up @@ -10857,7 +10879,7 @@ DWORD Inject(BOOL bIsExplorer)
// ^^^^^^^
PBYTE match = FindPattern(
hTwinuiPcshell,
miTwinuiPcshell.lpBaseOfDll,
miTwinuiPcshell.SizeOfImage,
"\x4D\x8B\xCF\x4D\x8B\xC4\x8B\xD6\x48\x8B\x49\x08\xE8\x00\x00\x00\x00\xE9",
"xxxxxxxxxxxxx????x"
);
Expand All @@ -10873,7 +10895,7 @@ DWORD Inject(BOOL bIsExplorer)
// 48 89 5C 24 ? 48 89 74 24 ? 57 48 83 EC 30 49 8B D8 48 8B FA 48 8B F1 49 83 20 00 41 B0 03 B2 01
PBYTE match = FindPattern(
hTwinuiPcshell,
miTwinuiPcshell.lpBaseOfDll,
miTwinuiPcshell.SizeOfImage,
"\x48\x89\x5C\x24\x00\x48\x89\x74\x24\x00\x57\x48\x83\xEC\x30\x49\x8B\xD8\x48\x8B\xFA\x48\x8B\xF1\x49\x83\x20\x00\x41\xB0\x03\xB2\x01",
"xxxx?xxxx?xxxxxxxxxxxxxxxxxxxxxxx"
);
Expand All @@ -10890,7 +10912,7 @@ DWORD Inject(BOOL bIsExplorer)
// ^^^^^^^
PBYTE match = FindPattern(
hTwinuiPcshell,
miTwinuiPcshell.lpBaseOfDll,
miTwinuiPcshell.SizeOfImage,
"\xE8\x00\x00\x00\x00\xE8\x00\x00\x00\x00\x0F\xB7\xC8\xE8\x00\x00\x00\x00\xF7\xD8",
"x????x????xxxx????xx"
);
Expand All @@ -10907,7 +10929,7 @@ DWORD Inject(BOOL bIsExplorer)
// ^^^^^^^
PBYTE match = FindPattern(
hTwinuiPcshell,
miTwinuiPcshell.lpBaseOfDll,
miTwinuiPcshell.SizeOfImage,
"\xE8\x00\x00\x00\x00\x85\xDB\x74\x29",
"x????xxxx"
);
Expand All @@ -10923,7 +10945,7 @@ DWORD Inject(BOOL bIsExplorer)
// ^^^^^^^
PBYTE match = FindPattern(
hTwinuiPcshell,
miTwinuiPcshell.lpBaseOfDll,
miTwinuiPcshell.SizeOfImage,
"\xE8\x00\x00\x00\x00\x90\x49\x8D\x56\x38\x49\x8B\xCE",
"x????xxxxxxxx"
);
Expand All @@ -10939,7 +10961,7 @@ DWORD Inject(BOOL bIsExplorer)
// ^^^^^^^
PBYTE match = FindPattern(
hTwinuiPcshell,
miTwinuiPcshell.lpBaseOfDll,
miTwinuiPcshell.SizeOfImage,
"\xE8\x00\x00\x00\x00\x90\x48\x8D\x56\x38\x48\x8B\xCE",
"x????xxxxxxxx"
);
Expand All @@ -10954,7 +10976,7 @@ DWORD Inject(BOOL bIsExplorer)
// 48 83 EC 28 41 B0 03 B2 01
PBYTE match = FindPattern(
hTwinuiPcshell,
miTwinuiPcshell.lpBaseOfDll,
miTwinuiPcshell.SizeOfImage,
"\x48\x83\xEC\x28\x41\xB0\x03\xB2\x01",
"xxxxxxxxx"
);
Expand All @@ -10971,7 +10993,7 @@ DWORD Inject(BOOL bIsExplorer)
// ^^^^^^^
PBYTE match = FindPattern(
hTwinuiPcshell,
miTwinuiPcshell.lpBaseOfDll,
miTwinuiPcshell.SizeOfImage,
"\x4C\x89\x74\x24\x00\x00\x8B\x00\x00\x8B\x00\x8B\xD7\x48\x8B\xCE\xE8\x00\x00\x00\x00\x8B",
"xxxx??x??x?xxxxxx????x"
);
Expand All @@ -10989,7 +11011,7 @@ DWORD Inject(BOOL bIsExplorer)
// ^^^^^^^
PBYTE match = FindPattern(
hTwinuiPcshell,
miTwinuiPcshell.lpBaseOfDll,
miTwinuiPcshell.SizeOfImage,
"\x4C\x89\x74\x24\x00\x00\x8B\x00\x00\x8B\x00\x8B\xD7\x48\x8B\xCE\xE8\x00\x00\x00\x00\x90",
"xxxx??x??x?xxxxxx????x"
);
Expand Down

0 comments on commit 6023718

Please sign in to comment.