diff --git a/attach b/attach index 722a5082..32d6d9b7 100755 --- a/attach +++ b/attach @@ -5,17 +5,17 @@ line=$(pidof hl2_linux) arr=($line) inst=$1 if [ $# == 0 ]; then - inst=0 + inst=0 fi if [ ${#arr[@]} == 0 ]; then - echo TF2 isn\'t running! - exit + echo TF2 isn\'t running! + exit fi if [ $inst -gt ${#arr[@]} ] || [ $inst == ${#arr[@]} ]; then - echo wrong index! - exit + echo wrong index! + exit fi proc=${arr[$inst]} @@ -46,15 +46,15 @@ sudo killall -19 steam sudo killall -19 steamwebhelper gdb -n -q -batch \ - -ex "attach $proc" \ - -ex "set \$dlopen = (void*(*)(char*, int)) dlopen" \ - -ex "call \$dlopen(\"$FILENAME\", 1)" \ - -ex "call dlerror()" \ - -ex 'print (char *) $2' \ - -ex "catch syscall exit exit_group" \ - -ex "detach" \ - -ex "quit" - + -ex "attach $proc" \ + -ex "set \$dlopen = (void*(*)(char*, int)) dlopen" \ + -ex "call \$dlopen(\"$FILENAME\", 1)" \ + -ex "call dlerror()" \ + -ex 'print (char *) $2' \ + -ex "catch syscall exit exit_group" \ + -ex "detach" \ + -ex "quit" + rm $FILENAME sudo killall -18 steamwebhelper diff --git a/attach-libnamed.sh b/attach-libnamed.sh index 5194fcc3..898d23a2 100755 --- a/attach-libnamed.sh +++ b/attach-libnamed.sh @@ -8,17 +8,17 @@ line=$(pidof hl2_linux) arr=($line) inst=$1 if [ $# == 0 ]; then - inst=0 + inst=0 fi if [ ${#arr[@]} == 0 ]; then - echo TF2 isn\'t running! - exit + echo TF2 isn\'t running! + exit fi if [ $inst -gt ${#arr[@]} ] || [ $inst == ${#arr[@]} ]; then - echo wrong index! - exit + echo wrong index! + exit fi proc=${arr[$inst]} @@ -37,12 +37,12 @@ FILENAME=$(shuf -n 1 build_names) # Create directory if it doesn't exist if [ ! -d "/lib/i386-linux-gnu/" ]; then - sudo mkdir /lib/i386-linux-gnu/ + sudo mkdir /lib/i386-linux-gnu/ fi # In case this file exists, get another one. ( checked it works ) while [ -f "/lib/i386-linux-gnu/${FILENAME}" ]; do - FILENAME=$(shuf -n 1 build_names) + FILENAME=$(shuf -n 1 build_names) done # echo $FILENAME > build_id # For detaching @@ -52,13 +52,13 @@ sudo cp "bin/libcathook.so" "/lib/i386-linux-gnu/${FILENAME}" echo loading "$FILENAME" to "$proc" sudo gdb -n -q -batch \ - -ex "attach $proc" \ - -ex "set \$dlopen = (void*(*)(char*, int)) dlopen" \ - -ex "call \$dlopen(\"/lib/i386-linux-gnu/$FILENAME\", 1)" \ - -ex "call dlerror()" \ - -ex 'print (char *) $2' \ - -ex "catch syscall exit exit_group" \ - -ex "detach" \ - -ex "quit" + -ex "attach $proc" \ + -ex "set \$dlopen = (void*(*)(char*, int)) dlopen" \ + -ex "call \$dlopen(\"/lib/i386-linux-gnu/$FILENAME\", 1)" \ + -ex "call dlerror()" \ + -ex 'print (char *) $2' \ + -ex "catch syscall exit exit_group" \ + -ex "detach" \ + -ex "quit" sudo rm "/lib/i386-linux-gnu/${FILENAME}" diff --git a/include/copypasted/CSignature.h b/include/copypasted/CSignature.h index b22187e5..749a93b9 100644 --- a/include/copypasted/CSignature.h +++ b/include/copypasted/CSignature.h @@ -12,6 +12,7 @@ public: void *GetModuleHandleSafe(const char *pszModuleName); uintptr_t GetClientSignature(const char *chPattern); uintptr_t GetEngineSignature(const char *chPattern); + uintptr_t GetSteamAPISignature(const char *chPattern); uintptr_t GetVstdSignature(const char *chPattern); }; diff --git a/include/core/sharedobj.hpp b/include/core/sharedobj.hpp index 3028f681..74bdde86 100644 --- a/include/core/sharedobj.hpp +++ b/include/core/sharedobj.hpp @@ -40,6 +40,7 @@ public: SharedObject &steamclient(); SharedObject &client(); SharedObject &engine(); +SharedObject &steamapi(); SharedObject &vstdlib(); SharedObject &tier0(); SharedObject &inputsystem(); diff --git a/install-data b/install-data index db52c503..0c78b98d 100755 --- a/install-data +++ b/install-data @@ -1,10 +1,10 @@ #!/usr/bin/env bash if ! [ -d "/opt/cathook/data" ]; then - echo "Creating cathook data directory at /opt/cathook/data" - mkdir -p "/opt/cathook/data" - chown -R $USER "/opt/cathook/data" - chmod -R 777 "/opt/cathook/data" + echo "Creating cathook data directory at /opt/cathook/data" + mkdir -p "/opt/cathook/data" + chown -R $USER "/opt/cathook/data" + chmod -R 777 "/opt/cathook/data" fi echo "Installing cathook data to /opt/cathook/data" diff --git a/src/copypasted/CSignature.cpp b/src/copypasted/CSignature.cpp index 2cbcc727..8d01a7c6 100644 --- a/src/copypasted/CSignature.cpp +++ b/src/copypasted/CSignature.cpp @@ -216,6 +216,32 @@ uintptr_t CSignature::GetEngineSignature(const char *chPattern) return patr - (uintptr_t)(module) + moduleMap->l_addr; } //=================================================================================== +uintptr_t CSignature::GetSteamAPISignature(const char *chPattern) +{ + // we need to do this becuase (i assume that) under the hood, dlopen only + // loads up the sections that it needs into memory, meaning that we cannot + // get the string table from the module. + static int fd = open(sharedobj::steamapi().path.c_str(), O_RDONLY); + static void *module = mmap(NULL, lseek(fd, 0, SEEK_END), PROT_READ, MAP_SHARED, fd, 0); + static link_map *moduleMap = sharedobj::steamapi().lmap; + + // static void *module = (void *)moduleMap->l_addr; + + static Elf32_Shdr *textHeader = getSectionHeader(module, ".text"); + + static int textOffset = textHeader->sh_offset; + + static int textSize = textHeader->sh_size; + + // we need to remap the address that we got from the pattern search from our + // mapped file to the actual memory we do this by rebasing the address + // (subbing the mmapped one and adding the dlopened one. + uintptr_t patr = dwFindPattern(((uintptr_t) module) + textOffset, ((uintptr_t) module) + textOffset + textSize, chPattern); + if (!patr) + return NULL; + return patr - (uintptr_t)(module) + moduleMap->l_addr; +} +//=================================================================================== uintptr_t CSignature::GetVstdSignature(const char *chPattern) { // we need to do this becuase (i assume that) under the hood, dlopen only diff --git a/src/core/interfaces.cpp b/src/core/interfaces.cpp index 5bf0e24b..28e880e9 100644 --- a/src/core/interfaces.cpp +++ b/src/core/interfaces.cpp @@ -7,6 +7,7 @@ #include "common.hpp" #include "core/sharedobj.hpp" +#include #include @@ -76,23 +77,41 @@ template T *BruteforceInterface(std::string name, sharedobj::Shared return nullptr; } +extern "C" typedef HSteamUser (*GetHSteamUser_t)(); + void CreateInterfaces() { - g_ICvar = BruteforceInterface("VEngineCvar", sharedobj::vstdlib()); - g_IEngine = BruteforceInterface("VEngineClient", sharedobj::engine()); - g_AppID = g_IEngine->GetAppID(); - g_IEntityList = BruteforceInterface("VClientEntityList", sharedobj::client()); - g_ISteamClient = BruteforceInterface("SteamClient", sharedobj::steamclient(), 17); - g_IEventManager2 = BruteforceInterface("GAMEEVENTSMANAGER", sharedobj::engine(), 2); - g_IGameEventManager = BruteforceInterface("GAMEEVENTSMANAGER", sharedobj::engine(), 1); - g_IBaseClient = BruteforceInterface("VClient", sharedobj::client()); - g_ITrace = BruteforceInterface("EngineTraceClient", sharedobj::engine()); - g_IInputSystem = BruteforceInterface("InputSystemVersion", sharedobj::inputsystem()); - HSteamPipe sp = g_ISteamClient->CreateSteamPipe(); - HSteamUser su = g_ISteamClient->ConnectToGlobalUser(sp); - g_IVModelRender = BruteforceInterface("VEngineModel", sharedobj::engine(), 16); - g_ISteamFriends = nullptr; - g_IEngineVGui = BruteforceInterface("VEngineVGui", sharedobj::engine()); + g_ICvar = BruteforceInterface("VEngineCvar", sharedobj::vstdlib()); + g_IEngine = BruteforceInterface("VEngineClient", sharedobj::engine()); + g_AppID = g_IEngine->GetAppID(); + g_IEntityList = BruteforceInterface("VClientEntityList", sharedobj::client()); + g_ISteamClient = BruteforceInterface("SteamClient", sharedobj::steamclient(), 17); + g_IEventManager2 = BruteforceInterface("GAMEEVENTSMANAGER", sharedobj::engine(), 2); + g_IGameEventManager = BruteforceInterface("GAMEEVENTSMANAGER", sharedobj::engine(), 1); + g_IBaseClient = BruteforceInterface("VClient", sharedobj::client()); + g_ITrace = BruteforceInterface("EngineTraceClient", sharedobj::engine()); + g_IInputSystem = BruteforceInterface("InputSystemVersion", sharedobj::inputsystem()); + uintptr_t steampipe_sig = gSignatures.GetSteamAPISignature("8D 83 ? ? ? ? 89 34 24 89 44 24 ? E8 ? ? ? ? 89 C6") + 0xE7; + typedef HSteamPipe (*GetSteamPipe)(); + GetSteamPipe GetSteamPipe_fn = GetSteamPipe(steampipe_sig); + HSteamPipe sp = GetSteamPipe_fn(); + if (!sp) + { + logging::Info("Creating new Steam Pipe..."); + sp = g_ISteamClient->CreateSteamPipe(); + } + logging::Info("Inited Steam Pipe"); + GetHSteamUser_t func = (GetHSteamUser_t)(GetHSteamUser_t) dlsym(sharedobj::steamapi().lmap, "SteamAPI_GetHSteamUser"); + HSteamUser su = func(); + if (!su) + { + logging::Info("Connecting to Steam User"); + g_ISteamClient->ConnectToGlobalUser(sp); + } + logging::Info("Inited Steam User"); + g_IVModelRender = BruteforceInterface("VEngineModel", sharedobj::engine(), 16); + g_ISteamFriends = nullptr; + g_IEngineVGui = BruteforceInterface("VEngineVGui", sharedobj::engine()); IF_GAME(IsTF2()) { uintptr_t sig_steamapi = gSignatures.GetEngineSignature("55 0F 57 C0 89 E5 83 EC 18 F3 0F 11 05 ? ? ? ? F3 0F 11 05 ? ? ? " @@ -101,16 +120,25 @@ void CreateInterfaces() "C7 04 24 ? ? ? ? E8 ? ? ? ? C9 C3"); logging::Info("SteamAPI: 0x%08x", sig_steamapi); void **SteamAPI_engine = *reinterpret_cast(sig_steamapi + 36); - g_ISteamFriends = (ISteamFriends *) (SteamAPI_engine[2]); // + logging::Info("A"); + g_ISteamFriends = (ISteamFriends *) (SteamAPI_engine[2]); + logging::Info("A"); } if (g_ISteamFriends == nullptr) { + logging::Info("A"); // FIXME SIGNATURE g_ISteamFriends = g_ISteamClient->GetISteamFriends(su, sp, "SteamFriends002"); + logging::Info("A"); } - g_GlobalVars = **(reinterpret_cast((uintptr_t) 11 + gSignatures.GetClientSignature("55 89 E5 83 EC ? 8B 45 08 8B 15 ? ? ? ? F3 0F 10"))); - g_IPrediction = BruteforceInterface("VClientPrediction", sharedobj::client()); + logging::Info("B"); + //g_GlobalVars = **(reinterpret_cast((uintptr_t) 11 + gSignatures.GetClientSignature("55 89 E5 83 EC ? 8B 45 08 8B 15 ? ? ? ? F3 0F 10"))); + g_GlobalVars = **reinterpret_cast(gSignatures.GetClientSignature("8B 15 ? ? ? ? F3 0F 10 88 D0 08 00 00") + 2); + logging::Info("A"); + g_IPrediction = BruteforceInterface("VClientPrediction", sharedobj::client()); + logging::Info("A"); g_IGameMovement = BruteforceInterface("GameMovement", sharedobj::client()); + logging::Info("A"); IF_GAME(IsTF2()) { // g_IMoveHelper = diff --git a/src/core/sharedobj.cpp b/src/core/sharedobj.cpp index 9ce1b5cb..a764ef76 100644 --- a/src/core/sharedobj.cpp +++ b/src/core/sharedobj.cpp @@ -91,6 +91,7 @@ void LoadAllSharedObjects() steamclient().Load(); client().Load(); engine().Load(); + steamapi().Load(); vstdlib().Load(); tier0().Load(); inputsystem().Load(); @@ -113,6 +114,11 @@ SharedObject &steamclient() static SharedObject obj("steamclient.so", true); return obj; } +SharedObject &steamapi() +{ + static SharedObject obj("libsteam_api.so", false); + return obj; +} SharedObject &client() { static SharedObject obj("client.so", true); @@ -164,5 +170,6 @@ SharedObject &libsdl() static SharedObject obj("libSDL2-2.0.so.0", false); return obj; } + #endif } // namespace sharedobj diff --git a/src/hack.cpp b/src/hack.cpp index d04fd96d..f2314e83 100644 --- a/src/hack.cpp +++ b/src/hack.cpp @@ -146,7 +146,7 @@ void critical_error_handler(int signum) void hack::Initialize() { ::signal(SIGSEGV, &critical_error_handler); - //::signal(SIGABRT, &my_signal_handler); + ::signal(SIGABRT, &critical_error_handler); time_injected = time(nullptr); /*passwd *pwd = getpwuid(getuid()); char *logname = strfmt("/tmp/cathook-game-stdout-%s-%u.log", pwd->pw_name, diff --git a/src/hacks/Misc.cpp b/src/hacks/Misc.cpp index 9c0c7cd9..423f4fe3 100644 --- a/src/hacks/Misc.cpp +++ b/src/hacks/Misc.cpp @@ -221,8 +221,11 @@ void CreateMove() SendAutoBalanceRequest(); // Simple No-Push through cvars - if (*nopush_enabled == teammatesPushaway->GetBool()) - teammatesPushaway->SetValue(!nopush_enabled); + if (teammatesPushaway) + { + if (*nopush_enabled == teammatesPushaway->GetBool()) + teammatesPushaway->SetValue(!nopush_enabled); + } } } diff --git a/src/hooks/Paint.cpp b/src/hooks/Paint.cpp index 24f6873e..5bc18ee1 100644 --- a/src/hooks/Paint.cpp +++ b/src/hooks/Paint.cpp @@ -19,6 +19,11 @@ namespace hooked_methods DEFINE_HOOKED_METHOD(Paint, void, IEngineVGui *this_, PaintMode_t mode) { + if (!isHackActive()) + { + return original::Paint(this_, mode);; + } + if (!g_IEngine->IsInGame()) g_Settings.bInvalid = true;