AzerothCore 3.3.5a
OpenSource WoW Emulator
Loading...
Searching...
No Matches
Warden Class Referenceabstract

#include "Warden.h"

Inheritance diagram for Warden:
WardenMac WardenWin

Public Member Functions

 Warden ()
 
virtual ~Warden ()
 
virtual void Init (WorldSession *session, SessionKey const &k)=0
 
virtual ClientWardenModuleGetModuleForClient ()=0
 
virtual void InitializeModule ()=0
 
virtual void RequestHash ()=0
 
virtual void HandleHashResult (ByteBuffer &buff)=0
 
virtual bool IsCheckInProgress ()=0
 
virtual bool IsInitialized ()
 
virtual void ForceChecks ()=0
 
virtual void RequestChecks ()=0
 
virtual void HandleData (ByteBuffer &buff)=0
 
bool ProcessLuaCheckResponse (std::string const &msg)
 
void SendModuleToClient ()
 
void RequestModule ()
 
void Update (uint32 const diff)
 
void DecryptData (uint8 *buffer, uint32 length)
 
void EncryptData (uint8 *buffer, uint32 length)
 
void ApplyPenalty (uint16 checkId, std::string const &reason)
 
WardenPayloadMgrGetPayloadMgr ()
 

Static Public Member Functions

static bool IsValidCheckSum (uint32 checksum, uint8 const *data, const uint16 length)
 
static uint32 BuildChecksum (uint8 const *data, uint32 length)
 

Private Attributes

WorldSession_session
 
WardenPayloadMgr _payloadMgr
 
uint8 _inputKey [16]
 
uint8 _outputKey [16]
 
uint8 _seed [16]
 
Acore::Crypto::ARC4 _inputCrypto
 
Acore::Crypto::ARC4 _outputCrypto
 
uint32 _checkTimer
 
uint32 _clientResponseTimer
 
bool _dataSent
 
ClientWardenModule_module
 
bool _initialized
 
bool _interrupted
 
bool _checkInProgress
 
uint32 _interruptCounter = 0
 

Friends

class WardenWin
 
class WardenMac
 

Detailed Description

Constructor & Destructor Documentation

◆ Warden()

Warden::Warden ( )
31 : _session(nullptr), _checkTimer(10000/*10 sec*/), _clientResponseTimer(0),
32 _dataSent(false), _module(nullptr), _initialized(false), _interrupted(false), _checkInProgress(false)
33{
34 memset(_inputKey, 0, sizeof(_inputKey));
35 memset(_outputKey, 0, sizeof(_outputKey));
36 memset(_seed, 0, sizeof(_seed));
37}
uint32 _checkTimer
Definition Warden.h:145
uint32 _clientResponseTimer
Definition Warden.h:146
uint8 _inputKey[16]
Definition Warden.h:140
uint8 _outputKey[16]
Definition Warden.h:141
uint8 _seed[16]
Definition Warden.h:142
ClientWardenModule * _module
Definition Warden.h:148
bool _checkInProgress
Definition Warden.h:151
bool _dataSent
Definition Warden.h:147
bool _initialized
Definition Warden.h:149
WorldSession * _session
Definition Warden.h:138
bool _interrupted
Definition Warden.h:150

References _inputKey, _outputKey, and _seed.

◆ ~Warden()

Warden::~Warden ( )
virtual
40{
41 if (_module)
42 {
43 delete[] _module->CompressedData;
44 delete _module;
45 _module = nullptr;
46 }
47 _initialized = false;
48}
uint8 * CompressedData
Definition Warden.h:97

References _initialized, _module, and ClientWardenModule::CompressedData.

Member Function Documentation

◆ ApplyPenalty()

