-
Notifications
You must be signed in to change notification settings - Fork 0
/
Trampoline.h
347 lines (285 loc) · 11.5 KB
/
Trampoline.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
#pragma once
#include "HookInstaller.h"
#include <vector>
#include <direct.h>
HMODULE hOriginalDLL = NULL;
//Define export functions
#define EXPORT extern "C" __declspec(dllexport)
// SteamAPI hooks
SteamAPI_Init_proto original_SteamAPI_Init = NULL;
// Lua function hooks
lua_createtable_proto original_lua_createtable = NULL;
lua_setfield_proto original_lua_setfield = NULL;
lua_pushcclosure_proto original_lua_pushcclosure = NULL;
lua_pushboolean_proto original_lua_pushboolean = NULL;
lua_pushnumber_proto original_lua_pushnumber = NULL;
luaL_checklstring_proto original_luaL_checklstring = NULL;
luaL_checkinteger_proto original_luaL_checkinteger = NULL;
// Luasteam functions
luasteam_common_function_proto original_luasteam_init = NULL;
luasteam_common_function_proto original_luasteam_shutdown = NULL;
luasteam_common_function_proto original_luasteam_runCallbacks = NULL;
luasteam_common_function_proto original_luasteam_setAchievement = NULL;
luasteam_common_function_proto original_luasteam_storeStats = NULL;
luasteam_common_function_proto original_luasteam_getAchievement = NULL;
luasteam_common_function_proto original_luasteam_getStatInt = NULL;
luasteam_common_function_proto original_luasteam_setStatInt = NULL;
luasteam_common_function_proto original_luasteam_getSteamID = NULL;
#pragma region steam_api64.dll functions
bool __stdcall SteamAPI_Init_hook() {
Console::Print("SteamAPI_Init called");
return true;
}
#pragma endregion
#pragma region lua function hooks
void __stdcall lua_createtable_hook(void** L, int narr, int nrec) {
//std::cout << "lua_createtable called" << std::endl;
original_lua_createtable(L, narr, nrec);
}
void __stdcall lua_setfield_hook(void** L, int idx, const char* k) {
//std::cout << "lua_setfield called with idx " << idx << " value " << k << std::endl;
original_lua_setfield(L, idx, k);
}
void __stdcall lua_pushcclosure_hook(void** L, lua_CFunction fn, int n) {
if (n == 0)
{
//std::cout << "lua_pushcclosure called with " << reinterpret_cast<void*>(fn) << std::endl;
}
original_lua_pushcclosure(L, fn, n);
}
#pragma endregion
#pragma region luasteam function hook functions
int __stdcall luasteam_init_hook(void** L) {
int ret = original_luasteam_init(L); // Original callen
return (ret);
}
int __stdcall luasteam_shutdown_hook(void** L) { // return 0
int ret = 0;//original_luasteam_shutdown(L);
std::cout << "luasteam_shutdown called with return value " << ret << std::endl;
return (ret);
}
int __stdcall luasteam_runCallbacks_hook(void** L) { // return 0
std::cout << "luasteam_runCallbacks called" << std::endl;
return 0;//original_luasteam_runCallbacks(L);
}
// setAchievements
int __stdcall luasteam_setAchievement_hook(void** L)
{
original_luaL_checklstring(L, 1, NULL);
original_lua_pushboolean(L, true); // Pushes a luaboolean "true" to the stack
Console::Print("luasteam_setAchievement hook tripped!");
return 1;
}
//storeStats
int __stdcall luasteam_storeStats_hook(void** L)// return 1
{
Console::Print("luasteam_storeStats hook tripped!");
original_lua_pushboolean(L, true); // Pushes a luaboolean "true" to the stack
return 1;
}
// getAchievement,
int __stdcall luasteam_getAchievement_hook(void** L)
{
const char* value = original_luaL_checklstring(L, 1, NULL);
Console::Print("luasteam_getAchievement hook tripped with value: " + std::string(value));
original_lua_pushboolean(L, true); // Pushes a luaboolean "true" to the stack
original_lua_pushboolean(L, true); // Pushes a luaboolean "true" to the stack
return 2;
}
// getStatInt
int __stdcall luasteam_getStatInt_hook(void** L)
{
original_luaL_checklstring(L, 1, NULL);
Console::Print("luasteam_getStatInt hook tripped!");
original_lua_pushboolean(L, false);
return 1;
}
//setStatInt
int __stdcall luasteam_setStatInt_hook(void** L)
{
original_luaL_checklstring(L, 1, NULL);
original_luaL_checkinteger(L, 2);
original_lua_pushboolean(L, true);
Console::Print("luasteam_setStatInt hook tripped");
return 1;
}
//getSteamID
int __stdcall luasteam_getSteamID_hook(void** L)
{
Console::Print("luasteam_getSteamID hook tripped");
return original_luasteam_getSteamID(L);
}
#pragma endregion
// define the hooked functions
EXPORT int luaopen_luasteam(void** L) {
if (hOriginalDLL == NULL)
{
std::cout << "hOriginalDLL is NULL!" << std::endl;
return 0;
}
lua_CFunction pfnOriginal = (lua_CFunction)GetProcAddress(hOriginalDLL, "luaopen_luasteam");
if (pfnOriginal == NULL)
{
Console::Print("Failed to get address of luaopen_luasteam", 2);
MessageBoxA(NULL, "Failed to get address of luaopen_luasteam", "Error", MB_OK | MB_ICONERROR);
return 0;
}
Console::Print("luaopen_luasteam called");
return pfnOriginal(L);
}
namespace Cheats {
void Prepare()
{
original_SteamAPI_Init(); // I think I can just call this and get away with it LOL
}
void UnlockAchievement(const char* achname, void** L)
{
// Push an achievement name to the stack
// original_lua_pushstring(L, achname);
// Call the luasteam_setAchievement function
// original_luasteam_setAchievement(L);
}
}
namespace Trampoline {
const char* g_szOriginalDLL = "Original.dll";
std::string GetCurrentDir() // Returns EXE directory
{
char cCurrentPath[FILENAME_MAX]; // get working directory into buffer
if (!_getcwd(cCurrentPath, sizeof(cCurrentPath)))
exit(-1);
cCurrentPath[sizeof(cCurrentPath) - 1] = '\0'; // not really required
char* s = cCurrentPath; // save path from buffer into currentpath chararr
std::string str(s);
//free(s);
return str;
}
HMODULE GetLoadedModuleHandle(std::string path)
{
HMODULE hMOD= GetModuleHandleA(path.c_str());
Console::Print("Expecting lua51.dll in : " + path, 1);
if (!hMOD) {
Console::Print("Failed to load DLL from: " + path, 2);
return NULL;
}
else
{
Console::Print("Loaded DLL from: " + path, 1);
}
return hMOD;
}
BOOL LoadOriginalDLL()
{
// Find the original DLL in the current executable's directory
std::string exedir = GetCurrentDir();
// Load steam_api64.dll
std::string steamapipath = (exedir + "\\steam_api64.dll");
HMODULE hSteamDLL = LoadLibraryA(steamapipath.c_str());
Console::Print("Expecting steam_api64.dll in : " + steamapipath, 1);
if(!hSteamDLL)
{
Console::Print("Failed to load the steam_api64.dll", 2);
return FALSE;
}
else
{
Console::Print("Loaded steam_api64.dll", 1);
}
// try to install detour for SteamAPI_Init
InstallDetourSteamAPI(hSteamDLL, "SteamAPI_Init", original_SteamAPI_Init, SteamAPI_Init_hook);
// Load luasteam
std::string originalLuasteamDLLpath = exedir + "\\" + g_szOriginalDLL;
Console::Print("Expecting Original.dll in : " + originalLuasteamDLLpath, 1);
hOriginalDLL = LoadLibraryA(originalLuasteamDLLpath.c_str());
if (!hOriginalDLL) {
Console::Print("Failed to load Original.dll, which is the renamed luasteam.dll", 2);
return FALSE;
}
else
{
Console::Print("Loaded Original.dll, which is the renamed luasteam.dll", 1);
}
// try to load lua functions
std::string lua51DLLpath = exedir + "\\lua51.dll";
HMODULE hLuaDLL = GetLoadedModuleHandle(lua51DLLpath);
if (hLuaDLL == NULL)
{
return FALSE;
}
HMODULE hOriginalLuaSteamDLL = GetLoadedModuleHandle(exedir + "\\" + g_szOriginalDLL);
if (!hOriginalLuaSteamDLL) {
return FALSE;
}
InstallDetour<lua_createtable_proto>(hLuaDLL, "lua_createtable", original_lua_createtable, lua_createtable_hook);
InstallDetour<lua_setfield_proto>(hLuaDLL, "lua_setfield", original_lua_setfield, lua_setfield_hook);
InstallDetour<lua_pushcclosure_proto>(hLuaDLL, "lua_pushcclosure", original_lua_pushcclosure, lua_pushcclosure_hook);
original_lua_pushboolean = (lua_pushboolean_proto)GetProcAddress(hLuaDLL, "lua_pushboolean");
if (!original_lua_pushboolean)
{
std::cout << "Failed to get address of lua_pushboolean" << GetLastError() << std::endl;
}
original_lua_pushnumber = (lua_pushnumber_proto)GetProcAddress(hLuaDLL, "lua_pushnumber");
if (!original_lua_pushnumber)
{
std::cout << "Failed to get address of lua_pushnumber" << GetLastError() << std::endl;
}
original_luaL_checklstring = (luaL_checklstring_proto)GetProcAddress(hLuaDLL, "luaL_checklstring");
if (!original_luaL_checklstring)
{
std::cout << "Failed to get address of luaL_checklstring" << GetLastError() << std::endl;
}
original_luaL_checkinteger = (luaL_checkinteger_proto)GetProcAddress(hLuaDLL, "luaL_checkinteger");
if (!original_luaL_checkinteger)
{
std::cout << "Failed to get address of luaL_checkinteger" << GetLastError() << std::endl;
}
/// Hooked luasteam functions, getting called by the game
InstallDetour<luasteam_common_function_proto>(hOriginalLuaSteamDLL, "luasteam_init", original_luasteam_init, luasteam_init_hook);
InstallDetour<luasteam_common_function_proto>(hOriginalLuaSteamDLL, "luasteam_shutdown", original_luasteam_shutdown, luasteam_shutdown_hook);
if (InstallDetourLuasteam(hOriginalLuaSteamDLL, "luasteam_runCallbacks", original_luasteam_runCallbacks, luasteam_runCallbacks_hook) == 1)
{
std::cout << "Failed to install detour luasteam_runCallbacks" << std::endl;
}
if (InstallDetourLuasteam(hOriginalLuaSteamDLL,"luasteam_setAchievement", original_luasteam_setAchievement, luasteam_setAchievement_hook) == 1)
{
std::cout << "Failed to install detour luasteam_setAchievement" << std::endl;
}
if (InstallDetourLuasteam(hOriginalLuaSteamDLL, "luasteam_storeStats", original_luasteam_storeStats, luasteam_storeStats_hook) == 1)
{
std::cout << "Failed to install detour luasteam_storeStats" << std::endl;
}
if (InstallDetourLuasteam(hOriginalLuaSteamDLL, "luasteam_getAchievement", original_luasteam_getAchievement, luasteam_getAchievement_hook) == 1)
{
std::cout << "Failed to install detour luasteam_getAchievement" << std::endl;
}
if (InstallDetourLuasteam(hOriginalLuaSteamDLL, "luasteam_getStatInt", original_luasteam_getStatInt, luasteam_getStatInt_hook) == 1)
{
std::cout << "Failed to install detour luasteam_getStatInt" << std::endl;
}
if (InstallDetourLuasteam(hOriginalLuaSteamDLL, "luasteam_setStatInt", original_luasteam_setStatInt, luasteam_setStatInt_hook) == 1)
{
std::cout << "Failed to install detour luasteam_setStatInt" << std::endl;
}
if (InstallDetourLuasteam(hOriginalLuaSteamDLL, "luasteam_getSteamID", original_luasteam_getSteamID, luasteam_getSteamID_hook) == 1)
{
std::cout << "Failed to install detour luasteam_getSteamID" << std::endl;
}
Console::Print("End of loading libraries and installing hooks.\nHopefully everything works correctly now.\nYou can hide this window by pressing F2.", 69);
return TRUE;
}
void KeyboardMenu()
{
while (true)
{
Sleep(100);
// Key F1 pressed
if (GetAsyncKeyState(VK_F1) & 1)
{
Console::CycleLogLevel();
}
if (GetAsyncKeyState(VK_F2) & 1)
{
Console::ToggleConsole();
}
}
}
}