mirror of
https://github.com/Kelsidavis/WoWee.git
synced 2026-04-01 03:13:50 +00:00
Extract domain-specific logic from the monolithic GameHandler into
dedicated handler classes, each owning its own opcode registration,
state, and packet parsing:
- CombatHandler: combat, XP, kill, PvP, loot roll (~26 methods)
- SpellHandler: spells, auras, pet stable, talent (~3+ methods)
- SocialHandler: friends, guild, groups, BG, RAF, PvP AFK (~14+ methods)
- ChatHandler: chat messages, channels, GM tickets, server messages,
defense/area-trigger messages (~7+ methods)
- InventoryHandler: items, trade, loot, mail, vendor, equipment sets,
read item (~3+ methods)
- QuestHandler: gossip, quests, completed quest response (~5+ methods)
- MovementHandler: movement, follow, transport (~2 methods)
- WardenHandler: Warden anti-cheat module
Each handler registers its own dispatch table entries via
registerOpcodes(DispatchTable&), called from
GameHandler::registerOpcodeHandlers(). GameHandler retains core
orchestration: auth/session handshake, update-object parsing,
opcode routing, and cross-handler coordination.
game_handler.cpp reduced from ~10,188 to ~9,432 lines.
Also add a POST_BUILD CMake step to symlink Data/ next to the
executable so expansion profiles and opcode tables are found at
runtime when running from build/bin/.
103 lines
3.6 KiB
C++
103 lines
3.6 KiB
C++
#pragma once
|
|
|
|
#include "game/opcode_table.hpp"
|
|
#include "network/packet.hpp"
|
|
#include <cstdint>
|
|
#include <functional>
|
|
#include <future>
|
|
#include <memory>
|
|
#include <string>
|
|
#include <unordered_map>
|
|
#include <vector>
|
|
|
|
namespace wowee {
|
|
namespace game {
|
|
|
|
class GameHandler;
|
|
class WardenCrypto;
|
|
class WardenMemory;
|
|
class WardenModule;
|
|
class WardenModuleManager;
|
|
|
|
class WardenHandler {
|
|
public:
|
|
using PacketHandler = std::function<void(network::Packet&)>;
|
|
using DispatchTable = std::unordered_map<LogicalOpcode, PacketHandler>;
|
|
|
|
explicit WardenHandler(GameHandler& owner);
|
|
|
|
void registerOpcodes(DispatchTable& table);
|
|
|
|
// --- Public API ---
|
|
|
|
/** Reset all warden state (called on connect / disconnect). */
|
|
void reset();
|
|
|
|
/** Initialize warden module manager (called once from GameHandler ctor). */
|
|
void initModuleManager();
|
|
|
|
/** Whether the server requires Warden (gates char enum / create). */
|
|
bool requiresWarden() const { return requiresWarden_; }
|
|
void setRequiresWarden(bool v) { requiresWarden_ = v; }
|
|
|
|
bool wardenGateSeen() const { return wardenGateSeen_; }
|
|
|
|
/** Increment packet-after-gate counter (called from handlePacket). */
|
|
void notifyPacketAfterGate() { ++wardenPacketsAfterGate_; }
|
|
|
|
bool wardenCharEnumBlockedLogged() const { return wardenCharEnumBlockedLogged_; }
|
|
void setWardenCharEnumBlockedLogged(bool v) { wardenCharEnumBlockedLogged_ = v; }
|
|
|
|
/** Called from GameHandler::update() to drain async warden response + log gate timing. */
|
|
void update(float deltaTime);
|
|
|
|
private:
|
|
void handleWardenData(network::Packet& packet);
|
|
bool loadWardenCRFile(const std::string& moduleHashHex);
|
|
|
|
GameHandler& owner_;
|
|
|
|
// --- Warden state ---
|
|
bool requiresWarden_ = false;
|
|
bool wardenGateSeen_ = false;
|
|
float wardenGateElapsed_ = 0.0f;
|
|
float wardenGateNextStatusLog_ = 2.0f;
|
|
uint32_t wardenPacketsAfterGate_ = 0;
|
|
bool wardenCharEnumBlockedLogged_ = false;
|
|
std::unique_ptr<WardenCrypto> wardenCrypto_;
|
|
std::unique_ptr<WardenMemory> wardenMemory_;
|
|
std::unique_ptr<WardenModuleManager> wardenModuleManager_;
|
|
|
|
// Warden module download state
|
|
enum class WardenState {
|
|
WAIT_MODULE_USE, // Waiting for first SMSG (MODULE_USE)
|
|
WAIT_MODULE_CACHE, // Sent MODULE_MISSING, receiving module chunks
|
|
WAIT_HASH_REQUEST, // Module received, waiting for HASH_REQUEST
|
|
WAIT_CHECKS, // Hash sent, waiting for check requests
|
|
};
|
|
WardenState wardenState_ = WardenState::WAIT_MODULE_USE;
|
|
std::vector<uint8_t> wardenModuleHash_; // 16 bytes MD5
|
|
std::vector<uint8_t> wardenModuleKey_; // 16 bytes RC4
|
|
uint32_t wardenModuleSize_ = 0;
|
|
std::vector<uint8_t> wardenModuleData_; // Downloaded module chunks
|
|
std::vector<uint8_t> wardenLoadedModuleImage_; // Parsed module image for key derivation
|
|
std::shared_ptr<WardenModule> wardenLoadedModule_; // Loaded Warden module
|
|
|
|
// Pre-computed challenge/response entries from .cr file
|
|
struct WardenCREntry {
|
|
uint8_t seed[16];
|
|
uint8_t reply[20];
|
|
uint8_t clientKey[16]; // Encrypt key (client→server)
|
|
uint8_t serverKey[16]; // Decrypt key (server→client)
|
|
};
|
|
std::vector<WardenCREntry> wardenCREntries_;
|
|
// Module-specific check type opcodes [9]: MEM, PAGE_A, PAGE_B, MPQ, LUA, DRIVER, TIMING, PROC, MODULE
|
|
uint8_t wardenCheckOpcodes_[9] = {};
|
|
|
|
// Async Warden response: avoids 5-second main-loop stalls from PAGE_A/PAGE_B code pattern searches
|
|
std::future<std::vector<uint8_t>> wardenPendingEncrypted_; // encrypted response bytes
|
|
bool wardenResponsePending_ = false;
|
|
};
|
|
|
|
} // namespace game
|
|
} // namespace wowee
|