void Warden::ApplyPenalty ( uint16  checkId,
std::string const &  reason 
)
200{
201 WardenCheck const* checkData = sWardenCheckMgr->GetWardenDataById(checkId);
202
204 std::string causeMsg;
205 if (checkId && checkData)
206 {
207 action = checkData->Action;
208
209 if (checkData->Comment.empty())
210 {
211 causeMsg = "Warden id " + std::to_string(checkId) + " violation";
212 }
213 else
214 {
215 causeMsg = "Warden: " + checkData->Comment;
216 }
217 }
218 else
219 {
220 // if its not warden check id based, reason must be always provided
221 ASSERT(!reason.empty());
222 causeMsg = reason;
223 }
224
225 switch (action)
226 {
228 break;
230 {
231 _session->KickPlayer(causeMsg.find("Warden") != std::string::npos ? causeMsg : "Warden: " + causeMsg);
232 break;
233 }
235 {
236 std::stringstream duration;
237 duration << sWorld->getIntConfig(CONFIG_WARDEN_CLIENT_BAN_DURATION) << "s";
238 std::string accountName;
240 sBan->BanAccount(accountName, duration.str(), causeMsg, "Server");
241 break;
242 }
243 }
244
245 std::string reportMsg;
246 if (checkId)
247 {
248 if (Player const* plr = _session->GetPlayer())
249 {
250 std::string const reportFormat = "Player {} (guid {}, account id: {}) failed warden {} check ({}). Action: {}";
251 reportMsg = Acore::StringFormat(reportFormat, plr->GetName(), plr->GetGUID().GetCounter(), _session->GetAccountId(),
252 checkId, ((checkData && !checkData->Comment.empty()) ? checkData->Comment : "<warden comment is not set>"),
253 GetWardenActionStr(action));
254 }
255 else
256 {
257 std::string const reportFormat = "Account id: {} failed warden {} check. Action: {}";
258 reportMsg = Acore::StringFormat(reportFormat, _session->GetAccountId(), checkId, GetWardenActionStr(action));
259 }
260 }
261 else
262 {
263 if (Player const* plr = _session->GetPlayer())
264 {
265 std::string const reportFormat = "Player {} (guid {}, account id: {}) triggered warden penalty by reason: {}. Action: {}";
266 reportMsg = Acore::StringFormat(reportFormat, plr->GetName(), plr->GetGUID().GetCounter(), _session->GetAccountId(), causeMsg, GetWardenActionStr(action));
267 }
268 else
269 {
270 std::string const reportFormat = "Account id: {} failed warden {} check. Action: {}";
271 reportMsg = Acore::StringFormat(reportFormat, _session->GetAccountId(), causeMsg, GetWardenActionStr(action));
272 }
273 }
274
275 reportMsg = "Warden: " + reportMsg;
276 LOG_INFO("warden", "> Warden: {}", reportMsg);
277}
#define sBan
Definition BanMgr.h:48
std::uint32_t uint32
Definition Define.h:107
#define ASSERT
Definition Errors.h:68
#define LOG_INFO(filterType__,...)
Definition Log.h:166
#define sWardenCheckMgr
Definition WardenCheckMgr.h:89
WardenActions
Definition WardenCheckMgr.h:26
@ WARDEN_ACTION_KICK
Definition WardenCheckMgr.h:28
@ WARDEN_ACTION_BAN
Definition WardenCheckMgr.h:29
@ WARDEN_ACTION_LOG
Definition WardenCheckMgr.h:27
static std::string GetWardenActionStr(uint32 action)
Definition Warden.cpp:184
@ CONFIG_WARDEN_CLIENT_BAN_DURATION
Definition WorldConfig.h:338
@ CONFIG_WARDEN_CLIENT_FAIL_ACTION
Definition WorldConfig.h:337
Definition Player.h:1084
Player * GetPlayer() const
Definition WorldSession.h:444
uint32 GetAccountId() const
Definition WorldSession.h:443
void KickPlayer(bool setKicked=true)
Definition WorldSession.h:482
#define sWorld
Definition World.h:316
bool GetName(uint32 accountId, std::string &name)
Definition AccountMgr.cpp:264
std::string StringFormat(FormatString< Args... > fmt, Args &&... args)
Default AC string format function.
Definition StringFormat.h:44
Definition WardenCheckMgr.h:44
uint32 Action
Definition WardenCheckMgr.h:53
std::string Comment
Definition WardenCheckMgr.h:50

