Advertisement
Guest User

Untitled

a guest
Aug 13th, 2009
127
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 45.30 KB | None | 0 0
  1. diff --git a/src/game/MovementHandler.cpp b/src/game/MovementHandler.cpp
  2. index 4650e04..b34ea79 100644
  3. --- a/src/game/MovementHandler.cpp
  4. +++ b/src/game/MovementHandler.cpp
  5. @@ -31,7 +31,11 @@
  6. #include "WaypointMovementGenerator.h"
  7. #include "InstanceSaveMgr.h"
  8. #include "ObjectMgr.h"
  9. +#include "World.h"
  10.  
  11. +/*Movement anticheat DEBUG defines */
  12. +//#define MOVEMENT_ANTICHEAT_DEBUG true
  13. +/*end Movement anticheate defines*/
  14. void WorldSession::HandleMoveWorldportAckOpcode( WorldPacket & /*recv_data*/ )
  15. {
  16. sLog.outDebug( "WORLD: got MSG_MOVE_WORLDPORT_ACK." );
  17. @@ -53,6 +57,9 @@ void WorldSession::HandleMoveWorldportAckOpcode()
  18. LogoutPlayer(false);
  19. return;
  20. }
  21. + //movement anticheat
  22. + GetPlayer()->m_anti_JustTeleported = 1;
  23. + //end movement anticheat
  24.  
  25. // get the destination map entry, not the current one, this will fix homebind and reset greeting
  26. MapEntry const* mEntry = sMapStore.LookupEntry(loc.mapid);
  27. @@ -216,8 +223,12 @@ void WorldSession::HandleMovementOpcodes( WorldPacket & recv_data )
  28. Player *plMover = mover->GetTypeId()==TYPEID_PLAYER ? (Player*)mover : NULL;
  29.  
  30. // ignore, waiting processing in WorldSession::HandleMoveWorldportAckOpcode and WorldSession::HandleMoveTeleportAck
  31. - if(plMover && plMover->IsBeingTeleported())
  32. + if(plMover && plMover->IsBeingTeleported()){
  33. + // movement anticheat
  34. + plMover->m_anti_JustTeleported = 1;
  35. + // end movement anticheat
  36. return;
  37. + }
  38.  
  39. /* extract packet */
  40. MovementInfo movementInfo;
  41. @@ -239,43 +250,63 @@ void WorldSession::HandleMovementOpcodes( WorldPacket & recv_data )
  42. {
  43. // transports size limited
  44. // (also received at zeppelin leave by some reason with t_* as absolute in continent coordinates, can be safely skipped)
  45. - if( movementInfo.t_x > 50 || movementInfo.t_y > 50 || movementInfo.t_z > 50 )
  46. + if( movementInfo.t_x > 60 || movementInfo.t_y > 60 || movementInfo.t_x < -60 || movementInfo.t_y < -60 )
  47. return;
  48.  
  49. if( !MaNGOS::IsValidMapCoord(movementInfo.x+movementInfo.t_x, movementInfo.y + movementInfo.t_y,
  50. movementInfo.z + movementInfo.t_z, movementInfo.o + movementInfo.t_o) )
  51. return;
  52.  
  53. - // if we boarded a transport, add us to it
  54. - if (plMover && !plMover->m_transport)
  55. + if (plMover && plMover->m_anti_TransportGUID == 0 && (movementInfo.t_guid !=0))
  56. {
  57. - // elevators also cause the client to send MOVEMENTFLAG_ONTRANSPORT - just unmount if the guid can be found in the transport list
  58. - for (MapManager::TransportSet::const_iterator iter = MapManager::Instance().m_Transports.begin(); iter != MapManager::Instance().m_Transports.end(); ++iter)
  59. + // if we boarded a transport, add us to it
  60. + if (plMover && !plMover->m_transport)
  61. {
  62. - if ((*iter)->GetGUID() == movementInfo.t_guid)
  63. + // elevators also cause the client to send MOVEMENTFLAG_ONTRANSPORT - just unmount if the guid can be found in the transport list
  64. + for (MapManager::TransportSet::const_iterator iter = MapManager::Instance().m_Transports.begin(); iter != MapManager::Instance().m_Transports.end(); ++iter)
  65. {
  66. - plMover->m_transport = (*iter);
  67. - (*iter)->AddPassenger(plMover);
  68. - break;
  69. + if ((*iter)->GetGUID() == movementInfo.t_guid)
  70. + {
  71. + plMover->m_transport = (*iter);
  72. + (*iter)->AddPassenger(plMover);
  73. + break;
  74. + }
  75. }
  76. }
  77. + //movement anticheat;
  78. + //Correct finding GO guid in DB (thanks to GriffonHeart)
  79. + GameObject *obj = HashMapHolder<GameObject>::Find(movementInfo.t_guid);
  80. + if(obj)
  81. + plMover->m_anti_TransportGUID = obj->GetDBTableGUIDLow();
  82. + else
  83. + plMover->m_anti_TransportGUID = GUID_LOPART(movementInfo.t_guid);
  84. + // end movement anticheat
  85. + }
  86. + } else if (plMover && plMover->m_anti_TransportGUID != 0){
  87. + if (plMover && plMover->m_transport) // if we were on a transport, leave
  88. + {
  89. + plMover->m_transport->RemovePassenger(plMover);
  90. + plMover->m_transport = NULL;
  91. }
  92. - }
  93. - else if (plMover && plMover->m_transport) // if we were on a transport, leave
  94. - {
  95. - plMover->m_transport->RemovePassenger(plMover);
  96. - plMover->m_transport = NULL;
  97. movementInfo.t_x = 0.0f;
  98. movementInfo.t_y = 0.0f;
  99. movementInfo.t_z = 0.0f;
  100. movementInfo.t_o = 0.0f;
  101. movementInfo.t_time = 0;
  102. movementInfo.t_seat = -1;
  103. + plMover->m_anti_TransportGUID = 0;
  104. }
  105.  
  106. // fall damage generation (ignore in flight case that can be triggered also at lags in moment teleportation to another map).
  107. if (opcode == MSG_MOVE_FALL_LAND && plMover && !plMover->isInFlight())
  108. + {
  109. + //movement anticheat
  110. + plMover->m_anti_JustJumped = 0;
  111. + plMover->m_anti_JumpBaseZ = 0;
  112. + //end movement anticheat
  113. plMover->HandleFall(movementInfo);
  114. + }
  115. +
  116.  
  117. if (plMover && (movementInfo.HasMovementFlag(MOVEMENTFLAG_SWIMMING) != plMover->IsInWater()))
  118. {
  119. @@ -284,8 +315,299 @@ void WorldSession::HandleMovementOpcodes( WorldPacket & recv_data )
  120. }
  121.  
  122. /*----------------------*/
  123. + //---- anti-cheat features -->>>
  124. + bool check_passed = true;
  125. + #ifdef MOVEMENT_ANTICHEAT_DEBUG
  126. + if (plMover){
  127. + sLog.outBasic("MA-%s > client-time:%d fall-time:%d | xyzo: %f,%f,%fo(%f) flags[%X] opcode[%s]| transport (xyzo): %f,%f,%fo(%f)",
  128. + plMover->GetName(),movementInfo.time,movementInfo.fallTime,movementInfo.x,movementInfo.y,movementInfo.z,movementInfo.o,
  129. + movementInfo.flags, LookupOpcodeName(opcode),movementInfo.t_x,movementInfo.t_y,movementInfo.t_z,movementInfo.t_o);
  130. + sLog.outBasic("MA-%s Transport > server GUID: %d | client GUID: (lo)%d - (hi)%d",
  131. + plMover->GetName(),plMover->m_anti_TransportGUID, GUID_LOPART(movementInfo.t_guid), GUID_HIPART(movementInfo.t_guid));
  132. + } else {
  133. + sLog.outBasic("MA > client-time:%d fall-time:%d | xyzo: %f,%f,%fo(%f) flags[%X] opcode[%s]| transport (xyzo): %f,%f,%fo(%f)",
  134. + movementInfo.time,movementInfo.fallTime,movementInfo.x,movementInfo.y,movementInfo.z,movementInfo.o,
  135. + movementInfo.flags, LookupOpcodeName(opcode),movementInfo.t_x,movementInfo.t_y,movementInfo.t_z,movementInfo.t_o);
  136. + sLog.outBasic("MA Transport > server GUID: | client GUID: (lo)%d - (hi)%d",
  137. + GUID_LOPART(movementInfo.t_guid), GUID_HIPART(movementInfo.t_guid));
  138. + }
  139. + #endif
  140. +
  141. + if (plMover && World::GetEnableMvAnticheat())
  142. + {
  143. + //calc time deltas
  144. + int32 cClientTimeDelta = 1500;
  145. + if (plMover->m_anti_LastClientTime !=0){
  146. + cClientTimeDelta = movementInfo.time - plMover->m_anti_LastClientTime;
  147. + plMover->m_anti_DeltaClientTime += cClientTimeDelta;
  148. + plMover->m_anti_LastClientTime = movementInfo.time;
  149. + } else {
  150. + plMover->m_anti_LastClientTime = movementInfo.time;
  151. + }
  152. +
  153. + uint32 cServerTime=getMSTime();
  154. + uint32 cServerTimeDelta = 1500;
  155. + if (plMover->m_anti_LastServerTime != 0){
  156. + cServerTimeDelta = cServerTime - plMover->m_anti_LastServerTime;
  157. + plMover->m_anti_DeltaServerTime += cServerTimeDelta;
  158. + plMover->m_anti_LastServerTime = cServerTime;
  159. + } else {
  160. + plMover->m_anti_LastServerTime = cServerTime;
  161. + }
  162. +
  163. + //resync times on client login (first 15 sec for heavy areas)
  164. + if (plMover->m_anti_DeltaServerTime < 15000 && plMover->m_anti_DeltaClientTime < 15000)
  165. + plMover->m_anti_DeltaClientTime = plMover->m_anti_DeltaServerTime;
  166. +
  167. + int32 sync_time = plMover->m_anti_DeltaClientTime - plMover->m_anti_DeltaServerTime;
  168. +
  169. + #ifdef MOVEMENT_ANTICHEAT_DEBUG
  170. + sLog.outBasic("MA-%s Time > cClientTimeDelta: %d, cServerTime: %d || deltaC: %d - deltaS: %d || SyncTime: %d",
  171. + plMover->GetName(),cClientTimeDelta, cServerTime,
  172. + plMover->m_anti_DeltaClientTime, plMover->m_anti_DeltaServerTime, sync_time);
  173. + #endif
  174. +
  175. + //mistiming checks
  176. + int32 gmd = World::GetMistimingDelta();
  177. + if (sync_time > gmd || sync_time < -gmd){
  178. + cClientTimeDelta = cServerTimeDelta;
  179. + plMover->m_anti_MistimingCount++;
  180. +
  181. + sLog.outError("MA-%s, mistiming exception. #:%d, mistiming: %dms ",
  182. + plMover->GetName(), plMover->m_anti_MistimingCount, sync_time);
  183. +
  184. + if (plMover->m_anti_MistimingCount > World::GetMistimingAlarms())
  185. + {
  186. + plMover->GetSession()->KickPlayer();
  187. + return;
  188. + }
  189. + check_passed = false;
  190. + }
  191. + // end mistiming checks
  192. +
  193. +
  194. + uint32 curDest = plMover->m_taxi.GetTaxiDestination(); //check taxi flight
  195. + if ((plMover->m_anti_TransportGUID == 0) && !curDest)
  196. + {
  197. + UnitMoveType move_type;
  198. +
  199. + // calculating section ---------------------
  200. + //current speed
  201. + if (movementInfo.flags & MOVEMENTFLAG_FLYING) move_type = movementInfo.flags & MOVEMENTFLAG_BACKWARD ? MOVE_FLIGHT_BACK : MOVE_FLIGHT;
  202. + else if (movementInfo.flags & MOVEMENTFLAG_SWIMMING) move_type = movementInfo.flags & MOVEMENTFLAG_BACKWARD ? MOVE_SWIM_BACK : MOVE_SWIM;
  203. + else if (movementInfo.flags & MOVEMENTFLAG_WALK_MODE) move_type = MOVE_WALK;
  204. + //hmm... in first time after login player has MOVE_SWIMBACK instead MOVE_WALKBACK
  205. + else move_type = movementInfo.flags & MOVEMENTFLAG_BACKWARD ? MOVE_SWIM_BACK : MOVE_RUN;
  206. +
  207. + float current_speed = plMover->GetSpeed(move_type);
  208. + // end current speed
  209. +
  210. + // movement distance
  211. + float allowed_delta= 0;
  212. +
  213. + float delta_x = plMover->GetPositionX() - movementInfo.x;
  214. + float delta_y = plMover->GetPositionY() - movementInfo.y;
  215. + float delta_z = plMover->GetPositionZ() - movementInfo.z;
  216. + float real_delta = delta_x * delta_x + delta_y * delta_y;
  217. + float tg_z = -99999; //tangens
  218. + // end movement distance
  219. +
  220. + if (cClientTimeDelta < 0) {cClientTimeDelta = 0;}
  221. + float time_delta = (cClientTimeDelta < 1500) ? (float)cClientTimeDelta/1000 : 1.5f; //normalize time - 1.5 second allowed for heavy loaded server
  222. +
  223. + if (!(movementInfo.flags & (MOVEMENTFLAG_FLYING | MOVEMENTFLAG_SWIMMING)))
  224. + tg_z = (real_delta !=0) ? (delta_z*delta_z / real_delta) : -99999;
  225. +
  226. + if (current_speed < plMover->m_anti_Last_HSpeed)
  227. + {
  228. + allowed_delta = plMover->m_anti_Last_HSpeed;
  229. + if (plMover->m_anti_LastSpeedChangeTime == 0 )
  230. + plMover->m_anti_LastSpeedChangeTime = movementInfo.time + (uint32)floor(((plMover->m_anti_Last_HSpeed / current_speed) * 1500)) + 100; //100ms above for random fluctuating =)))
  231. + } else {
  232. + allowed_delta = current_speed;
  233. + }
  234. + allowed_delta = allowed_delta * time_delta;
  235. + allowed_delta = allowed_delta * allowed_delta + 2;
  236. + if (tg_z > 2.2)
  237. + allowed_delta = allowed_delta + (delta_z*delta_z)/2.37; // mountain fall allowed speed
  238. +
  239. + if (movementInfo.time>plMover->m_anti_LastSpeedChangeTime)
  240. + {
  241. + plMover->m_anti_Last_HSpeed = current_speed; // store current speed
  242. + plMover->m_anti_Last_VSpeed = -2.3f;
  243. + if (plMover->m_anti_LastSpeedChangeTime != 0) plMover->m_anti_LastSpeedChangeTime = 0;
  244. + }
  245. + // end calculating section ---------------------
  246. +
  247. + //AntiGravitation (thanks to Meekro)
  248. + float JumpHeight = plMover->m_anti_JumpBaseZ - movementInfo.z;
  249. + if ((plMover->m_anti_JumpBaseZ != 0)
  250. + && !(movementInfo.flags & (MOVEMENTFLAG_SWIMMING | MOVEMENTFLAG_FLYING | MOVEMENTFLAG_FLYING2))
  251. + && (JumpHeight < plMover->m_anti_Last_VSpeed))
  252. + {
  253. + #ifdef MOVEMENT_ANTICHEAT_DEBUG
  254. + sLog.outError("MA-%s, GraviJump exception. JumpHeight = %f, Allowed Veritcal Speed = %f",
  255. + plMover->GetName(), JumpHeight, plMover->m_anti_Last_VSpeed);
  256. + #endif
  257. + check_passed = false;
  258. + }
  259.  
  260. + //multi jump checks
  261. + if (opcode == MSG_MOVE_JUMP && !plMover->IsInWater())
  262. + {
  263. + if (plMover->m_anti_JustJumped >= 1){
  264. + check_passed = false; //don't process new jump packet
  265. + } else {
  266. + plMover->m_anti_JustJumped += 1;
  267. + plMover->m_anti_JumpBaseZ = movementInfo.z;
  268. + }
  269. + } else if (plMover->IsInWater()) {
  270. + plMover->m_anti_JustJumped = 0;
  271. + }
  272. +
  273. + //speed hack checks
  274. + if ((real_delta > allowed_delta)) // && (delta_z < 0))
  275. + {
  276. + #ifdef MOVEMENT_ANTICHEAT_DEBUG
  277. + sLog.outError("MA-%s, speed exception | cDelta=%f aDelta=%f | cSpeed=%f lSpeed=%f deltaTime=%f",
  278. + plMover->GetName(), real_delta, allowed_delta, current_speed, plMover->m_anti_Last_HSpeed,time_delta);
  279. + #endif
  280. + check_passed = false;
  281. + }
  282. + //teleport hack checks
  283. + if ((real_delta>4900.0f) && !(real_delta < allowed_delta))
  284. + {
  285. + #ifdef MOVEMENT_ANTICHEAT_DEBUG
  286. + sLog.outError("MA-%s, is teleport exception | cDelta=%f aDelta=%f | cSpeed=%f lSpeed=%f deltaToime=%f",
  287. + plMover->GetName(),real_delta, allowed_delta, current_speed, plMover->m_anti_Last_HSpeed,time_delta);
  288. + #endif
  289. + check_passed = false;
  290. + }
  291. +
  292. + //mountian hack checks // 1.56f (delta_z < GetPlayer()->m_anti_Last_VSpeed))
  293. + if ((delta_z < plMover->m_anti_Last_VSpeed) && (plMover->m_anti_JustJumped == 0) && (tg_z > 2.37f))
  294. + {
  295. + #ifdef MOVEMENT_ANTICHEAT_DEBUG
  296. + sLog.outError("MA-%s, mountain exception | tg_z=%f", plMover->GetName(),tg_z);
  297. + #endif
  298. + check_passed = false;
  299. + }
  300. + //Fly hack checks
  301. + if (((movementInfo.flags & (MOVEMENTFLAG_CAN_FLY | MOVEMENTFLAG_FLYING | MOVEMENTFLAG_FLYING2)) != 0)
  302. + && !plMover->isGameMaster()
  303. + && !(plMover->HasAuraType(SPELL_AURA_FLY) || plMover->HasAuraType(SPELL_AURA_MOD_INCREASE_FLIGHT_SPEED)))
  304. + {
  305. + #ifdef MOVEMENT_ANTICHEAT_DEBUG
  306. + sLog.outError("MA-%s, flight exception. {SPELL_AURA_FLY=[%X]} {SPELL_AURA_MOD_INCREASE_FLIGHT_SPEED=[%X]} {SPELL_AURA_MOD_SPEED_FLIGHT=[%X]} {SPELL_AURA_MOD_FLIGHT_SPEED_ALWAYS=[%X]} {SPELL_AURA_MOD_FLIGHT_SPEED_NOT_STACK=[%X]}",
  307. + plMover->GetName(),
  308. + plMover->HasAuraType(SPELL_AURA_FLY), plMover->HasAuraType(SPELL_AURA_MOD_INCREASE_FLIGHT_SPEED),
  309. + plMover->HasAuraType(SPELL_AURA_MOD_SPEED_FLIGHT), plMover->HasAuraType(SPELL_AURA_MOD_FLIGHT_SPEED_ALWAYS),
  310. + plMover->HasAuraType(SPELL_AURA_MOD_FLIGHT_SPEED_NOT_STACK));
  311. + #endif
  312. + check_passed = false;
  313. + }
  314. + //Water-Walk checks
  315. + if (((movementInfo.flags & MOVEMENTFLAG_WATERWALKING) != 0)
  316. + && !plMover->isGameMaster()
  317. + && !(plMover->HasAuraType(SPELL_AURA_WATER_WALK) | plMover->HasAuraType(SPELL_AURA_GHOST)))
  318. + {
  319. + #ifdef MOVEMENT_ANTICHEAT_DEBUG
  320. + sLog.outError("MA-%s, water-walk exception. [%X]{SPELL_AURA_WATER_WALK=[%X]}",
  321. + plMover->GetName(), movementInfo.flags, plMover->HasAuraType(SPELL_AURA_WATER_WALK));
  322. + #endif
  323. + check_passed = false;
  324. + }
  325. + //Teleport To Plane checks
  326. + if (movementInfo.z < 0.0001f && movementInfo.z > -0.0001f
  327. + && ((movementInfo.flags & (MOVEMENTFLAG_SWIMMING | MOVEMENTFLAG_CAN_FLY | MOVEMENTFLAG_FLYING | MOVEMENTFLAG_FLYING2)) == 0)
  328. + && !plMover->isGameMaster())
  329. + {
  330. + // Prevent using TeleportToPlan.
  331. + Map *map = plMover->GetMap();
  332. + if (map){
  333. + float plane_z = map->GetHeight(movementInfo.x, movementInfo.y, MAX_HEIGHT) - movementInfo.z;
  334. + plane_z = (plane_z < -500.0f) ? 0 : plane_z; //check holes in heigth map
  335. + if(plane_z > 0.1f || plane_z < -0.1f)
  336. + {
  337. + plMover->m_anti_TeleToPlane_Count++;
  338. + check_passed = false;
  339. + #ifdef MOVEMENT_ANTICHEAT_DEBUG
  340. + sLog.outDebug("MA-%s, teleport to plan exception. plane_z: %f ",
  341. + plMover->GetName(), plane_z);
  342. + #endif
  343. + if (plMover->m_anti_TeleToPlane_Count > World::GetTeleportToPlaneAlarms())
  344. + {
  345. + sLog.outError("MA-%s, teleport to plan exception. Exception count: %d ",
  346. + plMover->GetName(), plMover->m_anti_TeleToPlane_Count);
  347. + plMover->GetSession()->KickPlayer();
  348. + return;
  349. + }
  350. + }
  351. + }
  352. + } else {
  353. + if (plMover->m_anti_TeleToPlane_Count != 0)
  354. + plMover->m_anti_TeleToPlane_Count = 0;
  355. + }
  356. + } else if (movementInfo.flags & MOVEMENTFLAG_ONTRANSPORT) {
  357. + //antiwrap checks
  358. + if (plMover->m_transport)
  359. + {
  360. + float trans_rad = movementInfo.t_x*movementInfo.t_x + movementInfo.t_y*movementInfo.t_y + movementInfo.t_z*movementInfo.t_z;
  361. + if (trans_rad > 3600.0f){
  362. + check_passed = false;
  363. + #ifdef MOVEMENT_ANTICHEAT_DEBUG
  364. + sLog.outError("MA-%s, leave transport.", plMover->GetName());
  365. + #endif
  366. + }
  367. + } else {
  368. + if (GameObjectData const* go_data = objmgr.GetGOData(plMover->m_anti_TransportGUID))
  369. + {
  370. + float delta_gox = go_data->posX - movementInfo.x;
  371. + float delta_goy = go_data->posY - movementInfo.y;
  372. + float delta_goz = go_data->posZ - movementInfo.z;
  373. + int mapid = go_data->mapid;
  374. + #ifdef MOVEMENT_ANTICHEAT_DEBUG
  375. + sLog.outDebug("MA-%s, transport movement. GO xyzo: %f,%f,%f",
  376. + plMover->GetName(), go_data->posX,go_data->posY,go_data->posZ);
  377. + #endif
  378. + if (plMover->GetMapId() != mapid){
  379. + check_passed = false;
  380. + } else if (mapid !=369) {
  381. + float delta_go = delta_gox*delta_gox + delta_goy*delta_goy;
  382. + if (delta_go > 3600.0f) {
  383. + check_passed = false;
  384. + #ifdef MOVEMENT_ANTICHEAT_DEBUG
  385. + sLog.outError("MA-%s, leave transport. GO xyzo: %f,%f,%f",
  386. + plMover->GetName(), go_data->posX,go_data->posY,go_data->posZ);
  387. + #endif
  388. + }
  389. + }
  390. +
  391. + } else {
  392. + #ifdef MOVEMENT_ANTICHEAT_DEBUG
  393. + sLog.outDebug("MA-%s, undefined transport.", plMover->GetName());
  394. + #endif
  395. + check_passed = false;
  396. + }
  397. + }
  398. + if (!check_passed){
  399. + if (plMover->m_transport)
  400. + {
  401. + plMover->m_transport->RemovePassenger(plMover);
  402. + plMover->m_transport = NULL;
  403. + }
  404. + movementInfo.t_x = 0.0f;
  405. + movementInfo.t_y = 0.0f;
  406. + movementInfo.t_z = 0.0f;
  407. + movementInfo.t_o = 0.0f;
  408. + movementInfo.t_time = 0;
  409. + plMover->m_anti_TransportGUID = 0;
  410. + }
  411. + }
  412. + }
  413. /* process position-change */
  414. + if (check_passed)
  415. + {
  416. recv_data.put<uint32>(6, getMSTime()); // fix time, offset flags(4) + unk(2)
  417. WorldPacket data(recv_data.GetOpcode(), (mover->GetPackGUID().size()+recv_data.size()));
  418. data.append(mover->GetPackGUID()); // use mover guid
  419. @@ -331,12 +653,28 @@ void WorldSession::HandleMovementOpcodes( WorldPacket & recv_data )
  420. plMover->RepopAtGraveyard();
  421. }
  422. }
  423. + //movement anticheat >>>
  424. + if (plMover->m_anti_AlarmCount > 0){
  425. + sLog.outError("MA-%s produce %d anticheat alarms",plMover->GetName(),plMover->m_anti_AlarmCount);
  426. + plMover->m_anti_AlarmCount = 0;
  427. + }
  428. + // end movement anticheat
  429. }
  430. else // creature charmed
  431. {
  432. if(mover->IsInWorld())
  433. mover->GetMap()->CreatureRelocation((Creature*)mover, movementInfo.x, movementInfo.y, movementInfo.z, movementInfo.o);
  434. }
  435. +
  436. + } else if (plMover) {
  437. + plMover->m_anti_AlarmCount++;
  438. + WorldPacket data;
  439. + plMover->m_movementInfo.SetMovementFlags(MovementFlags(MOVEMENTFLAG_NONE));
  440. + plMover->BuildTeleportAckMsg(&data, plMover->GetPositionX(), plMover->GetPositionY(), plMover->GetPositionZ(), plMover->GetOrientation());
  441. + plMover->GetSession()->SendPacket(&data);
  442. + plMover->BuildHeartBeatMsg(&data);
  443. + plMover->SendMessageToSet(&data, true);
  444. + }
  445. }
  446.  
  447. void WorldSession::HandleForceSpeedChangeAck(WorldPacket &recv_data)
  448. @@ -489,34 +827,33 @@ void WorldSession::HandleMountSpecialAnimOpcode(WorldPacket& /*recvdata*/)
  449. GetPlayer()->SendMessageToSet(&data, false);
  450. }
  451.  
  452. -void WorldSession::HandleMoveKnockBackAck( WorldPacket & /*recv_data*/ )
  453. +void WorldSession::HandleMoveKnockBackAck( WorldPacket & recv_data )
  454. {
  455. // CHECK_PACKET_SIZE(recv_data,?);
  456. sLog.outDebug("CMSG_MOVE_KNOCK_BACK_ACK");
  457. // Currently not used but maybe use later for recheck final player position
  458. // (must be at call same as into "recv_data >> x >> y >> z >> orientation;"
  459.  
  460. - /*
  461. - uint32 flags, time;
  462. - float x, y, z, orientation;
  463. - uint64 guid;
  464. - uint32 sequence;
  465. - uint32 ukn1;
  466. - float xdirection,ydirection,hspeed,vspeed;
  467. + /* extract packet */
  468. + MovementInfo movementInfo;
  469. + uint32 unk1,unk2,unk3;
  470. + recv_data >> unk1 >> unk2 >> unk3;
  471. + ReadMovementInfo(recv_data, &movementInfo);
  472.  
  473. - recv_data >> guid;
  474. - recv_data >> sequence;
  475. - recv_data >> flags >> time;
  476. - recv_data >> x >> y >> z >> orientation;
  477. - recv_data >> ukn1; //unknown
  478. - recv_data >> vspeed >> xdirection >> ydirection >> hspeed;
  479. + //Save movement flags
  480. + _player->m_movementInfo.SetMovementFlags(MovementFlags(movementInfo.flags));
  481.  
  482. - // skip not personal message;
  483. - if(GetPlayer()->GetGUID()!=guid)
  484. - return;
  485. + #ifdef MOVEMENT_ANTICHEAT_DEBUG
  486. + sLog.outBasic("%s CMSG_MOVE_KNOCK_BACK_ACK: tm:%d ftm:%d | %f,%f,%fo(%f) [%X]",GetPlayer()->GetName(),movementInfo.time,movementInfo.fallTime,movementInfo.x,movementInfo.y,movementInfo.z,movementInfo.o,movementInfo.flags);
  487. + sLog.outBasic("%s CMSG_MOVE_KNOCK_BACK_ACK additional: vspeed:%f, hspeed:%f",GetPlayer()->GetName(), movementInfo.j_unk, movementInfo.j_xyspeed);
  488. + #endif
  489. +
  490. + _player->m_movementInfo = movementInfo;
  491. + _player->m_anti_Last_HSpeed = movementInfo.j_xyspeed;
  492. + _player->m_anti_Last_VSpeed = movementInfo.j_unk < 3.2f ? movementInfo.j_unk - 1.0f : 3.2f;
  493.  
  494. - // check code
  495. - */
  496. + uint32 dt = (_player->m_anti_Last_VSpeed < 0) ? (int)(ceil(_player->m_anti_Last_VSpeed/-25)*1000) : (int)(ceil(_player->m_anti_Last_VSpeed/25)*1000);
  497. + _player->m_anti_LastSpeedChangeTime = movementInfo.time + dt + 1000;
  498. }
  499.  
  500. void WorldSession::HandleMoveHoverAck( WorldPacket& /*recv_data*/ )
  501. diff --git a/src/game/ObjectMgr.cpp b/src/game/ObjectMgr.cpp
  502. index 60d8fef..e40378c 100644
  503. --- a/src/game/ObjectMgr.cpp
  504. +++ b/src/game/ObjectMgr.cpp
  505. @@ -4841,8 +4841,8 @@ void ObjectMgr::LoadAreaTriggerScripts()
  506. sLog.outString();
  507. sLog.outString( ">> Loaded %u areatrigger scripts", count );
  508. }
  509. -
  510. -uint32 ObjectMgr::GetNearestTaxiNode( float x, float y, float z, uint32 mapid, uint32 team )
  511. +//use searched_node for search some known node
  512. +uint32 ObjectMgr::GetNearestTaxiNode( float x, float y, float z, uint32 mapid, uint32 team, uint32 searched_node )
  513. {
  514. bool found = false;
  515. float dist;
  516. @@ -4851,9 +4851,23 @@ uint32 ObjectMgr::GetNearestTaxiNode( float x, float y, float z, uint32 mapid, u
  517. for(uint32 i = 1; i < sTaxiNodesStore.GetNumRows(); ++i)
  518. {
  519. TaxiNodesEntry const* node = sTaxiNodesStore.LookupEntry(i);
  520. - if(!node || node->map_id != mapid || !node->MountCreatureID[team == ALLIANCE ? 1 : 0])
  521. +
  522. + if (!node || node->map_id != mapid)
  523. + continue;
  524. +
  525. + float dist2 = (node->x - x)*(node->x - x)+(node->y - y)*(node->y - y)+(node->z - z)*(node->z - z);
  526. +
  527. + if (searched_node != 0 && i == searched_node){
  528. + id = i;
  529. + dist = dist2;
  530. + break;
  531. + }
  532. +
  533. + if(!node->MountCreatureID[team == ALLIANCE ? 1 : 0])
  534. continue;
  535.  
  536. + // float dist2 = (node->x - x)*(node->x - x)+(node->y - y)*(node->y - y)+(node->z - z)*(node->z - z);
  537. +
  538. uint8 field = (uint8)((i - 1) / 32);
  539. uint32 submask = 1<<((i-1)%32);
  540.  
  541. @@ -4861,7 +4875,6 @@ uint32 ObjectMgr::GetNearestTaxiNode( float x, float y, float z, uint32 mapid, u
  542. if((sTaxiNodesMask[field] & submask)==0)
  543. continue;
  544.  
  545. - float dist2 = (node->x - x)*(node->x - x)+(node->y - y)*(node->y - y)+(node->z - z)*(node->z - z);
  546. if(found)
  547. {
  548. if(dist2 < dist)
  549. @@ -4878,6 +4891,11 @@ uint32 ObjectMgr::GetNearestTaxiNode( float x, float y, float z, uint32 mapid, u
  550. }
  551. }
  552.  
  553. + //movement anticheat fix
  554. + if (dist > 3600)
  555. + id = 0;
  556. + //movement anticheat fix
  557. +
  558. return id;
  559. }
  560.  
  561. diff --git a/src/game/ObjectMgr.h b/src/game/ObjectMgr.h
  562. index b36394c..a4705cf 100644
  563. --- a/src/game/ObjectMgr.h
  564. +++ b/src/game/ObjectMgr.h
  565. @@ -401,7 +401,7 @@ class ObjectMgr
  566. uint32 GetPlayerAccountIdByGUID(const uint64 &guid) const;
  567. uint32 GetPlayerAccountIdByPlayerName(const std::string& name) const;
  568.  
  569. - uint32 GetNearestTaxiNode( float x, float y, float z, uint32 mapid, uint32 team );
  570. + uint32 GetNearestTaxiNode( float x, float y, float z, uint32 mapid, uint32 team, uint32 searched_node );
  571. void GetTaxiPath( uint32 source, uint32 destination, uint32 &path, uint32 &cost);
  572. uint32 GetTaxiMountDisplayId( uint32 id, uint32 team, bool allowed_alt_team = false);
  573. void GetTaxiPathNodes( uint32 path, Path &pathnodes, std::vector<uint32>& mapIds );
  574. diff --git a/src/game/Player.cpp b/src/game/Player.cpp
  575. index 650040e..7f158c8 100644
  576. --- a/src/game/Player.cpp
  577. +++ b/src/game/Player.cpp
  578. @@ -404,7 +404,30 @@ Player::Player (WorldSession *session): Unit(), m_achievementMgr(this), m_reputa
  579. m_rest_bonus=0;
  580. rest_type=REST_TYPE_NO;
  581. ////////////////////Rest System/////////////////////
  582. + //movement anticheat
  583. + m_anti_LastClientTime = 0; //last movement client time
  584. + m_anti_LastServerTime = 0; //last movement server time
  585. + m_anti_DeltaClientTime = 0; //client side session time
  586. + m_anti_DeltaServerTime = 0; //server side session time
  587. + m_anti_MistimingCount = 0; //mistiming counts before kick
  588.  
  589. + m_anti_LastSpeedChangeTime = 0; //last speed change time
  590. + m_anti_BeginFallTime = 0; //alternative falling begin time (obsolete)
  591. +
  592. + m_anti_Last_HSpeed = 7.0f; //horizontal speed, default RUN speed
  593. + m_anti_Last_VSpeed = -2.3f; //vertical speed, default max jump height
  594. +
  595. + m_anti_TransportGUID = 0; //current transport GUID
  596. +
  597. + m_anti_JustTeleported = 0; //seted when player was teleported
  598. + m_anti_TeleToPlane_Count = 0; //Teleport To Plane alarm counter
  599. +
  600. + m_anti_AlarmCount = 0; //alarm counter
  601. +
  602. + m_anti_JustJumped = 0; //Jump already began, anti air jump check
  603. + m_anti_JumpBaseZ = 0; //Z coord before jump (AntiGrav)
  604. + // << movement anticheat
  605. + /////////////////////////////////
  606. m_mailsLoaded = false;
  607. m_mailsUpdated = false;
  608. unReadMails = 0;
  609. @@ -1560,7 +1583,9 @@ bool Player::TeleportTo(uint32 mapid, float x, float y, float z, float orientati
  610. sLog.outError("TeleportTo: invalid map %d or absent instance template.", mapid);
  611. return false;
  612. }
  613. -
  614. + //movement anticheat
  615. + m_anti_JustTeleported = 1;
  616. + //end movement anticheat
  617. // preparing unsummon pet if lost (we must get pet before teleportation or will not find it later)
  618. Pet* pet = GetPet();
  619.  
  620. @@ -1615,6 +1640,7 @@ bool Player::TeleportTo(uint32 mapid, float x, float y, float z, float orientati
  621.  
  622. if ((GetMapId() == mapid) && (!m_transport))
  623. {
  624. + m_anti_JumpBaseZ = 0;
  625. //lets reset far teleport flag if it wasn't reset during chained teleports
  626. SetSemaphoreTeleportFar(false);
  627. //setup delayed teleport flag
  628. @@ -1761,6 +1787,7 @@ bool Player::TeleportTo(uint32 mapid, float x, float y, float z, float orientati
  629.  
  630. m_teleport_dest = WorldLocation(mapid, final_x, final_y, final_z, final_o);
  631. SetFallInformation(0, final_z);
  632. + m_anti_JumpBaseZ = 0;
  633. // if the player is saved before worldportack (at logout for example)
  634. // this will be used instead of the current location in SaveToDB
  635.  
  636. @@ -19482,6 +19509,8 @@ void Player::EnterVehicle(Vehicle *vehicle)
  637. data << uint32(0); // fall time
  638. GetSession()->SendPacket(&data);
  639.  
  640. + SetPosition(vehicle->GetPositionX(), vehicle->GetPositionY(), vehicle->GetPositionZ(),vehicle->GetOrientation());
  641. +
  642. data.Initialize(SMSG_PET_SPELLS, 8+2+4+4+4*MAX_UNIT_ACTION_BAR_INDEX+1+1);
  643. data << uint64(vehicle->GetGUID());
  644. data << uint16(0);
  645. diff --git a/src/game/Player.h b/src/game/Player.h
  646. index f951af9..e063a7a 100644
  647. --- a/src/game/Player.h
  648. +++ b/src/game/Player.h
  649. @@ -2384,6 +2384,29 @@ class MANGOS_DLL_SPEC Player : public Unit
  650. float m_rest_bonus;
  651. RestType rest_type;
  652. ////////////////////Rest System/////////////////////
  653. + //movement anticheat
  654. + uint32 m_anti_LastClientTime; //last movement client time
  655. + uint32 m_anti_LastServerTime; //last movement server time
  656. + uint32 m_anti_DeltaClientTime; //client side session time
  657. + uint32 m_anti_DeltaServerTime; //server side session time
  658. + uint32 m_anti_MistimingCount; //mistiming counts before kick
  659. +
  660. + uint32 m_anti_LastSpeedChangeTime;//last speed change time
  661. + uint32 m_anti_BeginFallTime; //alternative falling begin time (obsolete)
  662. +
  663. + float m_anti_Last_HSpeed; //horizontal speed, default RUN speed
  664. + float m_anti_Last_VSpeed; //vertical speed, default max jump height
  665. +
  666. + uint64 m_anti_TransportGUID; //current transport GUID
  667. +
  668. + uint32 m_anti_JustTeleported; //seted when player was teleported
  669. + uint32 m_anti_TeleToPlane_Count; //Teleport To Plane alarm counter
  670. +
  671. + uint64 m_anti_AlarmCount; //alarm counter
  672. +
  673. + uint32 m_anti_JustJumped; //Jump already began, anti air jump check
  674. + float m_anti_JumpBaseZ; //Z coord before jump
  675. + // << movement anticheat
  676.  
  677. // Transports
  678. Transport * m_transport;
  679. diff --git a/src/game/TaxiHandler.cpp b/src/game/TaxiHandler.cpp
  680. index fe2f28c..eef187b 100644
  681. --- a/src/game/TaxiHandler.cpp
  682. +++ b/src/game/TaxiHandler.cpp
  683. @@ -53,7 +53,7 @@ void WorldSession::SendTaxiStatus( uint64 guid )
  684. return;
  685. }
  686.  
  687. - uint32 curloc = objmgr.GetNearestTaxiNode(unit->GetPositionX(),unit->GetPositionY(),unit->GetPositionZ(),unit->GetMapId(),GetPlayer( )->GetTeam());
  688. + uint32 curloc = objmgr.GetNearestTaxiNode(unit->GetPositionX(),unit->GetPositionY(),unit->GetPositionZ(),unit->GetMapId(),GetPlayer( )->GetTeam(),0);
  689.  
  690. // not found nearest
  691. if(curloc == 0)
  692. @@ -100,7 +100,7 @@ void WorldSession::HandleTaxiQueryAvailableNodes( WorldPacket & recv_data )
  693. void WorldSession::SendTaxiMenu( Creature* unit )
  694. {
  695. // find current node
  696. - uint32 curloc = objmgr.GetNearestTaxiNode(unit->GetPositionX(),unit->GetPositionY(),unit->GetPositionZ(),unit->GetMapId(),GetPlayer( )->GetTeam());
  697. + uint32 curloc = objmgr.GetNearestTaxiNode(unit->GetPositionX(),unit->GetPositionY(),unit->GetPositionZ(),unit->GetMapId(),GetPlayer( )->GetTeam(), 0);
  698.  
  699. if ( curloc == 0 )
  700. return;
  701. @@ -135,7 +135,7 @@ void WorldSession::SendDoFlight( uint32 mountDisplayId, uint32 path, uint32 path
  702. bool WorldSession::SendLearnNewTaxiNode( Creature* unit )
  703. {
  704. // find current node
  705. - uint32 curloc = objmgr.GetNearestTaxiNode(unit->GetPositionX(),unit->GetPositionY(),unit->GetPositionZ(),unit->GetMapId(),GetPlayer( )->GetTeam());
  706. + uint32 curloc = objmgr.GetNearestTaxiNode(unit->GetPositionX(),unit->GetPositionY(),unit->GetPositionZ(),unit->GetMapId(),GetPlayer( )->GetTeam(), 0);
  707.  
  708. if ( curloc == 0 )
  709. return true; // `true` send to avoid WorldSession::SendTaxiMenu call with one more curlock seartch with same false result.
  710. @@ -193,7 +193,8 @@ void WorldSession::HandleActivateTaxiExpressOpcode ( WorldPacket & recv_data )
  711. GetPlayer()->ActivateTaxiPathTo(nodes, npc);
  712. }
  713.  
  714. -void WorldSession::HandleMoveSplineDoneOpcode(WorldPacket& /*recv_data*/)
  715. +
  716. +void WorldSession::HandleMoveSplineDoneOpcode(WorldPacket& recv_data)
  717. {
  718. sLog.outDebug( "WORLD: Received CMSG_MOVE_SPLINE_DONE" );
  719.  
  720. @@ -201,12 +202,93 @@ void WorldSession::HandleMoveSplineDoneOpcode(WorldPacket& /*recv_data*/)
  721. // 1) end taxi path in far (multi-node) flight
  722. // 2) switch from one map to other in case multim-map taxi path
  723. // we need proccess only (1)
  724. +
  725. + //movement anticheat code
  726. + /* extract packet */
  727. + Unit *mover = _player->m_mover;
  728. + Player *plMover = mover->GetTypeId()==TYPEID_PLAYER ? (Player*)mover : NULL;
  729. + if (!plMover)
  730. + return;
  731. +
  732. + MovementInfo movementInfo;
  733. + ReadMovementInfo(recv_data, &movementInfo);
  734. + //<<< end movement anticheat
  735. +
  736. uint32 curDest = GetPlayer()->m_taxi.GetTaxiDestination();
  737. +
  738. if(!curDest)
  739. + {
  740. + //movement anticheat code
  741. + GetPlayer()->SetPosition(movementInfo.x, movementInfo.y, movementInfo.z, movementInfo.o);
  742. + GetPlayer()->m_movementInfo = movementInfo;
  743. + GetPlayer()->m_movementInfo.SetMovementFlags(MovementFlags(movementInfo.flags));
  744. +
  745. + //calc time deltas
  746. + int32 cClientTimeDelta = 0;
  747. + if (GetPlayer()->m_anti_LastClientTime !=0){
  748. + cClientTimeDelta = movementInfo.time - GetPlayer()->m_anti_LastClientTime;
  749. + GetPlayer()->m_anti_DeltaClientTime += cClientTimeDelta;
  750. + GetPlayer()->m_anti_LastClientTime = movementInfo.time;
  751. + } else {
  752. + GetPlayer()->m_anti_LastClientTime = movementInfo.time;
  753. + }
  754. +
  755. + uint32 cServerTime=getMSTime();
  756. + uint32 cServerTimeDelta = 0;
  757. + if (GetPlayer()->m_anti_LastServerTime != 0){
  758. + cServerTimeDelta = cServerTime - GetPlayer()->m_anti_LastServerTime;
  759. + GetPlayer()->m_anti_DeltaServerTime += cServerTimeDelta;
  760. + GetPlayer()->m_anti_LastServerTime = cServerTime;
  761. + } else {
  762. + GetPlayer()->m_anti_LastServerTime = cServerTime;
  763. + }
  764. +
  765. + GetPlayer()->m_anti_JustTeleported = 1;
  766. + //end movement anticheat
  767. return;
  768. + }
  769. +
  770. + //movment anticheat
  771. + uint32 curloc = objmgr.GetNearestTaxiNode(movementInfo.x,movementInfo.y,movementInfo.z,GetPlayer()->GetMapId(),GetPlayer( )->GetTeam(), curDest);
  772. + //end movement anticheat
  773. +
  774. + //sLog.outBasic("MA-%s > | xyzo: %f,%f,%fo(%f) flags[%X] | curloc: %d | destloc: %d ",
  775. + // GetPlayer()->GetName(),movementInfo.x,movementInfo.y,movementInfo.z,movementInfo.o,
  776. + // movementInfo.flags, curloc,curDest);
  777.  
  778. TaxiNodesEntry const* curDestNode = sTaxiNodesStore.LookupEntry(curDest);
  779.  
  780. + if(curDestNode && curDestNode->map_id == GetPlayer()->GetMapId())
  781. + {
  782. + while(GetPlayer()->GetMotionMaster()->GetCurrentMovementGeneratorType()==FLIGHT_MOTION_TYPE)
  783. + GetPlayer()->GetMotionMaster()->MovementExpired(false);
  784. + }
  785. +
  786. + //movement anticheat code
  787. + GetPlayer()->SetPosition(movementInfo.x, movementInfo.y, movementInfo.z, movementInfo.o);
  788. + GetPlayer()->m_movementInfo = movementInfo;
  789. + GetPlayer()->m_movementInfo.SetMovementFlags(MovementFlags(movementInfo.flags));
  790. + //calc time deltas
  791. + int32 cClientTimeDelta = 0;
  792. + if (GetPlayer()->m_anti_LastClientTime !=0){
  793. + cClientTimeDelta = movementInfo.time - GetPlayer()->m_anti_LastClientTime;
  794. + GetPlayer()->m_anti_DeltaClientTime += cClientTimeDelta;
  795. + GetPlayer()->m_anti_LastClientTime = movementInfo.time;
  796. + } else {
  797. + GetPlayer()->m_anti_LastClientTime = movementInfo.time;
  798. + }
  799. +
  800. + uint32 cServerTime=getMSTime();
  801. + uint32 cServerTimeDelta = 0;
  802. + if (GetPlayer()->m_anti_LastServerTime != 0){
  803. + cServerTimeDelta = cServerTime - GetPlayer()->m_anti_LastServerTime;
  804. + GetPlayer()->m_anti_DeltaServerTime += cServerTimeDelta;
  805. + GetPlayer()->m_anti_LastServerTime = cServerTime;
  806. + } else {
  807. + GetPlayer()->m_anti_LastServerTime = cServerTime;
  808. + }
  809. + //<<< end movement anticheat
  810. +
  811. // far teleport case
  812. if(curDestNode && curDestNode->map_id != GetPlayer()->GetMapId())
  813. {
  814. @@ -223,6 +305,24 @@ void WorldSession::HandleMoveSplineDoneOpcode(WorldPacket& /*recv_data*/)
  815. }
  816. return;
  817. }
  818. +
  819. + //<<< movement anticheat fix - disallow unmount from taxi
  820. + if(curloc != curDest){
  821. + // current source node for next destination
  822. + uint32 sourcenode = GetPlayer()->m_taxi.GetTaxiSource();
  823. + uint16 MountId = objmgr.GetTaxiMountDisplayId(sourcenode, GetPlayer()->GetTeam());
  824. +
  825. + uint32 path, cost;
  826. + objmgr.GetTaxiPath( sourcenode, curDest, path, cost);
  827. +
  828. + if(path && MountId)
  829. + SendDoFlight( MountId, path, 1 ); // skip start fly node
  830. + else
  831. + GetPlayer()->m_taxi.ClearTaxiDestinations(); // clear problematic path and next
  832. + return;
  833. + }
  834. + ///<<< movement anticheat
  835. +
  836.  
  837. uint32 destinationnode = GetPlayer()->m_taxi.NextTaxiDestination();
  838. if ( destinationnode > 0 ) // if more destinations to go
  839. diff --git a/src/game/World.cpp b/src/game/World.cpp
  840. index d8a5ab6..e7b39c8 100644
  841. --- a/src/game/World.cpp
  842. +++ b/src/game/World.cpp
  843. @@ -76,6 +76,12 @@ float World::m_MaxVisibleDistanceInFlight = DEFAULT_VISIBILITY_DISTANCE;
  844. float World::m_VisibleUnitGreyDistance = 0;
  845. float World::m_VisibleObjectGreyDistance = 0;
  846.  
  847. +//movement anticheat
  848. +bool World::m_EnableMvAnticheat = true;
  849. +uint32 World::m_TeleportToPlaneAlarms = 50;
  850. +uint32 World::m_MistimingAlarms = 20;
  851. +uint32 World::m_MistimingDelta = 2000;
  852. +
  853. /// World constructor
  854. World::World()
  855. {
  856. @@ -530,7 +536,35 @@ void World::LoadConfigSettings(bool reload)
  857. sLog.outError("DurabilityLossChance.Block (%f) must be >=0. Using 0.0 instead.",rate_values[RATE_DURABILITY_LOSS_BLOCK]);
  858. rate_values[RATE_DURABILITY_LOSS_BLOCK] = 0.0f;
  859. }
  860. -
  861. + // movement anticheat
  862. + m_EnableMvAnticheat = sConfig.GetBoolDefault("Anticheat.Movement.Enable",true);
  863. + m_TeleportToPlaneAlarms = sConfig.GetIntDefault("Anticheat.Movement.TeleportToPlaneAlarms", 50);
  864. + if (m_TeleportToPlaneAlarms<20){
  865. + sLog.outError("Anticheat.Movement.TeleportToPlaneAlarms (%d) must be >=20. Using 20 instead.",m_TeleportToPlaneAlarms);
  866. + m_TeleportToPlaneAlarms = 20;
  867. + }
  868. + if (m_TeleportToPlaneAlarms>100){
  869. + sLog.outError("Anticheat.Movement.TeleportToPlaneAlarms (%d) must be <=100. Using 100 instead.",m_TeleportToPlaneAlarms);
  870. + m_TeleportToPlaneAlarms = 100;
  871. + }
  872. + m_MistimingDelta = sConfig.GetIntDefault("Anticheat.Movement.MistimingDelta",10000);
  873. + if (m_MistimingDelta<1000){
  874. + sLog.outError("Anticheat.Movement.m_MistimingDelta (%d) must be >=1000ms. Using 1000 instead.",m_TeleportToPlaneAlarms);
  875. + m_MistimingDelta = 1000;
  876. + }
  877. + if (m_MistimingDelta>15000){
  878. + sLog.outError("Anticheat.Movement.m_MistimingDelta (%d) must be <=15000ms. Using 15000 instead.",m_TeleportToPlaneAlarms);
  879. + m_MistimingDelta = 15000;
  880. + }
  881. + m_MistimingAlarms = sConfig.GetIntDefault("Anticheat.Movement.MistimingAlarms",20);
  882. + if (m_MistimingAlarms<10) {
  883. + sLog.outError("Anticheat.Movement.MistimingAlarms (%d) must be >=20. Using 10 instead.",m_TeleportToPlaneAlarms);
  884. + m_MistimingAlarms = 10;
  885. + }
  886. + if (m_MistimingAlarms>50){
  887. + sLog.outError("Anticheat.Movement.m_MistimingAlarms (%d) must be <=50. Using 50 instead.",m_TeleportToPlaneAlarms);
  888. + m_MistimingAlarms = 50;
  889. + }
  890. ///- Read other configuration items from the config file
  891.  
  892. m_configs[CONFIG_COMPRESSION] = sConfig.GetIntDefault("Compression", 1);
  893. diff --git a/src/game/World.h b/src/game/World.h
  894. index e4ff977..134240a 100644
  895. --- a/src/game/World.h
  896. +++ b/src/game/World.h
  897. @@ -495,7 +495,12 @@ class World
  898. static float GetMaxVisibleDistanceInFlight() { return m_MaxVisibleDistanceInFlight; }
  899. static float GetVisibleUnitGreyDistance() { return m_VisibleUnitGreyDistance; }
  900. static float GetVisibleObjectGreyDistance() { return m_VisibleObjectGreyDistance; }
  901. -
  902. + //movement anticheat
  903. + static bool GetEnableMvAnticheat() {return m_EnableMvAnticheat;}
  904. + static uint32 GetTeleportToPlaneAlarms() {return m_TeleportToPlaneAlarms;}
  905. + static uint32 GetMistimingDelta() {return m_MistimingDelta;}
  906. + static uint32 GetMistimingAlarms() {return m_MistimingAlarms;}
  907. + //<<< end movement anticheat
  908. void ProcessCliCommands();
  909. void QueueCliCommand( CliCommandHolder::Print* zprintf, char const* input ) { cliCmdQueue.add(new CliCommandHolder(input, zprintf)); }
  910.  
  911. @@ -561,7 +566,11 @@ class World
  912. static float m_MaxVisibleDistanceInFlight;
  913. static float m_VisibleUnitGreyDistance;
  914. static float m_VisibleObjectGreyDistance;
  915. -
  916. + //movement anticheat enable flag
  917. + static bool m_EnableMvAnticheat;
  918. + static uint32 m_TeleportToPlaneAlarms;
  919. + static uint32 m_MistimingDelta;
  920. + static uint32 m_MistimingAlarms;
  921. // CLI command holder to be thread safe
  922. ACE_Based::LockedQueue<CliCommandHolder*,ACE_Thread_Mutex> cliCmdQueue;
  923. SqlResultQueue *m_resultQueue;
  924. diff --git a/src/mangosd/mangosd.conf.dist.in b/src/mangosd/mangosd.conf.dist.in
  925. index ae0ac39..e658153 100644
  926. --- a/src/mangosd/mangosd.conf.dist.in
  927. +++ b/src/mangosd/mangosd.conf.dist.in
  928. @@ -1272,6 +1272,30 @@ Network.OutUBuff = 65536
  929. Network.TcpNodelay = 1
  930.  
  931. ###################################################################################################################
  932. +# MOVEMENT ANTICHEAT
  933. +#
  934. +# Anticheat.Movement.Enable
  935. +# Enable Movement Anticheat
  936. +# Default: 1 - on
  937. +# 0 - off
  938. +#
  939. +# Anticheat.Movement.TeleportToPlaneAlarms
  940. +# maximum alarms before player will be kicked (default 50, allowed 20 - 100)
  941. +#
  942. +# Anticheat.Movement.MistimingDelta
  943. +# mistiming intelval between client and serverside (default 10000 ms, allowed 1000 - 15000 ms)
  944. +#
  945. +# Anticheat.Movement.MistimingAlarms
  946. +# mistiming alarms before player will be kicked (default 20, allowed 10 - 50)
  947. +#
  948. +###################################################################################################################
  949. +
  950. +Anticheat.Movement.Enable = 1
  951. +Anticheat.Movement.TeleportToPlaneAlarms = 50
  952. +Anticheat.Movement.MistimingDelta = 10000
  953. +Anticheat.Movement.MistimingAlarms = 20
  954. +
  955. +###################################################################################################################
  956. # CONSOLE AND REMOTE ACCESS
  957. #
  958. # Console.Enable
  959.  
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement