I am trying to modify closed source game client that works with my game server. The purpose of that is being able to add new graphical elements into the client.
I have read a lot of tutorials about dll injection and in the end theres the code I made:
// dllmain.cpp : Defines the entry point for the DLL application.
#include "stdafx.h"
#include <windows.h>
#define BASE_ADDR 0x00400000
DWORD WINAPI MyThread(LPVOID);
DWORD g_threadID;
HMODULE g_hModule;
void __stdcall CallFunction(int&, int&, int&, int&, int&, int&, int&, int&);
void __stdcall typeText(int&, const char*);
//must be at least one function to prevent crash
__declspec(dllexport) int APIENTRY Func(LPVOID lpParam)
{//empty function
return 0;
}
//main func
BOOL APIENTRY DllMain( HMODULE hModule,
DWORD ul_reason_for_call,
LPVOID lpReserved
)
{
DWORD myThreadID;
HANDLE myHandle;
switch (ul_reason_for_call)
{
case DLL_PROCESS_ATTACH:
g_hModule = hModule;
DisableThreadLibraryCalls(hModule);
CreateThread(NULL, NULL, &MyThread, NULL, NULL, &g_threadID);
break;
case DLL_THREAD_ATTACH:
case DLL_THREAD_DETACH:
case DLL_PROCESS_DETACH:
break;
}
return TRUE;
}
DWORD WINAPI MyThread(LPVOID)
{
int i1 = 1;
int i2 = 10;
int i3 = 10;
int i4 = 200;
int i5 = 200;
int i6 = 60;
int i7 = 0;
int i8 = 0;
while (true)
{
if (GetAsyncKeyState(VK_F3) & 1) //Set F3 as hotkey
{
// call GUI window (do it before login)
CallFunction(i1, i2, i3, i4, i5, i6, i7, i8);
//display text from char (do it after login)
//typeText(i1, "halo halo");
}
else if (GetAsyncKeyState(VK_F4) & 1)
break;
Sleep(100);
}
FreeLibraryAndExitThread(g_hModule, 0);
/* another way to call function?
typedef void tipo(int& p1, int& p2, int& p3, int& p4, int& p5, int& p6, int& p7, int& p8);
void(*func)(int& p1, int& p2, int& p3, int& p4, int& p5, int& p6, int& p7, int& p8);
func = (tipo*)0x490C60;
func(i1, i2, i3, i4, i5, i6, i7, i8);
*/
return 0;
}
//0x004067C0, pattern = (int, char*)
void __stdcall typeText(int& type, const char* text)
{
typedef void(__stdcall *pFunctionAddress)(int&, const char*);
pFunctionAddress pMySecretFunction = (pFunctionAddress)(0x004067C0);
pMySecretFunction(type, text);
}
//const DWORD DrawSkinExAddress =0x490C60;.
//typedef void TF_DRAWSKIN(int nSurface, int X, int Y, int W, int H, int SkinId, int dX, int dY);
void __stdcall CallFunction(int& p1, int& p2, int& p3, int& p4, int& p5, int& p6, int& p7, int& p8)
{
typedef void(__stdcall *pFunctionAddress)(int&, int&, int&, int&, int&, int&, int&, int&);
pFunctionAddress pMySecretFunction = (pFunctionAddress)(0x490C60);
pMySecretFunction(p1,p2,p3,p4,p5,p6,p7,p8);
}
I can successfully inject it and run the client. When I try to call definied there function (Press F3 to do it), the client crashes. the runtime error shows up (picture presenting error: https://i.sstatic.net/8sL1m.jpg ) and client crashes. I think theres problem with the method I call the functions. The addresses and variables are fine I think because if I try to do it on another random addresses the client just crash normally (app not responding).
I have tried replacing stdcall with cdecl but nothing has changed.