References _session, WardenCheck::Action, ASSERT, WardenCheck::Comment, CONFIG_WARDEN_CLIENT_BAN_DURATION, CONFIG_WARDEN_CLIENT_FAIL_ACTION, WorldSession::GetAccountId(), AccountMgr::GetName(), WorldSession::GetPlayer(), GetWardenActionStr(), WorldSession::KickPlayer(), LOG_INFO, sBan, Acore::StringFormat(), sWardenCheckMgr, sWorld, WARDEN_ACTION_BAN, WARDEN_ACTION_KICK, and WARDEN_ACTION_LOG.

Referenced by WardenWin::HandleData(), WardenMac::HandleHashResult(), WardenWin::HandleHashResult(), and ProcessLuaCheckResponse().

◆ BuildChecksum()

uint32 Warden::BuildChecksum ( uint8 const *  data,
uint32  length 
)
static
171{
172 keyData hash{};
173 hash.bytes = Acore::Crypto::SHA1::GetDigestOf(data, std::size_t(length));
174 uint32 checkSum = 0;
175
176 for (uint8 i = 0; i < 5; ++i)
177 {
178 checkSum = checkSum ^ hash.ints[i];
179 }
180
181 return checkSum;
182}
std::uint8_t uint8
Definition Define.h:109
static Digest GetDigestOf(uint8 const *data, std::size_t len)
Definition CryptoHash.h:48
Definition Warden.cpp:165
std::array< uint8, 20 > bytes
Definition Warden.cpp:166

References keyData::bytes, and Acore::Impl::GenericHash< HashCreator, DigestLength >::GetDigestOf().

Referenced by WardenWin::InitializeModule(), and IsValidCheckSum().

◆ DecryptData()

void Warden::DecryptData ( uint8 buffer,
uint32  length 
)
134{
135 _inputCrypto.UpdateData(buffer, length);
136}
void UpdateData(uint8 *data, std::size_t len)
Definition ARC4.cpp:44
Acore::Crypto::ARC4 _inputCrypto
Definition Warden.h:143

References _inputCrypto, and Acore::Crypto::ARC4::UpdateData().

◆ EncryptData()

void Warden::EncryptData ( uint8 buffer,
uint32  length 
)

◆ ForceChecks()

virtual void Warden::ForceChecks ( )
pure virtual

Implemented in WardenWin.

◆ GetModuleForClient()

virtual ClientWardenModule * Warden::GetModuleForClient ( )
pure virtual

Implemented in WardenMac, and WardenWin.

◆ GetPayloadMgr()

WardenPayloadMgr * Warden::GetPayloadMgr ( )
316{
317 return &_payloadMgr;
318}
WardenPayloadMgr _payloadMgr
Definition Warden.h:139

References _payloadMgr.

◆ HandleData()

virtual void Warden::HandleData ( ByteBuffer buff)
pure virtual

Implemented in WardenMac, and WardenWin.

◆ HandleHashResult()

virtual void Warden::HandleHashResult ( ByteBuffer buff)
pure virtual

Implemented in WardenMac, and WardenWin.

◆ Init()

virtual void Warden::Init ( WorldSession session,
SessionKey const &  k 
)
pure virtual

Implemented in WardenMac, and WardenWin.

◆ InitializeModule()

virtual void Warden::InitializeModule ( )
pure virtual

Implemented in WardenMac, and WardenWin.

◆ IsCheckInProgress()

virtual bool Warden::IsCheckInProgress ( )
pure virtual

Implemented in WardenWin.

◆ IsInitialized()

bool Warden::IsInitialized ( )
virtual
160{
161 return _initialized;
162}

References _initialized.

◆ IsValidCheckSum()

