CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutSign UpSign In
hrydgard

CoCalc provides the best real-time collaborative environment for Jupyter Notebooks, LaTeX documents, and SageMath, scalable from individual users to large groups and classes!

GitHub Repository: hrydgard/ppsspp
Path: blob/master/Windows/W32Util/IatHook.h
Views: 1401
1
// This file contains code from
2
// https://github.com/stevemk14ebr/PolyHook_2_0/blob/master/sources/IatHook.cpp
3
// which is licensed under the MIT License.
4
// See PolyHook_2_0-LICENSE for more information.
5
6
#pragma once
7
8
#include "Common/CommonWindows.h"
9
#include <cstdint>
10
#include <winnt.h>
11
12
template <typename T, typename T1, typename T2>
13
constexpr T RVA2VA(T1 base, T2 rva)
14
{
15
return reinterpret_cast<T>(reinterpret_cast<ULONG_PTR>(base) + rva);
16
}
17
18
template <typename T>
19
constexpr T DataDirectoryFromModuleBase(void *moduleBase, size_t entryID)
20
{
21
auto dosHdr = reinterpret_cast<PIMAGE_DOS_HEADER>(moduleBase);
22
auto ntHdr = RVA2VA<PIMAGE_NT_HEADERS>(moduleBase, dosHdr->e_lfanew);
23
auto dataDir = ntHdr->OptionalHeader.DataDirectory;
24
return RVA2VA<T>(moduleBase, dataDir[entryID].VirtualAddress);
25
}
26
27
inline PIMAGE_THUNK_DATA FindAddressByName(void *moduleBase, PIMAGE_THUNK_DATA impName, PIMAGE_THUNK_DATA impAddr, const char *funcName)
28
{
29
for (; impName->u1.Ordinal; ++impName, ++impAddr)
30
{
31
if (IMAGE_SNAP_BY_ORDINAL(impName->u1.Ordinal))
32
continue;
33
34
auto import = RVA2VA<PIMAGE_IMPORT_BY_NAME>(moduleBase, impName->u1.AddressOfData);
35
if (strcmp(import->Name, funcName) != 0)
36
continue;
37
return impAddr;
38
}
39
return nullptr;
40
}
41
42
inline PIMAGE_THUNK_DATA FindAddressByOrdinal(void *moduleBase, PIMAGE_THUNK_DATA impName, PIMAGE_THUNK_DATA impAddr, uint16_t ordinal)
43
{
44
for (; impName->u1.Ordinal; ++impName, ++impAddr)
45
{
46
if (IMAGE_SNAP_BY_ORDINAL(impName->u1.Ordinal) && IMAGE_ORDINAL(impName->u1.Ordinal) == ordinal)
47
return impAddr;
48
}
49
return nullptr;
50
}
51
52
inline PIMAGE_THUNK_DATA FindIatThunkInModule(void *moduleBase, const char *dllName, const char *funcName)
53
{
54
auto imports = DataDirectoryFromModuleBase<PIMAGE_IMPORT_DESCRIPTOR>(moduleBase, IMAGE_DIRECTORY_ENTRY_IMPORT);
55
for (; imports->Name; ++imports)
56
{
57
if (_stricmp(RVA2VA<LPCSTR>(moduleBase, imports->Name), dllName) != 0)
58
continue;
59
60
auto origThunk = RVA2VA<PIMAGE_THUNK_DATA>(moduleBase, imports->OriginalFirstThunk);
61
auto thunk = RVA2VA<PIMAGE_THUNK_DATA>(moduleBase, imports->FirstThunk);
62
return FindAddressByName(moduleBase, origThunk, thunk, funcName);
63
}
64
return nullptr;
65
}
66
67
inline PIMAGE_THUNK_DATA FindDelayLoadThunkInModule(void *moduleBase, const char *dllName, const char *funcName)
68
{
69
auto imports = DataDirectoryFromModuleBase<PIMAGE_DELAYLOAD_DESCRIPTOR>(moduleBase, IMAGE_DIRECTORY_ENTRY_DELAY_IMPORT);
70
for (; imports->DllNameRVA; ++imports)
71
{
72
if (_stricmp(RVA2VA<LPCSTR>(moduleBase, imports->DllNameRVA), dllName) != 0)
73
continue;
74
75
auto impName = RVA2VA<PIMAGE_THUNK_DATA>(moduleBase, imports->ImportNameTableRVA);
76
auto impAddr = RVA2VA<PIMAGE_THUNK_DATA>(moduleBase, imports->ImportAddressTableRVA);
77
return FindAddressByName(moduleBase, impName, impAddr, funcName);
78
}
79
return nullptr;
80
}
81
82
inline PIMAGE_THUNK_DATA FindDelayLoadThunkInModule(void *moduleBase, const char *dllName, uint16_t ordinal)
83
{
84
auto imports = DataDirectoryFromModuleBase<PIMAGE_DELAYLOAD_DESCRIPTOR>(moduleBase, IMAGE_DIRECTORY_ENTRY_DELAY_IMPORT);
85
for (; imports->DllNameRVA; ++imports)
86
{
87
if (_stricmp(RVA2VA<LPCSTR>(moduleBase, imports->DllNameRVA), dllName) != 0)
88
continue;
89
90
auto impName = RVA2VA<PIMAGE_THUNK_DATA>(moduleBase, imports->ImportNameTableRVA);
91
auto impAddr = RVA2VA<PIMAGE_THUNK_DATA>(moduleBase, imports->ImportAddressTableRVA);
92
return FindAddressByOrdinal(moduleBase, impName, impAddr, ordinal);
93
}
94
return nullptr;
95
}
96
97