diff --git a/src/Components/Loader.cpp b/src/Components/Loader.cpp index 4d964935..add72fda 100644 --- a/src/Components/Loader.cpp +++ b/src/Components/Loader.cpp @@ -19,6 +19,7 @@ namespace Components Loader::Register(new Auth()); Loader::Register(new Bans()); + Loader::Register(new Bots()); Loader::Register(new Dvar()); Loader::Register(new Lean()); Loader::Register(new Maps()); diff --git a/src/Components/Loader.hpp b/src/Components/Loader.hpp index 88dc7c6c..e79eb17c 100644 --- a/src/Components/Loader.hpp +++ b/src/Components/Loader.hpp @@ -32,6 +32,7 @@ namespace Components #include "Modules\Auth.hpp" #include "Modules\Bans.hpp" +#include "Modules\Bots.hpp" #include "Modules\Dvar.hpp" #include "Modules\Lean.hpp" #include "Modules\Maps.hpp" diff --git a/src/Components/Modules/Bots.cpp b/src/Components/Modules/Bots.cpp new file mode 100644 index 00000000..a9eb6ac0 --- /dev/null +++ b/src/Components/Modules/Bots.cpp @@ -0,0 +1,66 @@ +#include "STDInclude.hpp" + +namespace Components +{ + std::vector Bots::BotNames; + + void Bots::InsertBotName(const char* arg) + { + const char** args = &arg; + if (Bots::BotNames.empty()) + { + FileSystem::File bots("bots.txt"); + + if (bots.exists()) + { + std::vector names = Utils::String::Explode(bots.getBuffer(), '\n'); + + for (auto name : names) + { + Utils::String::Replace(name, "\r", ""); + name = Utils::String::Trim(name); + + if (!name.empty()) + { + Bots::BotNames.push_back(name); + } + } + } + + if(Bots::BotNames.empty()) + { + Bots::BotNames.push_back("bot"); + } + } + + int botId = reinterpret_cast(args[12]); + args[12] = Utils::String::VA("%s", Bots::BotNames[botId % Bots::BotNames.size()].data()); + } + + __declspec(naked) void Bots::BuildConnectStringStub() + { + __asm + { + pushad + call Bots::InsertBotName + popad + + push 6B5D80h // sprintf + retn + } + } + + Bots::Bots() + { + // Replace connect string + Utils::Hook::Set(0x48ADA6, "connect bot%d \"\\cg_predictItems\\1\\cl_anonymous\\0\\color\\4\\head\\default\\model\\multi\\snaps\\20\\rate\\5000\\name\\%s\\protocol\\%d\\checksum\\%d\\statver\\%d %u\\qport\\%d\""); + + // Intercept sprintf for the connect string + Utils::Hook(0x48ADAB, Bots::BuildConnectStringStub, HOOK_CALL).install()->quick(); + } + + Bots::~Bots() + { + Bots::BotNames.clear(); + } +} diff --git a/src/Components/Modules/Bots.hpp b/src/Components/Modules/Bots.hpp new file mode 100644 index 00000000..9d9d20e4 --- /dev/null +++ b/src/Components/Modules/Bots.hpp @@ -0,0 +1,19 @@ +namespace Components +{ + class Bots : public Component + { + public: + Bots(); + ~Bots(); + +#if defined(DEBUG) || defined(FORCE_UNIT_TESTS) + const char* getName() { return "Bots"; }; +#endif + + private: + static std::vector BotNames; + + static void InsertBotName(const char* arg); + static void BuildConnectStringStub(); + }; +}