bool Warden::IsValidCheckSum ( uint32  checksum,
uint8 const *  data,
const uint16  length 
)
static
144{
145 uint32 newChecksum = BuildChecksum(data, length);
146
147 if (checksum != newChecksum)
148 {
149 LOG_DEBUG("warden", "CHECKSUM IS NOT VALID");
150 return false;
151 }
152 else
153 {
154 LOG_DEBUG("warden", "CHECKSUM IS VALID");
155 return true;
156 }
157}
#define LOG_DEBUG(filterType__,...)
Definition Log.h:170
static uint32 BuildChecksum(uint8 const *data, uint32 length)
Definition Warden.cpp:170

References BuildChecksum(), and LOG_DEBUG.

Referenced by WardenWin::HandleData().

◆ ProcessLuaCheckResponse()

bool Warden::ProcessLuaCheckResponse ( std::string const &  msg)
280{
281 static constexpr char WARDEN_TOKEN[] = "_TW\t";
282 // if msg starts with WARDEN_TOKEN
283 if (msg.rfind(WARDEN_TOKEN, 0) != 0)
284 {
285 return false;
286 }
287
288 uint16 id = 0;
289
290 {
291 std::stringstream msg2(msg);
292 std::string temp;
293 while (msg2 >> temp)
294 {
295 // Found check id - stop loop
296 if (std::stringstream(temp) >> id)
297 break;
298 }
299 }
300
301 if (id < sWardenCheckMgr->GetMaxValidCheckId())
302 {
303 WardenCheck const* check = sWardenCheckMgr->GetWardenDataById(id);
304 if (check && check->Type == LUA_EVAL_CHECK)
305 {
306 ApplyPenalty(id, "");
307 return true;
308 }
309 }
310
311 ApplyPenalty(0, "Sent bogus Lua check response for Warden");
312 return true;
313}
std::uint16_t uint16
Definition Define.h:108
@ LUA_EVAL_CHECK
Definition Warden.h:52
void ApplyPenalty(uint16 checkId, std::string const &reason)
Definition Warden.cpp:199
uint8 Type
Definition WardenCheckMgr.h:45

References ApplyPenalty(), LUA_EVAL_CHECK, sWardenCheckMgr, and WardenCheck::Type.

◆ RequestChecks()

virtual void Warden::RequestChecks ( )
pure virtual

Implemented in WardenMac, and WardenWin.

Referenced by Update().

◆ RequestHash()

virtual void Warden::RequestHash ( )
pure virtual

Implemented in WardenMac, and WardenWin.

◆ RequestModule()

void Warden::RequestModule ( )
77{
78 LOG_DEBUG("warden", "Request module");
79
80 // Create packet structure
81 WardenModuleUse request{};
83
84 memcpy(request.ModuleId, _module->Id.data(), 16);
85 memcpy(request.ModuleKey, _module->Key.data(), 16);
86 request.Size = _module->CompressedSize;
87
88 EndianConvert(request.Size);
89
90 // Encrypt with warden RC4 key.
91 EncryptData((uint8*)&request, sizeof(WardenModuleUse));
92
94 pkt.append((uint8*)&request, sizeof(WardenModuleUse));
95 _session->SendPacket(&pkt);
96}
void EndianConvert(T &val)
Definition ByteConverter.h:47
@ WARDEN_SMSG_MODULE_USE
Definition Warden.h:38
void EncryptData(uint8 *buffer, uint32 length)
Definition Warden.cpp:138
Definition WorldPacket.h:26
void SendPacket(WorldPacket const *packet)
Send a packet to the client.
Definition WorldSession.cpp:283
@ SMSG_WARDEN_DATA
Definition Opcodes.h:772
uint32 CompressedSize
Definition Warden.h:96
std::array< uint8, 16 > Key
Definition Warden.h:95
std::array< uint8, 16 > Id
Definition Warden.h:94
Definition Warden.h:66
uint8 Command
Definition Warden.h:67

References _module, _session, ByteBuffer::append(), WardenModuleUse::Command, ClientWardenModule::CompressedSize, EncryptData(), EndianConvert(), ClientWardenModule::Id, ClientWardenModule::Key, LOG_DEBUG, WorldSession::SendPacket(), SMSG_WARDEN_DATA, and WARDEN_SMSG_MODULE_USE.

