Skip to content

Commit

Permalink
Revamped API for main, new imgui style, etc.
Browse files Browse the repository at this point in the history
  • Loading branch information
fishnet-technologies committed Jul 23, 2024
1 parent 2cae22d commit 43a9a32
Show file tree
Hide file tree
Showing 6 changed files with 302 additions and 59 deletions.
26 changes: 21 additions & 5 deletions mod-demo/include/api.h
Original file line number Diff line number Diff line change
Expand Up @@ -36,12 +36,28 @@ class ModApi {
uintptr_t GetSkyBase();
uintptr_t GetSkySize();

uintptr_t Scan(const char *signature);
uintptr_t Scan(const char *signature, uintptr_t start, size_t size);

void Hook(uintptr_t addr, void* newFn, void** oldFn);
uintptr_t Scan(const char* signature);
uintptr_t Scan(const char* signature, uintptr_t start, size_t size);

void UnHook(uintptr_t addr);
uintptr_t ScanPattern(lm_bytearr_t pattern, const char* masking);
uintptr_t ScanPattern(lm_bytearr_t pattern, const char* masking, uintptr_t start, size_t size);

uintptr_t ScanData(lm_bytearr_t data, size_t scansize);
uintptr_t ScanData(lm_bytearr_t data, size_t size, uintptr_t start, size_t scansize);

bool Hook(uintptr_t addr, void* newFn, void** oldFn);
bool Patch(uintptr_t address, const std::vector<unsigned char>& patchBytes, bool toggle = true);
bool Unpatch(uintptr_t address, const std::vector<unsigned char>& unpatchBytes);
bool Restore(uintptr_t address);
bool SetByte(uintptr_t address, std::vector<unsigned char> setByte);

bool FastHook(uintptr_t addr, void* newFn, void** oldFn);
bool FastPatch(uintptr_t address, const std::vector<unsigned char>& patchBytes, bool toggle = true);
bool FastUnpatch(uintptr_t address, const std::vector<unsigned char>& unpatchBytes);
bool FastRestore(uintptr_t address);
bool FastSetByte(uintptr_t address, std::vector<unsigned char> setByte);

bool UnHook(uintptr_t addr);
};

#define API ModApi::Instance()
139 changes: 130 additions & 9 deletions src/api.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -56,26 +56,43 @@ uintptr_t ModApi::Scan(const char *signature, uintptr_t start, size_t size){
return LM_SigScan(signature, start, size);
}

uintptr_t ModApi::ScanPattern(lm_bytearr_t pattern, const char* masking) {
return LM_PatternScan(pattern, masking, skyBase, skySize);
}

uintptr_t ModApi::ScanPattern(lm_bytearr_t pattern, const char* masking, uintptr_t start, size_t size) {
return LM_PatternScan(pattern, masking, start, size);
}

uintptr_t ModApi::ScanData(lm_bytearr_t data, size_t scansize) {
return LM_DataScan(data, skySize, skyBase, scansize);
}

uintptr_t ModApi::ScanData(lm_bytearr_t data, size_t size, uintptr_t start, size_t scansize) {
return LM_DataScan(data, size, start, scansize);
}

bool ModApi::Hook(uintptr_t addr, void* newFn, void** oldFn) {
//todo: check if already hooked,Multiple modification hooks for the same function
HookDef hook;
hook.addr = addr;
hook.newFn = newFn;
hook.oldFn = oldFn;

if (hooks.contains(addr)) { // dogshit_check.cpp
printf("hooking : function is already hooked!");
return true;
}
hook.addr = addr; hook.newFn = newFn; hook.oldFn = oldFn;

hook.size = LM_HookCode(addr, (lm_address_t)newFn, (lm_address_t*)oldFn);
if(!hook.size)
if (!hook.size)
return false;

hooks[addr] = hook;
return true;
}

