From cc92e7b719a3f5dc584d261afbcc5dafe880b48c Mon Sep 17 00:00:00 2001 From: kyoubate-haruka <46010460+kyoubate-haruka@users.noreply.github.com> Date: Sat, 25 Oct 2025 10:38:05 +0200 Subject: [PATCH] ekt: hook ShellExecuteExA/W (wtf sega) --- common/hooklib/createprocess.c | 99 +++++++++++++++++++++++++++++++--- common/hooklib/createprocess.h | 1 + games/ekthook/dllmain.c | 7 +++ 3 files changed, 100 insertions(+), 7 deletions(-) diff --git a/common/hooklib/createprocess.c b/common/hooklib/createprocess.c index 6462394..eb1d754 100644 --- a/common/hooklib/createprocess.c +++ b/common/hooklib/createprocess.c @@ -5,11 +5,13 @@ #include #include #include +#include #include "hook/table.h" #include "hooklib/createprocess.h" +#include "hook/procaddr.h" #include "util/dprintf.h" void createprocess_hook_init(); @@ -36,7 +38,15 @@ BOOL my_CreateProcessW( LPCWSTR lpCurrentDirectory, LPSTARTUPINFOW lpStartupInfo, LPPROCESS_INFORMATION lpProcessInformation -); + ); + +BOOL my_ShellExecuteExA(SHELLEXECUTEINFOA *pExecInfo); + +BOOL my_ShellExecuteExW(SHELLEXECUTEINFOW *pExecInfo); + +static BOOL (WINAPI *next_ShellExecuteExA)(SHELLEXECUTEINFOA *pExecInfo); + +static BOOL (WINAPI *next_ShellExecuteExW)(SHELLEXECUTEINFOW *pExecInfo); static BOOL (WINAPI *next_CreateProcessA)( LPCSTR lpApplicationName, @@ -76,6 +86,18 @@ static const struct hook_symbol win32_hooks[] = { .link = (void **) &next_CreateProcessW }, }; +static const struct hook_symbol shell32_hooks[] = { + { + .name = "ShellExecuteExA", + .patch = my_ShellExecuteExA, + .link = (void **) &next_ShellExecuteExA + }, + { + .name = "ShellExecuteExW", + .patch = my_ShellExecuteExW, + .link = (void **) &next_ShellExecuteExW + }, +}; static bool did_init = false; @@ -157,18 +179,31 @@ HRESULT createprocess_push_hook_a(const char *name, const char *head, const char return S_OK; } +void createprocess_hook_apply_hooks(HMODULE mod) { + hook_table_apply( + mod, + "kernel32.dll", + win32_hooks, + _countof(win32_hooks)); + hook_table_apply( + mod, + "shell32.dll", + shell32_hooks, + _countof(shell32_hooks)); + + proc_addr_table_push(mod, "kernel32.dll", win32_hooks, _countof(win32_hooks)); + proc_addr_table_push(mod, "shell32.dll", shell32_hooks, _countof(shell32_hooks)); + + InitializeCriticalSection(&createproc_lock); +} + void createprocess_hook_init() { if (did_init) { return; } did_init = true; - hook_table_apply( - NULL, - "kernel32.dll", - win32_hooks, - _countof(win32_hooks)); - InitializeCriticalSection(&createproc_lock); + createprocess_hook_apply_hooks(NULL); dprintf("CreateProcess: Init\n"); } @@ -255,4 +290,54 @@ BOOL my_CreateProcessW( lpStartupInfo, lpProcessInformation ); +} + +BOOL my_ShellExecuteExA(SHELLEXECUTEINFOA *pExecInfo) { + for (int i = 0; i < process_nsyms_a; i++) { + if (strncmp(process_syms_a[i].name, pExecInfo->lpFile, strlen(process_syms_a[i].name))) { + continue; + } + + dprintf("CreateProcess: Hooking child process %s %s\n", pExecInfo->lpFile, pExecInfo->lpParameters); + char new_args[MAX_PATH] = {0}; + strcat_s(new_args, MAX_PATH, process_syms_a[i].head); + + if (!process_syms_a[i].replace_all) { + strcat_s(new_args, MAX_PATH, pExecInfo->lpParameters); + } + + if (process_syms_a[i].tail != NULL) { + strcat_s(new_args, MAX_PATH, process_syms_a[i].tail); + } + + pExecInfo->lpParameters = new_args; + + dprintf("CreateProcess: Replaced ShellExecuteExA %s %s\n", pExecInfo->lpFile, new_args); + } + return next_ShellExecuteExA(pExecInfo); +} + +BOOL my_ShellExecuteExW(SHELLEXECUTEINFOW *pExecInfo) { + for (int i = 0; i < process_nsyms_w; i++) { + if (wcsncmp(process_syms_w[i].name, pExecInfo->lpFile, wcslen(process_syms_w[i].name))) { + continue; + } + + dprintf("CreateProcess: Hooking child process %ls %ls\n", pExecInfo->lpFile, pExecInfo->lpParameters); + wchar_t new_args[MAX_PATH] = {0}; + wcscat_s(new_args, MAX_PATH, process_syms_w[i].head); + + if (!process_syms_w[i].replace_all) { + wcscat_s(new_args, MAX_PATH, pExecInfo->lpParameters); + } + + if (process_syms_w[i].tail != NULL) { + wcscat_s(new_args, MAX_PATH, process_syms_w[i].tail); + } + + pExecInfo->lpParameters = new_args; + + dprintf("CreateProcess: Replaced ShellExecuteExW %ls %ls\n", pExecInfo->lpFile, new_args); + } + return next_ShellExecuteExW(pExecInfo); } \ No newline at end of file diff --git a/common/hooklib/createprocess.h b/common/hooklib/createprocess.h index bf226d5..462523e 100644 --- a/common/hooklib/createprocess.h +++ b/common/hooklib/createprocess.h @@ -5,6 +5,7 @@ HRESULT createprocess_push_hook_w(const wchar_t *name, const wchar_t *head, const wchar_t *tail, bool replace_all); HRESULT createprocess_push_hook_a(const char *name, const char *head, const char *tail, bool replace_all); +void createprocess_hook_apply_hooks(HMODULE mod); struct process_hook_sym_w { const wchar_t *name; diff --git a/games/ekthook/dllmain.c b/games/ekthook/dllmain.c index 305a995..a16bf6c 100644 --- a/games/ekthook/dllmain.c +++ b/games/ekthook/dllmain.c @@ -18,6 +18,7 @@ COM3: 837-15093-06 LED Controller Board */ +#include #include #include @@ -34,6 +35,7 @@ #include "ekthook/config.h" #include "ekthook/io4.h" +#include "hooklib/createprocess.h" #include "hooklib/printer_cx.h" #include "platform/platform.h" @@ -51,6 +53,7 @@ static struct ekt_hook_config ekt_hook_cfg; static void unity_hook_callback(HMODULE hmodule, const wchar_t* p) { netenv_hook_apply_hooks(hmodule); + createprocess_hook_apply_hooks(hmodule); } static DWORD CALLBACK ekt_pre_startup(void) @@ -69,6 +72,10 @@ static DWORD CALLBACK ekt_pre_startup(void) dvd_hook_init(&ekt_hook_cfg.dvd, ekt_hook_mod); serial_hook_init(); + wchar_t video_path_hook[MAX_PATH]; + swprintf(video_path_hook, MAX_PATH, L"file createnew %ls\\SDGY\\EtUpload\\live\\video_0.ts 524288", ekt_hook_cfg.platform.vfs.appdata); + createprocess_push_hook_w(L"fsutil", L"", video_path_hook, true); + /* Hook external DLL APIs */ hr = y3_hook_init(&ekt_hook_cfg.y3, ekt_hook_mod, get_config_path());