Referenced by WardenMac::Init(), and WardenWin::Init().

◆ SendModuleToClient()

void Warden::SendModuleToClient ( )
51{
52 LOG_DEBUG("warden", "Send module to client");
53
54 // Create packet structure
56
57 uint32 sizeLeft = _module->CompressedSize;
58 uint32 pos = 0;
59 uint16 burstSize;
60 while (sizeLeft > 0)
61 {
62 burstSize = sizeLeft < 500 ? sizeLeft : 500;
64 packet.DataSize = burstSize;
65 memcpy(packet.Data, &_module->CompressedData[pos], burstSize);
66 sizeLeft -= burstSize;
67 pos += burstSize;
68
69 EncryptData((uint8*)&packet, burstSize + 3);
70 WorldPacket pkt1(SMSG_WARDEN_DATA, burstSize + 3);
71 pkt1.append((uint8*)&packet, burstSize + 3);
72 _session->SendPacket(&pkt1);
73 }
74}
@ WARDEN_SMSG_MODULE_CACHE
Definition Warden.h:39
Definition Warden.h:74
uint16 DataSize
Definition Warden.h:76
uint8 Command
Definition Warden.h:75
uint8 Data[500]
Definition Warden.h:77

References _module, _session, ByteBuffer::append(), WardenModuleTransfer::Command, ClientWardenModule::CompressedData, ClientWardenModule::CompressedSize, WardenModuleTransfer::Data, WardenModuleTransfer::DataSize, EncryptData(), LOG_DEBUG, WorldSession::SendPacket(), SMSG_WARDEN_DATA, and WARDEN_SMSG_MODULE_CACHE.

◆ Update()

void Warden::Update ( uint32 const  diff)
99{
100 if (!_initialized)
101 {
102 return;
103 }
104
105 if (_dataSent)
106 {
107 uint32 maxClientResponseDelay = sWorld->getIntConfig(CONFIG_WARDEN_CLIENT_RESPONSE_DELAY);
108 if (maxClientResponseDelay > 0)
109 {
110 if (_clientResponseTimer > maxClientResponseDelay * IN_MILLISECONDS)
111 {
112 _session->KickPlayer("Warden: clientResponseTimer > maxClientResponseDelay (Warden::Update)");
113 }
114 else
115 {
116 _clientResponseTimer += diff;
117 }
118 }
119 }
120 else
121 {
122 if (diff >= _checkTimer)
123 {
125 }
126 else
127 {
128 _checkTimer -= diff;
129 }
130 }
131}
constexpr auto IN_MILLISECONDS
Definition Common.h:53
@ CONFIG_WARDEN_CLIENT_RESPONSE_DELAY
Definition WorldConfig.h:335
virtual void RequestChecks()=0

References _checkTimer, _clientResponseTimer, _dataSent, _initialized, _session, CONFIG_WARDEN_CLIENT_RESPONSE_DELAY, IN_MILLISECONDS, WorldSession::KickPlayer(), RequestChecks(), and sWorld.

Friends And Related Symbol Documentation

◆ WardenMac

friend class WardenMac
friend

◆ WardenWin

friend class WardenWin
friend

Member Data Documentation

◆ _checkInProgress

bool Warden::_checkInProgress
private

◆ _checkTimer

uint32 Warden::_checkTimer
private

Referenced by WardenWin::HandleData(), and Update().

◆ _clientResponseTimer

uint32 Warden::_clientResponseTimer
private

◆ _dataSent

◆ _initialized

bool Warden::_initialized
private

◆ _inputCrypto

◆ _inputKey

◆ _interruptCounter

uint32 Warden::_interruptCounter = 0
private

◆ _interrupted

bool Warden::_interrupted
private

◆ _module

◆ _outputCrypto

◆ _outputKey

◆ _payloadMgr

WardenPayloadMgr Warden::_payloadMgr
private

◆ _seed

◆ _session


The documentation for this class was generated from the following files: