forked from TeamTofuShop/segatools
switched to new capnhook, updated unityhook, added LED 15093 to MU3
This commit is contained in:
@ -23,8 +23,6 @@ hooklib_lib = static_library(
|
||||
'fdshark.h',
|
||||
'path.c',
|
||||
'path.h',
|
||||
'procaddr.c',
|
||||
'procaddr.h',
|
||||
'reg.c',
|
||||
'reg.h',
|
||||
'setupapi.c',
|
||||
|
@ -1,125 +0,0 @@
|
||||
#include <windows.h>
|
||||
#include <stdbool.h>
|
||||
#include <stdint.h>
|
||||
#include <libgen.h>
|
||||
|
||||
#include "hooklib/procaddr.h"
|
||||
|
||||
#include "hook/table.h"
|
||||
|
||||
#include "util/dprintf.h"
|
||||
|
||||
static struct proc_addr_table *proc_addr_hook_list;
|
||||
static size_t proc_addr_hook_count;
|
||||
static CRITICAL_SECTION proc_addr_hook_lock;
|
||||
static bool proc_addr_hook_initted;
|
||||
|
||||
static FARPROC WINAPI my_GetProcAddress(HMODULE hModule, const char *name);
|
||||
static FARPROC (WINAPI *next_GetProcAddress)(HMODULE hModule, const char *name);
|
||||
static void proc_addr_hook_init(void);
|
||||
|
||||
static const struct hook_symbol win32_hooks[] = {
|
||||
{
|
||||
.name = "GetProcAddress",
|
||||
.patch = my_GetProcAddress,
|
||||
.link = (void **) &next_GetProcAddress
|
||||
}
|
||||
};
|
||||
|
||||
HRESULT proc_addr_table_push(
|
||||
const char *target,
|
||||
struct hook_symbol *syms,
|
||||
size_t nsyms
|
||||
)
|
||||
{
|
||||
HRESULT hr;
|
||||
struct proc_addr_table *new_item;
|
||||
struct proc_addr_table *new_mem;
|
||||
|
||||
proc_addr_hook_init();
|
||||
|
||||
EnterCriticalSection(&proc_addr_hook_lock);
|
||||
|
||||
new_mem = realloc(
|
||||
proc_addr_hook_list,
|
||||
(proc_addr_hook_count + 1) * sizeof(struct proc_addr_table));
|
||||
|
||||
if (new_mem == NULL) {
|
||||
hr = E_OUTOFMEMORY;
|
||||
|
||||
LeaveCriticalSection(&proc_addr_hook_lock);
|
||||
return hr;
|
||||
}
|
||||
|
||||
new_item = &new_mem[proc_addr_hook_count];
|
||||
new_item->name = target;
|
||||
new_item->nsyms = nsyms;
|
||||
new_item->syms = syms;
|
||||
|
||||
proc_addr_hook_list = new_mem;
|
||||
proc_addr_hook_count++;
|
||||
hr = S_OK;
|
||||
|
||||
LeaveCriticalSection(&proc_addr_hook_lock);
|
||||
|
||||
return hr;
|
||||
}
|
||||
|
||||
static void proc_addr_hook_init(void)
|
||||
{
|
||||
if (proc_addr_hook_initted) {
|
||||
return;
|
||||
}
|
||||
|
||||
dprintf("ProcAddr: Hook init\n");
|
||||
proc_addr_hook_initted = true;
|
||||
|
||||
InitializeCriticalSection(&proc_addr_hook_lock);
|
||||
|
||||
hook_table_apply(
|
||||
NULL,
|
||||
"kernel32.dll",
|
||||
win32_hooks,
|
||||
_countof(win32_hooks));
|
||||
}
|
||||
|
||||
FARPROC WINAPI my_GetProcAddress(HMODULE hModule, const char *name)
|
||||
{
|
||||
uintptr_t ordinal = (uintptr_t) name;
|
||||
char mod_path[PATH_MAX];
|
||||
char *mod_name;
|
||||
const struct hook_symbol *sym;
|
||||
FARPROC result = next_GetProcAddress(hModule, name);
|
||||
|
||||
GetModuleFileNameA(hModule, mod_path, PATH_MAX);
|
||||
mod_name = basename(mod_path);
|
||||
|
||||
for (int i = 0; i < proc_addr_hook_count; i++) {
|
||||
|
||||
if (strcmp(proc_addr_hook_list[i].name, mod_name) == 0) {
|
||||
|
||||
for (int j = 0; j < proc_addr_hook_list[i].nsyms; j++) {
|
||||
sym = &proc_addr_hook_list[i].syms[j];
|
||||
|
||||
if (ordinal > 0xFFFF) {
|
||||
|
||||
if (strcmp(sym->name, name) == 0) {
|
||||
|
||||
dprintf("ProcAddr: Hooking %s from %s\n", name, mod_name);
|
||||
result = (FARPROC) sym->patch;
|
||||
}
|
||||
}
|
||||
|
||||
else {
|
||||
if (sym->ordinal == ordinal) {
|
||||
|
||||
dprintf("ProcAddr: Hooking Ord %p from %s\n", (void *)ordinal, mod_name);
|
||||
result = (FARPROC) sym->patch;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
@ -1,18 +0,0 @@
|
||||
#pragma once
|
||||
#include <windows.h>
|
||||
#include <stdbool.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include "hook/table.h"
|
||||
|
||||
struct proc_addr_table {
|
||||
const char *name;
|
||||
size_t nsyms;
|
||||
struct hook_symbol *syms;
|
||||
};
|
||||
|
||||
HRESULT proc_addr_table_push(
|
||||
const char *target,
|
||||
struct hook_symbol *syms,
|
||||
size_t nsyms
|
||||
);
|
165
hooklib/reg.c
165
hooklib/reg.c
@ -7,6 +7,7 @@
|
||||
#include "hook/table.h"
|
||||
|
||||
#include "hooklib/reg.h"
|
||||
#include "hook/procaddr.h"
|
||||
|
||||
#include "util/dprintf.h"
|
||||
#include "util/str.h"
|
||||
@ -99,6 +100,29 @@ static LSTATUS WINAPI hook_RegGetValueW(
|
||||
uint32_t *numData
|
||||
);
|
||||
|
||||
static LSTATUS WINAPI hook_RegQueryInfoKeyW(
|
||||
HKEY hKey,
|
||||
LPWSTR lpClass,
|
||||
LPDWORD lpcchClass,
|
||||
LPDWORD lpReserved,
|
||||
LPDWORD lpcSubKeys,
|
||||
LPDWORD lpcbMaxSubKeyLen,
|
||||
LPDWORD lpcbMaxClassLen,
|
||||
LPDWORD lpcValues,
|
||||
LPDWORD lpcbMaxValueNameLen,
|
||||
LPDWORD lpcbMaxValueLen,
|
||||
LPDWORD lpcbSecurityDescriptor,
|
||||
PFILETIME lpftLastWriteTime);
|
||||
|
||||
static LSTATUS WINAPI hook_RegEnumValueW(
|
||||
HKEY hkey,
|
||||
DWORD dwIndex,
|
||||
LPWSTR lpValueName,
|
||||
LPDWORD lpcchValueName,
|
||||
LPDWORD lpReserved,
|
||||
LPDWORD lpType,
|
||||
LPBYTE lpData,
|
||||
LPDWORD lpcbData);
|
||||
/* Link pointers */
|
||||
|
||||
static LSTATUS (WINAPI *next_RegOpenKeyExW)(
|
||||
@ -155,6 +179,30 @@ static LSTATUS (WINAPI *next_RegGetValueW)(
|
||||
uint32_t *numData
|
||||
);
|
||||
|
||||
static LSTATUS (WINAPI *next_RegQueryInfoKeyW)(
|
||||
HKEY hKey,
|
||||
LPWSTR lpClass,
|
||||
LPDWORD lpcchClass,
|
||||
LPDWORD lpReserved,
|
||||
LPDWORD lpcSubKeys,
|
||||
LPDWORD lpcbMaxSubKeyLen,
|
||||
LPDWORD lpcbMaxClassLen,
|
||||
LPDWORD lpcValues,
|
||||
LPDWORD lpcbMaxValueNameLen,
|
||||
LPDWORD lpcbMaxValueLen,
|
||||
LPDWORD lpcbSecurityDescriptor,
|
||||
PFILETIME lpftLastWriteTime);
|
||||
|
||||
static LSTATUS (WINAPI *next_RegEnumValueW)(
|
||||
HKEY hkey,
|
||||
DWORD dwIndex,
|
||||
LPWSTR lpValueName,
|
||||
LPDWORD lpcchValueName,
|
||||
LPDWORD lpReserved,
|
||||
LPDWORD lpType,
|
||||
LPBYTE lpData,
|
||||
LPDWORD lpcbData);
|
||||
|
||||
static const struct hook_symbol reg_hook_syms[] = {
|
||||
{
|
||||
.name = "RegOpenKeyExW",
|
||||
@ -184,6 +232,14 @@ static const struct hook_symbol reg_hook_syms[] = {
|
||||
.name = "RegGetValueW",
|
||||
.patch = hook_RegGetValueW,
|
||||
.link = (void **) &next_RegGetValueW,
|
||||
}, {
|
||||
.name = "RegQueryInfoKeyW",
|
||||
.patch = hook_RegQueryInfoKeyW,
|
||||
.link = (void **) &next_RegQueryInfoKeyW,
|
||||
}, {
|
||||
.name = "RegEnumValueW",
|
||||
.patch = hook_RegEnumValueW,
|
||||
.link = (void **) &next_RegEnumValueW,
|
||||
}
|
||||
};
|
||||
|
||||
@ -254,11 +310,24 @@ static void reg_hook_init(void)
|
||||
InitializeCriticalSection(®_hook_lock);
|
||||
dprintf("Reg hook init\n");
|
||||
|
||||
reg_hook_insert_hooks(NULL);
|
||||
|
||||
proc_addr_table_push(
|
||||
NULL,
|
||||
"ADVAPI32.dll",
|
||||
(struct hook_symbol *) reg_hook_syms,
|
||||
_countof(reg_hook_syms));
|
||||
|
||||
}
|
||||
|
||||
void reg_hook_insert_hooks(HMODULE target)
|
||||
{
|
||||
hook_table_apply(
|
||||
NULL,
|
||||
target,
|
||||
"advapi32.dll",
|
||||
reg_hook_syms,
|
||||
_countof(reg_hook_syms));
|
||||
|
||||
}
|
||||
|
||||
static LRESULT reg_hook_propagate_hr(HRESULT hr)
|
||||
@ -331,6 +400,7 @@ static LSTATUS reg_hook_open_locked(
|
||||
/* Assume reg keys are referenced from a root key and not from some
|
||||
intermediary key */
|
||||
key = ®_hook_keys[i];
|
||||
//dprintf("Reg: %ls vs %ls\n", name, key->name);
|
||||
|
||||
if (key->root == parent && wstr_ieq(key->name, name)) {
|
||||
break;
|
||||
@ -821,6 +891,99 @@ static LSTATUS WINAPI hook_RegGetValueW(
|
||||
return err;
|
||||
}
|
||||
|
||||
static LSTATUS WINAPI hook_RegQueryInfoKeyW(
|
||||
HKEY hKey,
|
||||
LPWSTR lpClass,
|
||||
LPDWORD lpcchClass,
|
||||
LPDWORD lpReserved,
|
||||
LPDWORD lpcSubKeys,
|
||||
LPDWORD lpcbMaxSubKeyLen,
|
||||
LPDWORD lpcbMaxClassLen,
|
||||
LPDWORD lpcValues,
|
||||
LPDWORD lpcbMaxValueNameLen,
|
||||
LPDWORD lpcbMaxValueLen,
|
||||
LPDWORD lpcbSecurityDescriptor,
|
||||
PFILETIME lpftLastWriteTime)
|
||||
{
|
||||
struct reg_hook_key *key;
|
||||
LSTATUS err;
|
||||
|
||||
EnterCriticalSection(®_hook_lock);
|
||||
|
||||
key = reg_hook_match_key_locked(hKey);
|
||||
|
||||
/* Check if this is a virtualized registry key */
|
||||
|
||||
if (key == NULL) {
|
||||
LeaveCriticalSection(®_hook_lock);
|
||||
|
||||
return next_RegQueryInfoKeyW(
|
||||
hKey,
|
||||
lpClass,
|
||||
lpcchClass,
|
||||
lpReserved,
|
||||
lpcSubKeys,
|
||||
lpcbMaxSubKeyLen,
|
||||
lpcbMaxClassLen,
|
||||
lpcValues,
|
||||
lpcbMaxValueNameLen,
|
||||
lpcbMaxValueLen,
|
||||
lpcbSecurityDescriptor,
|
||||
lpftLastWriteTime);
|
||||
}
|
||||
|
||||
// This is the only one I've seen even be changed, so it's all I'm doing
|
||||
// until I see otherwise.
|
||||
*lpcValues = key->nvals;
|
||||
LeaveCriticalSection(®_hook_lock);
|
||||
return ERROR_SUCCESS;
|
||||
}
|
||||
|
||||
static LSTATUS WINAPI hook_RegEnumValueW(
|
||||
HKEY hkey,
|
||||
DWORD dwIndex,
|
||||
LPWSTR lpValueName,
|
||||
LPDWORD lpcchValueName,
|
||||
LPDWORD lpReserved,
|
||||
LPDWORD lpType,
|
||||
LPBYTE lpData,
|
||||
LPDWORD lpcbData)
|
||||
{
|
||||
struct reg_hook_key *key;
|
||||
HRESULT hr;
|
||||
LSTATUS err;
|
||||
|
||||
EnterCriticalSection(®_hook_lock);
|
||||
|
||||
key = reg_hook_match_key_locked(hkey);
|
||||
|
||||
/* Check if this is a virtualized registry key */
|
||||
|
||||
if (key == NULL) {
|
||||
LeaveCriticalSection(®_hook_lock);
|
||||
|
||||
return next_RegEnumValueW(
|
||||
hkey,
|
||||
dwIndex,
|
||||
lpValueName,
|
||||
lpcchValueName,
|
||||
lpReserved,
|
||||
lpType,
|
||||
lpData,
|
||||
lpcbData);
|
||||
}
|
||||
|
||||
if (dwIndex >= key->nvals) {
|
||||
LeaveCriticalSection(®_hook_lock);
|
||||
return ERROR_NO_MORE_ITEMS; // Pretty sure this is what it actually returns here?
|
||||
}
|
||||
|
||||
wcscpy_s(lpValueName, *lpcchValueName, key->vals[dwIndex].name);
|
||||
*lpcchValueName = wcslen(key->vals[dwIndex].name);
|
||||
LeaveCriticalSection(®_hook_lock);
|
||||
return ERROR_SUCCESS;
|
||||
}
|
||||
|
||||
HRESULT reg_hook_read_bin(
|
||||
void *bytes,
|
||||
uint32_t *nbytes,
|
||||
|
@ -12,6 +12,8 @@ struct reg_hook_val {
|
||||
uint32_t type;
|
||||
};
|
||||
|
||||
void reg_hook_insert_hooks(HMODULE target);
|
||||
|
||||
HRESULT reg_hook_push_key(
|
||||
HKEY root,
|
||||
const wchar_t *name,
|
||||
|
@ -119,10 +119,19 @@ void touch_screen_hook_init(const struct touch_screen_config *cfg, HINSTANCE sel
|
||||
defaultCursor = LoadCursorA(NULL, IDC_CROSS);
|
||||
|
||||
memcpy(&touch_config, cfg, sizeof(*cfg));
|
||||
hook_table_apply(NULL, "user32.dll", touch_hooks, _countof(touch_hooks));
|
||||
touch_hook_insert_hooks(NULL);
|
||||
dprintf("TOUCH: hook enabled.\n");
|
||||
}
|
||||
|
||||
void touch_hook_insert_hooks(HMODULE target)
|
||||
{
|
||||
hook_table_apply(
|
||||
target,
|
||||
"user32.dll",
|
||||
touch_hooks,
|
||||
_countof(touch_hooks));
|
||||
}
|
||||
|
||||
static HCURSOR WINAPI hook_SetCursor(HCURSOR cursor) {
|
||||
if (cursor == 0 && touch_config.cursor)
|
||||
return next_SetCursor(defaultCursor);
|
||||
|
@ -14,3 +14,4 @@ struct touch_screen_config {
|
||||
blah blah you know the drill by now. */
|
||||
|
||||
void touch_screen_hook_init(const struct touch_screen_config *cfg, HINSTANCE self);
|
||||
void touch_hook_insert_hooks(HMODULE target);
|
||||
|
Reference in New Issue
Block a user