bool ModApi::UnHook(uintptr_t addr) {
//todo:
auto it = hooks.begin();
if ((it = hooks.find(addr)) != hooks.end()) {
if(LM_UnhookCode(addr, (lm_address_t )*(it->second.oldFn), it->second.size)){
if ((it = hooks.find(addr)) != hooks.end()) {
if (LM_UnhookCode(addr, (lm_address_t) * (it->second.oldFn), it->second.size)) {
hooks.erase(addr);
return true;
}
Expand All @@ -92,7 +109,7 @@ bool ModApi::Patch(uintptr_t address, const std::vector<unsigned char>& patchByt
if (it == OriginalBytes.end()) {
size_t size = patchBytes.size();
// Change the protection to ReadWriteable
if (!LM_ProtMemory(address, size,LM_PROT_XRW, NULL)) {
if (!LM_ProtMemory(address, size, LM_PROT_XRW, NULL)) {
std::cerr << "Failed to Change protection at address: " << std::hex << address << std::endl;
return false;
}
Expand All @@ -114,5 +131,109 @@ bool ModApi::Patch(uintptr_t address, const std::vector<unsigned char>& patchByt
return false;
}

return true;
}

bool ModApi::Unpatch(uintptr_t address, const std::vector<unsigned char>& unpatchBytes) {
size_t size = unpatchBytes.size();
if (!LM_FreeMemory(address, size)) {
std::cerr << "Failed to free memory at address: " << std::hex << address << std::endl;
return true;
}

return false;
}

bool ModApi::Restore(uintptr_t address) {
auto it = OriginalBytes.find(address);
if (it == OriginalBytes.end()) {
std::cerr << "Original bytes not found for address: " << std::hex << address << std::endl;
return false;
}

const std::vector<unsigned char>& OriginalBytes = it->second;
if (!LM_WriteMemory(address, OriginalBytes.data(), OriginalBytes.size())) {
std::cerr << "Failed to restore memory at address: " << std::hex << address << std::endl;
return false;
}

return true;
}

bool ModApi::SetByte(uintptr_t address, std::vector<unsigned char> setByte) {
address += skyBase; // Ensure address is relative to Sky_Base

if (OriginalBytes.find(address) == OriginalBytes.end()) {
if (!LM_ProtMemory(address, setByte.size(), LM_PROT_XRW, NULL)) {
std::cerr << "Failed to Change protection at address: " << std::hex << address << std::endl;
return false;
}
}

lm_byte_t* byte = setByte.data();
if (!LM_SetMemory(address, *(byte), OriginalBytes[address].size())) {
std::cerr << "Failed to set memory at address: " << std::hex << address << std::endl;
return false;
}

return true;
}

// fastfunctions (basically functions checkless counterparts)
// WARNING : fastfunctions should only be used for patches if you are extremely confident that it wont kill your game.
bool ModApi::FastHook(uintptr_t addr, void* newFn, void** oldFn) {
HookDef hook;

hook.addr = addr; hook.newFn = newFn; hook.oldFn = oldFn;
hook.size = LM_HookCode(addr, (lm_address_t)newFn, (lm_address_t*)oldFn);

hooks[addr] = hook;
return true;
}

bool ModApi::FastPatch(uintptr_t address, const std::vector<unsigned char>& patchBytes, bool toggle) {
address += skyBase;

auto it = OriginalBytes.find(address);
if (it == OriginalBytes.end()) {
size_t size = patchBytes.size();
LM_ProtMemory(address, size, LM_PROT_XRW, NULL);

std::vector<unsigned char> originalBytes(size);
LM_ReadMemory(address, originalBytes.data(), size);
}

const unsigned char* dataPtr = toggle ? patchBytes.data() : OriginalBytes[address].data();
LM_WriteMemory(address, dataPtr, OriginalBytes[address].size());
return true;
}


bool ModApi::FastUnpatch(uintptr_t address, const std::vector<unsigned char>& unpatchBytes) {
size_t size = unpatchBytes.size();
LM_FreeMemory(address, size);

return false;
}

bool ModApi::FastRestore(uintptr_t address) {
auto it = OriginalBytes.find(address);

const std::vector<unsigned char>& OriginalBytes = it->second;
LM_WriteMemory(address, OriginalBytes.data(), OriginalBytes.size());

return true;
}

bool ModApi::FastSetByte(uintptr_t address, std::vector<unsigned char> setByte) {
address += skyBase; // Ensure address is relative to Sky_Base

if (OriginalBytes.find(address) == OriginalBytes.end()) {
LM_ProtMemory(address, setByte.size(), LM_PROT_XRW, NULL);
}

lm_byte_t* byte = setByte.data();
LM_SetMemory(address, *(byte), OriginalBytes[address].size());

return true;
}
22 changes: 18 additions & 4 deletions src/include/api.h
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
#include <cstdint>
#include <string>
#include <vector>
#include <libmem.h>

#ifdef _MSC_VER
#define MOD_API __declspec(dllexport)
Expand Down Expand Up @@ -41,13 +42,26 @@ class MOD_API ModApi {
uintptr_t GetSkyBase();
uintptr_t GetSkySize();

uintptr_t Scan(const char *signature);
uintptr_t Scan(const char *signature, uintptr_t start, size_t size);
uintptr_t Scan(const char* signature);
uintptr_t Scan(const char* signature, uintptr_t start, size_t size);

bool Hook(uintptr_t addr, void* newFn, void** oldFn);
uintptr_t ScanPattern(lm_bytearr_t pattern, const char* masking);
uintptr_t ScanPattern(lm_bytearr_t pattern, const char* masking, uintptr_t start, size_t size);

bool UnHook(uintptr_t addr);
uintptr_t ScanData(lm_bytearr_t data, size_t scansize);
uintptr_t ScanData(lm_bytearr_t data, size_t size, uintptr_t start, size_t scansize);

bool Hook(uintptr_t addr, void* newFn, void** oldFn);
bool Patch(uintptr_t address, const std::vector<unsigned char>& patchBytes, bool toggle = true);
bool Unpatch(uintptr_t address, const std::vector<unsigned char>& unpatchBytes);
bool Restore(uintptr_t address);
bool SetByte(uintptr_t address, std::vector<unsigned char> setByte);

bool FastHook(uintptr_t addr, void* newFn, void** oldFn);
bool FastPatch(uintptr_t address, const std::vector<unsigned char>& patchBytes, bool toggle = true);
bool FastUnpatch(uintptr_t address, const std::vector<unsigned char>& unpatchBytes);
bool FastRestore(uintptr_t address);
bool FastSetByte(uintptr_t address, std::vector<unsigned char> setByte);

bool UnHook(uintptr_t addr);
};
32 changes: 19 additions & 13 deletions src/main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,7 @@ __declspec(dllexport) POWER_PLATFORM_ROLE PowerDeterminePlatformRole(){
void InitConsole(){
FreeConsole();
AllocConsole();
SetConsoleTitle("SML Console");
SetConsoleTitle("SML Console - 0.1.2 - TgcMainWindow::VulkanRendering");

if (IsValidCodePage(CP_UTF8)) {
SetConsoleCP(CP_UTF8);
Expand Down Expand Up @@ -88,6 +88,8 @@ void loadWrapper(){
dllHandle = LoadLibrary("C:\\Windows\\System32\\POWRPROF.dll");
}

printf("Loading powrprof.dll symbols...");

if (dllHandle != NULL) {
o_GetPwrCapabilities = (BOOLEAN(*)(PSYSTEM_POWER_CAPABILITIES))GetProcAddress(dllHandle, "GetPwrCapabilities");
o_CallNtPowerInformation = (NTSTATUS (*)(POWER_INFORMATION_LEVEL, PVOID, ULONG, PVOID, ULONG))GetProcAddress(dllHandle, "CallNtPowerInformation");
Expand Down Expand Up @@ -127,18 +129,19 @@ static LRESULT WINAPI WndProc(const HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM


void terminateCrashpadHandler() {

PROCESSENTRY32 entry;
entry.dwSize = sizeof(PROCESSENTRY32);

HANDLE snapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, NULL);
if (Process32First(snapshot, &entry) == TRUE) {
while (Process32Next(snapshot, &entry) == TRUE) {
if (lstrcmp(entry.szExeFile, "crashpad_handler.exe") == 0) {
HANDLE hProcess = OpenProcess(PROCESS_TERMINATE, FALSE, entry.th32ProcessID);

if (hProcess!= NULL) {
if (hProcess != NULL) {
TerminateProcess(hProcess, 0);
CloseHandle(hProcess);
printf("Detected and closed crashpad_handler.exe");
}
}
}
Expand Down Expand Up @@ -237,18 +240,21 @@ LSTATUS hkRegEnumValueA(HKEY hKey, DWORD dwIndex, LPSTR lpValueName, LPDWORD lpc
}


DWORD WINAPI hook_thread(PVOID lParam){
HWND window = nullptr;
printf("Searching for window...\n");
while(!window){
DWORD WINAPI hook_thread(PVOID lParam) {
HWND window = nullptr;
printf("Searching for TgcMainWindow...\n");
while (!window) {
std::this_thread::sleep_for(std::chrono::milliseconds(100));
window = FindWindowA("TgcMainWindow", "Sky");
}
printf("Window Found: %p\n", window);
layer::setup(window);
}
printf("Complete! info: %p\n", window);

// todo: add something a little special here.
layer::setup(window);
oWndProc = reinterpret_cast<WNDPROC>(SetWindowLongPtr(window, GWLP_WNDPROC, reinterpret_cast<LONG_PTR>(WndProc)));
InitConsole();
Sleep(3000);
printf("Finished hook_thread routine, loading mods.");
//clear_screen();
return EXIT_SUCCESS;
}
Expand All @@ -259,17 +265,17 @@ DWORD WINAPI console_thread(LPVOID lpParam){
}


void onAttach(){
void onAttach() {
loadWrapper();
WCHAR path[MAX_PATH];
GetModuleFileNameW(NULL, path, MAX_PATH);
std::wstring ws(path);
std::string _path(ws.begin(), ws.end());
g_path = _path.substr(0, _path.find_last_of("\\/"));
HMODULE handle = LoadLibrary("advapi32.dll");
if(handle!= NULL){
if (handle != NULL) {
lm_address_t fnRegEnumValue = (lm_address_t)GetProcAddress(handle, "RegEnumValueA");
LM_HookCode(fnRegEnumValue, (lm_address_t)&hkRegEnumValueA, (lm_address_t *)&oRegEnumValueA);
LM_HookCode(fnRegEnumValue, (lm_address_t)&hkRegEnumValueA, (lm_address_t*)&oRegEnumValueA);
InitConsole();
terminateCrashpadHandler();
ModApi::Instance().InitSkyBase();
Expand Down
Loading

0 comments on commit 43a9a32

Please sign in to comment.