当前位置:首页>>魔兽单机>>正文
第二种防外挂的服务端系统T端代码(335WOTLK)
2013-07-05 17:39:09 作者:网络 来源: 浏览次数:0
摘要:魔兽防外挂服务端:第二中防外挂的服务端系统T端
 From c592239f5ad07950c1a88a82b46ceac4409123c9 Mon Sep 17 00:00:00 2001
From: LordPsyan <uppp@juno.com>
Date: Thu, 24 Feb 2011 21:46:53 -0500
Subject: [PATCH] 11297-AC2
 
---
 src/server/game/Entities/Player/Player.cpp         |   22 +
 src/server/game/Entities/Player/Player.h           |   20 +
 src/server/game/Entities/Unit/Unit.h               |    1 +
 src/server/game/Globals/ObjectMgr.cpp              |   22 +-
 src/server/game/Globals/ObjectMgr.h                |    2 +-
 .../Server/Protocol/Handlers/MovementHandler.cpp   |  417 +++++++++++++++++++-
 .../game/Server/Protocol/Handlers/TaxiHandler.cpp  |   99 +++++-
 src/server/game/World/World.cpp                    |   41 ++-
 src/server/game/World/World.h                      |   12 +-
 src/server/worldserver/worldserver.conf.dist       |   24 ++
 10 files changed, 639 insertions(+), 21 deletions(-)
 
diff --git a/src/server/game/Entities/Player/Player.cpp b/src/server/game/Entities/Player/Player.cpp
index 57b42e2..f84f331 100755
--- a/src/server/game/Entities/Player/Player.cpp
+++ b/src/server/game/Entities/Player/Player.cpp
@@ -536,6 +536,26 @@ Player::Player (WorldSession *session): Unit(), m_achievementMgr(this), m_reputa
     rest_type=REST_TYPE_NO;
     ////////////////////Rest System/////////////////////
 
+    // movement anticheat
+    m_anti_LastClientTime  = 0;          // last movement client time
+    m_anti_LastServerTime  = 0;          // last movement server time
+    m_anti_DeltaClientTime = 0;          // client side session time
+    m_anti_DeltaServerTime = 0;          // server side session time
+    m_anti_MistimingCount  = 0;          // mistiming count
+
+    m_anti_LastSpeedChangeTime = 0;      // last speed change time
+
+    m_anti_Last_HSpeed =  7.0f;          // horizontal speed, default RUN speed
+    m_anti_Last_VSpeed = -2.3f;          // vertical speed, default max jump height
+
+    m_anti_TeleToPlane_Count = 0;        // Teleport To Plane alarm counter
+
+    m_anti_AlarmCount = 0;               // alarm counter
+
+    m_anti_JumpCount = 0;                // Jump already began, anti air jump check
+    m_anti_JumpBaseZ = 0;                // Z coord before jump (AntiGrav)
+    // end movement anticheat
+
     m_mailsLoaded = false;
     m_mailsUpdated = false;
     unReadMails = 0;
@@ -1938,6 +1958,7 @@ bool Player::TeleportTo(uint32 mapid, float x, float y, float z, float orientati
 
     if ((GetMapId() == mapid && !m_transport) || (GetTransport() && GetMapId() == 628))
     {
+        m_anti_JumpBaseZ = 0;
         //lets reset far teleport flag if it wasn't reset during chained teleports
         SetSemaphoreTeleportFar(false);
         //setup delayed teleport flag
@@ -2096,6 +2117,7 @@ bool Player::TeleportTo(uint32 mapid, float x, float y, float z, float orientati
 
             m_teleport_dest = WorldLocation(mapid, final_x, final_y, final_z, final_o);
             SetFallInformation(0, final_z);
+            m_anti_JumpBaseZ = 0;
             // if the player is saved before worldportack (at logout for example)
             // this will be used instead of the current location in SaveToDB
 
diff --git a/src/server/game/Entities/Player/Player.h b/src/server/game/Entities/Player/Player.h
index 55e6039..f925a60 100755
--- a/src/server/game/Entities/Player/Player.h
+++ b/src/server/game/Entities/Player/Player.h
@@ -2637,6 +2637,26 @@ class Player : public Unit, public GridObject<Player>
         float m_rest_bonus;
         RestType rest_type;
         ////////////////////Rest System/////////////////////
+        // movement anticheat
+        time_t m_anti_LastClientTime;           // last movement client time
+        time_t m_anti_LastServerTime;           // last movement server time
+        time_t m_anti_DeltaClientTime;          // client side session time
+        time_t m_anti_DeltaServerTime;          // server side session time
+        uint32 m_anti_MistimingCount;           // mistiming count
+
+        time_t m_anti_LastSpeedChangeTime;      // last speed change time
+
+        float m_anti_Last_HSpeed;               // horizontal speed, default RUN speed
+        float m_anti_Last_VSpeed;               // vertical speed, default max jump height
+
+        uint32 m_anti_TeleToPlane_Count;        // Teleport To Plane alarm counter
+
+        uint64 m_anti_AlarmCount;               // alarm counter
+
+        uint16 m_anti_JumpCount;                // Jump already began, anti air jump check
+        float m_anti_JumpBaseZ;                 // Z coord before jump
+        // end movement anticheat
+
         uint32 m_resetTalentsCost;
         time_t m_resetTalentsTime;
         uint32 m_usedTalentCount;
diff --git a/src/server/game/Entities/Unit/Unit.h b/src/server/game/Entities/Unit/Unit.h
index 73d5cae..2188c4a 100755
--- a/src/server/game/Entities/Unit/Unit.h
+++ b/src/server/game/Entities/Unit/Unit.h
@@ -2085,6 +2085,7 @@ class Unit : public WorldObject
     protected:
         explicit Unit ();
 
+        GameObject * m_temp_transport;
         UnitAI *i_AI, *i_disabledAI;
 
         void _UpdateSpells(uint32 time);
diff --git a/src/server/game/Globals/ObjectMgr.cpp b/src/server/game/Globals/ObjectMgr.cpp
index 3bb103f..9383c49 100755
--- a/src/server/game/Globals/ObjectMgr.cpp
+++ b/src/server/game/Globals/ObjectMgr.cpp
@@ -6020,7 +6020,8 @@ void ObjectMgr::LoadAreaTriggerScripts()
     sLog->outString();
 }
 
-uint32 ObjectMgr::GetNearestTaxiNode(float x, float y, float z, uint32 mapid, uint32 team)
+// use searched_node for search some known node
+uint32 ObjectMgr::GetNearestTaxiNode(float x, float y, float z, uint32 mapid, uint32 team, uint32 searched_node)
 {
     bool found = false;
     float dist = 10000;
@@ -6030,7 +6031,18 @@ uint32 ObjectMgr::GetNearestTaxiNode(float x, float y, float z, uint32 mapid, ui
     {
         TaxiNodesEntry const* node = sTaxiNodesStore.LookupEntry(i);
 
-        if (!node || node->map_id != mapid || (!node->MountCreatureID[team == ALLIANCE ? 1 : 0] && node->MountCreatureID[0] != 32981)) // dk flight
+        if (!node || node->map_id != mapid) continue;
+
+        const float dist2 = pow(node->x - x, 2) + pow(node->y - y, 2) + pow(node->z - z, 2);
+
+        if (searched_node != 0 && i == searched_node)
+        {
+            id = i;
+            dist = dist2;
+            break;
+        }
+
+        if (!node->MountCreatureID[team == ALLIANCE ? 1 : 0] && node->MountCreatureID[0] != 32981) // dk flight
             continue;
 
         uint8  field   = (uint8)((i - 1) / 32);
@@ -6040,7 +6052,7 @@ uint32 ObjectMgr::GetNearestTaxiNode(float x, float y, float z, uint32 mapid, ui
         if ((sTaxiNodesMask[field] & submask) == 0)
             continue;
 
-        float dist2 = (node->x - x)*(node->x - x)+(node->y - y)*(node->y - y)+(node->z - z)*(node->z - z);
+        //float dist2 = (node->x - x)*(node->x - x)+(node->y - y)*(node->y - y)+(node->z - z)*(node->z - z);
         if (found)
         {
             if (dist2 < dist)
@@ -6056,7 +6068,9 @@ uint32 ObjectMgr::GetNearestTaxiNode(float x, float y, float z, uint32 mapid, ui
             id = i;
         }
     }
-
+    // movement anticheat fix
+    if (dist > 3600) id = 0;
+    // movement anticheat fix
     return id;
 }
 
diff --git a/src/server/game/Globals/ObjectMgr.h b/src/server/game/Globals/ObjectMgr.h
index 085a6f9..0e6ccfb 100755
--- a/src/server/game/Globals/ObjectMgr.h
+++ b/src/server/game/Globals/ObjectMgr.h
@@ -702,7 +702,7 @@ class ObjectMgr
         uint32 GetPlayerAccountIdByGUID(const uint64 &guid) const;
         uint32 GetPlayerAccountIdByPlayerName(const std::string& name) const;
 
-        uint32 GetNearestTaxiNode(float x, float y, float z, uint32 mapid, uint32 team);
+        uint32 GetNearestTaxiNode(float x, float y, float z, uint32 mapid, uint32 team, uint32 searched_node);
         void GetTaxiPath(uint32 source, uint32 destination, uint32 &path, uint32 &cost);
         uint32 GetTaxiMountDisplayId(uint32 id, uint32 team, bool allowed_alt_team = false);
 
diff --git a/src/server/game/Server/Protocol/Handlers/MovementHandler.cpp b/src/server/game/Server/Protocol/Handlers/MovementHandler.cpp
index 0c3159f..1bf182c 100755
--- a/src/server/game/Server/Protocol/Handlers/MovementHandler.cpp
+++ b/src/server/game/Server/Protocol/Handlers/MovementHandler.cpp
@@ -32,6 +32,12 @@
 #include "WaypointMovementGenerator.h"
 #include "InstanceSaveMgr.h"
 #include "ObjectMgr.h"
+#include "World.h"
+
+// Movement anticheat defines
+//#define ANTICHEAT_DEBUG
+#define ANTICHEAT_EXCEPTION_INFO
+// End Movement anticheat defines
 
 void WorldSession::HandleMoveWorldportAckOpcode(WorldPacket & /*recv_data*/)
 {
@@ -252,6 +258,12 @@ void WorldSession::HandleMovementOpcodes(WorldPacket & recv_data)
     ASSERT(mover != NULL);                                  // there must always be a mover
 
     Player *plMover = mover->GetTypeId() == TYPEID_PLAYER ? (Player*)mover : NULL;
+    Vehicle *vehMover = mover->GetVehicleKit();
+    if (vehMover)
+        if (mover->HasFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_PLAYER_CONTROLLED))
+            if (Unit *charmer = mover->GetCharmer())
+                if (charmer->GetTypeId() == TYPEID_PLAYER)
+                    plMover = (Player*)charmer;
 
     // ignore, waiting processing in WorldSession::HandleMoveWorldportAckOpcode and WorldSession::HandleMoveTeleportAck
     if (plMover && plMover->IsBeingTeleported())
@@ -300,7 +312,7 @@ void WorldSession::HandleMovementOpcodes(WorldPacket & recv_data)
         }
 
         // if we boarded a transport, add us to it
-        if (plMover && !plMover->GetTransport())
+        if (plMover && !plMover->m_transport && !plMover->m_temp_transport)
         {
             // elevators also cause the client to send MOVEMENTFLAG_ONTRANSPORT - just unmount if the guid can be found in the transport list
             for (MapManager::TransportSet::const_iterator iter = sMapMgr->m_Transports.begin(); iter != sMapMgr->m_Transports.end(); ++iter)
@@ -312,27 +324,41 @@ void WorldSession::HandleMovementOpcodes(WorldPacket & recv_data)
                     break;
                 }
             }
+            if (!plMover->m_transport)
+                if (Map *tempMap = mover->GetMap())
+                    if (GameObject *tempTransport = tempMap->GetGameObject(movementInfo.t_guid))
+                        if (tempTransport->IsTransport())
+                            plMover->m_temp_transport = tempTransport;
         }
 
-        if (!mover->GetTransport() && !mover->GetVehicle())
+        if ((!plMover && !mover->GetTransport() && !mover->GetVehicle()) || (plMover && !plMover->m_vehicle && !plMover->m_transport && !plMover->m_temp_transport)) // Not sure if the first part is needed. Just added it for verbosity.
         {
             GameObject *go = mover->GetMap()->GetGameObject(movementInfo.t_guid);
             if (!go || go->GetGoType() != GAMEOBJECT_TYPE_TRANSPORT)
                 movementInfo.flags &= ~MOVEMENTFLAG_ONTRANSPORT;
         }
     }
-    else if (plMover && plMover->GetTransport())                // if we were on a transport, leave
+    else if (plMover && (plMover->m_transport || plMover->m_temp_transport)) // if we were on a transport, leave
     {
-        plMover->m_transport->RemovePassenger(plMover);
-        plMover->m_transport = NULL;
-        movementInfo.t_pos.Relocate(0.0f, 0.0f, 0.0f, 0.0f);
+        if (plMover->m_transport)
+        {
+            plMover->m_transport->RemovePassenger(plMover);
+            plMover->m_transport = NULL;
+        }
+        plMover->m_temp_transport = NULL;        movementInfo.t_pos.Relocate(0.0f, 0.0f, 0.0f, 0.0f);
         movementInfo.t_time = 0;
         movementInfo.t_seat = -1;
     }
 
     // fall damage generation (ignore in flight case that can be triggered also at lags in moment teleportation to another map).
     if (opcode == MSG_MOVE_FALL_LAND && plMover && !plMover->isInFlight())
-        plMover->HandleFall(movementInfo);
+    {
+        // movement anticheat
+        plMover->m_anti_JumpCount = 0;
+        plMover->m_anti_JumpBaseZ = 0;
+        if (!vehMover)
+            plMover->HandleFall(movementInfo);
+    }
 
     if (plMover && ((movementInfo.flags & MOVEMENTFLAG_SWIMMING) != 0) != plMover->IsInWater())
     {
@@ -344,8 +370,343 @@ void WorldSession::HandleMovementOpcodes(WorldPacket & recv_data)
         sAnticheatMgr->StartHackDetection(plMover, movementInfo, opcode);
 
     /*----------------------*/
+    // begin anti cheat
+    bool check_passed = true;
+    #ifdef ANTICHEAT_DEBUG
+    sLog.outBasic("AC2-%s > time: %d fall-time: %d | xyzo: %f, %f, %fo(%f) flags[%X] opcode[%s] | transport (xyzo): %f, %f, %fo(%f)",
+        plMover->GetName(), movementInfo.time, movementInfo.fallTime, movementInfo.x, movementInfo.y, movementInfo.z, movementInfo.o,
+        movementInfo.flags, LookupOpcodeName(opcode), movementInfo.t_x, movementInfo.t_y, movementInfo.t_z, movementInfo.t_o);
+    sLog.outBasic("AC2-%s Transport > GUID: (low)%d - (high)%d",
+        plMover->GetName(), GUID_LOPART(movementInfo.t_guid), GUID_HIPART(movementInfo.t_guid));
+    #endif
+
+    if (plMover)
+    {
+        if (World::GetEnableMvAnticheat() && !plMover->GetCharmerOrOwnerPlayerOrPlayerItself()->isGameMaster())
+        {
+            // calc time deltas
+            int32 cClientTimeDelta = 1500;
+            if (plMover->m_anti_LastClientTime != 0)
+            {
+                cClientTimeDelta = movementInfo.time - plMover->m_anti_LastClientTime;
+                plMover->m_anti_DeltaClientTime += cClientTimeDelta;
+                plMover->m_anti_LastClientTime = movementInfo.time;
+            }
+            else
+                plMover->m_anti_LastClientTime = movementInfo.time;
+
+            const uint64 cServerTime = getMSTime();
+            uint32 cServerTimeDelta = 1500;
+            if (plMover->m_anti_LastServerTime != 0)
+            {
+                cServerTimeDelta = cServerTime - plMover->m_anti_LastServerTime;
+                plMover->m_anti_DeltaServerTime += cServerTimeDelta;
+                plMover->m_anti_LastServerTime = cServerTime;
+            }
+            else
+                plMover->m_anti_LastServerTime = cServerTime;
+
+            // resync times on client login (first 15 sec for heavy areas)
+            if (plMover->m_anti_DeltaServerTime < 15000 && plMover->m_anti_DeltaClientTime < 15000)
+                plMover->m_anti_DeltaClientTime = plMover->m_anti_DeltaServerTime;
+
+            const int32 sync_time = plMover->m_anti_DeltaClientTime - plMover->m_anti_DeltaServerTime;
+
+            #ifdef ANTICHEAT_DEBUG
+            sLog.outBasic("AC2-%s Time > cClientTimeDelta: %d, cServerTime: %d | deltaC: %d - deltaS: %d | SyncTime: %d", plMover->GetName(), cClientTimeDelta, cServerTime, plMover->m_anti_DeltaClientTime, plMover->m_anti_DeltaServerTime, sync_time);
+            #endif
+
+            // mistiming checks
+            const int32 GetMistimingDelta = abs(int32(World::GetMistimingDelta()));
+            if (sync_time > GetMistimingDelta)
+            {
+                cClientTimeDelta = cServerTimeDelta;
+                ++(plMover->m_anti_MistimingCount);
+
+                const bool bMistimingModulo = plMover->m_anti_MistimingCount % 50 == 0;
+
+                if (bMistimingModulo)
+                {
+                    #ifdef ANTICHEAT_EXCEPTION_INFO
+                    sLog->outError("AC2-%s, mistiming exception #%d, mistiming: %dms", plMover->GetName(), plMover->m_anti_MistimingCount, sync_time);
+                    #endif
+                    check_passed = false;
+                }
+                if (vehMover)
+                    vehMover->Die();
+                // Tell the player "Sure, you can fly!"
+                {
+                    WorldPacket data(SMSG_MOVE_SET_CAN_FLY, 12);
+                    data.append(plMover->GetPackGUID());
+                    data << uint32(0);
+                    SendPacket(&data);
+                }
+                // Then tell the player "Wait, no, you can't."
+                {
+                    WorldPacket data(SMSG_MOVE_UNSET_CAN_FLY, 12);
+                    data.append(plMover->GetPackGUID());
+                    data << uint32(0);
+                    SendPacket(&data);
+                }
+                //plMover->FallGround(2);
+
+                /* Disabled, not passive at all, and apparently causing crashes:
+                if (plMover->m_anti_MistimingCount > World::GetMistimingAlarms())
+                {
+                    sWorld.SendWorldText(3, strcat("Kicking cheater: ", plMover->GetName()));
+                    KickPlayer();
+                    return;
+                } */
+            }
+            // end mistiming checks
+
+            const uint32 curDest = plMover->m_taxi.GetTaxiDestination(); // check taxi flight
+            if (!curDest)
+            {
+                UnitMoveType move_type;
+
+                // calculating section
+                // current speed
+                if (movementInfo.flags & MOVEMENTFLAG_FLYING)
+                    move_type = movementInfo.flags & MOVEMENTFLAG_BACKWARD ? MOVE_FLIGHT_BACK : MOVE_FLIGHT;
+                else if (movementInfo.flags & MOVEMENTFLAG_SWIMMING)
+                    move_type = movementInfo.flags & MOVEMENTFLAG_BACKWARD ? MOVE_SWIM_BACK : MOVE_SWIM;
+                else if (movementInfo.flags & MOVEMENTFLAG_WALKING)
+                    move_type = MOVE_WALK;
+                // hmm... in first time after login player has MOVE_SWIMBACK instead MOVE_WALKBACK
+                else
+                    move_type = movementInfo.flags & MOVEMENTFLAG_BACKWARD ? MOVE_SWIM_BACK : MOVE_RUN;
+
+                const float current_speed = mover->GetSpeed(move_type);
+                // end current speed
+
+                // movement distance
+                const float delta_x = plMover->m_transport || plMover->m_temp_transport ? 0 : plMover->GetPositionX() - movementInfo.pos.GetPositionX();
+                const float delta_y = plMover->m_transport || plMover->m_temp_transport ? 0 : plMover->GetPositionY() - movementInfo.pos.GetPositionY();
+                const float delta_z = plMover->m_transport || plMover->m_temp_transport ? 0 : plMover->GetPositionZ() - movementInfo.pos.GetPositionZ();
+                const float real_delta = plMover->m_transport || plMover->m_temp_transport ? 0 : pow(delta_x, 2) + pow(delta_y, 2);
+                // end movement distance
+
+                const bool no_fly_auras = !(plMover->HasAuraType(SPELL_AURA_FLY) || plMover->HasAuraType(SPELL_AURA_MOD_INCREASE_VEHICLE_FLIGHT_SPEED)
+                    || plMover->HasAuraType(SPELL_AURA_MOD_INCREASE_MOUNTED_FLIGHT_SPEED) || plMover->HasAuraType(SPELL_AURA_MOD_INCREASE_FLIGHT_SPEED)
+                    || plMover->HasAuraType(SPELL_AURA_MOD_MOUNTED_FLIGHT_SPEED_ALWAYS) || plMover->HasAuraType(SPELL_AURA_MOD_FLIGHT_SPEED_NOT_STACK));
+                const bool no_fly_flags = (movementInfo.flags & (MOVEMENTFLAG_CAN_FLY | MOVEMENTFLAG_FLYING)) == 0;
+
+                const bool no_swim_flags = (movementInfo.flags & MOVEMENTFLAG_SWIMMING) == 0;
+                const bool no_swim_in_water = !mover->IsInWater();
+                const bool no_swim_above_water = movementInfo.pos.GetPositionZ()-7.0f >= mover->GetBaseMap()->GetWaterLevel(movementInfo.pos.GetPositionX(),movementInfo.pos.GetPositionY());
+                const bool no_swim_water = no_swim_in_water && no_swim_above_water;
+
+                const bool no_waterwalk_flags = (movementInfo.flags & MOVEMENTFLAG_WATERWALKING) == 0;
+                const bool no_waterwalk_auras = !(plMover->HasAuraType(SPELL_AURA_WATER_WALK) || plMover->HasAuraType(SPELL_AURA_GHOST));
+
+                if (cClientTimeDelta < 0)
+                    cClientTimeDelta = 0;
+                const float time_delta = cClientTimeDelta < 1500 ? float(cClientTimeDelta)/1000.0f : 1.5f; // normalize time - 1.5 second allowed for heavy loaded server
+
+                const float tg_z = (real_delta != 0 && no_fly_auras && no_swim_flags) ? (pow(delta_z, 2) / real_delta) : -99999; // movement distance tangents
+
+                if (current_speed < plMover->m_anti_Last_HSpeed && plMover->m_anti_LastSpeedChangeTime == 0)
+                    plMover->m_anti_LastSpeedChangeTime = movementInfo.time + uint32(floor(((plMover->m_anti_Last_HSpeed / current_speed) * 1500)) + 100); // 100ms above for random fluctuation
+
+                const float allowed_delta = plMover->m_transport || plMover->m_temp_transport ? 2 : // movement distance allowed delta
+                    pow(std::max(current_speed, plMover->m_anti_Last_HSpeed) * time_delta, 2)
+                    + 2                                                                             // minimum allowed delta
+                    + (tg_z > 2.2 ? pow(delta_z, 2)/2.37f : 0);                                     // mountain fall allowed delta
+
+                if (movementInfo.time > plMover->m_anti_LastSpeedChangeTime)
+                {
+                    plMover->m_anti_Last_HSpeed = current_speed;                                    // store current speed
+                    plMover->m_anti_Last_VSpeed = -2.3f;
+                    plMover->m_anti_LastSpeedChangeTime = 0;
+                }
+                // end calculating section
+
+                // AntiGravity (thanks to Meekro)
+                const float JumpHeight = plMover->m_anti_JumpBaseZ - movementInfo.pos.GetPositionZ();
+                if (no_fly_auras && no_swim_in_water && plMover->m_anti_JumpBaseZ != 0 && JumpHeight < plMover->m_anti_Last_VSpeed)
+                {
+                    #ifdef ANTICHEAT_EXCEPTION_INFO
+                    sLog->outError("AC2-%s, AntiGravity exception. JumpHeight = %f, Allowed Vertical Speed = %f",
+                        plMover->GetName(), JumpHeight, plMover->m_anti_Last_VSpeed);
+                    #endif
+                    check_passed = false;
+                    if (vehMover)
+                        vehMover->Die();
+                    // Tell the player "Sure, you can fly!"
+                    {
+                        WorldPacket data(SMSG_MOVE_SET_CAN_FLY, 12);
+                        data.append(plMover->GetPackGUID());
+                        data << uint32(0);
+                        SendPacket(&data);
+                    }
+                    // Then tell the player "Wait, no, you can't."
+                    {
+                        WorldPacket data(SMSG_MOVE_UNSET_CAN_FLY, 12);
+                        data.append(plMover->GetPackGUID());
+                        data << uint32(0);
+                        SendPacket(&data);
+                    }
+                    //plMover->FallGround(2);
+                }
+
+                // multi jump checks
+                if (opcode == MSG_MOVE_JUMP)
+                {
+                    if (no_fly_auras && no_swim_water)
+                    {
+                        if (plMover->m_anti_JumpCount >= 1)
+                        {
+                            // don't process new jump packet
+                            check_passed = false;
+                            if (vehMover)
+                                vehMover->Die();
+                            // Tell the player "Sure, you can fly!"
+                            {
+                                WorldPacket data(SMSG_MOVE_SET_CAN_FLY, 12);
+                                data.append(plMover->GetPackGUID());
+                                data << uint32(0);
+                                SendPacket(&data);
+                            }
+                            // Then tell the player "Wait, no, you can't."
+                            {
+                                WorldPacket data(SMSG_MOVE_UNSET_CAN_FLY, 12);
+                                data.append(plMover->GetPackGUID());
+                                data << uint32(0);
+                                SendPacket(&data);
+                            }
+                            //plMover->FallGround(2);
+                            plMover->m_anti_JumpCount = 0;
+                        }
+                        else
+                        {
+                            plMover->m_anti_JumpCount += 1;
+                            plMover->m_anti_JumpBaseZ = movementInfo.pos.GetPositionZ();
+                        }
+                    } else
+                        plMover->m_anti_JumpCount = 0;
+                }
+
+                // speed and teleport hack checks
+                if (real_delta > allowed_delta)
+                {
+                    #ifdef ANTICHEAT_EXCEPTION_INFO
+                    if (real_delta < 4900.0f)
+                        sLog->outError("AC2-%s, speed exception | cDelta=%f aDelta=%f | cSpeed=%f lSpeed=%f deltaTime=%f", plMover->GetName(), real_delta, allowed_delta, current_speed, plMover->m_anti_Last_HSpeed, time_delta);
+                    else
+                        sLog->outError("AC2-%s, teleport exception | cDelta=%f aDelta=%f | cSpeed=%f lSpeed=%f deltaTime=%f", plMover->GetName(), real_delta, allowed_delta, current_speed, plMover->m_anti_Last_HSpeed, time_delta);
+                    #endif
+                    check_passed = false;
+                    if (vehMover)
+                        vehMover->Die();
+                    //plMover->FallGround(2);
+                }
+
+                // mountain hack checks // 1.56f (delta_z < GetPlayer()->m_anti_Last_VSpeed))
+                if (delta_z < plMover->m_anti_Last_VSpeed && plMover->m_anti_JumpCount == 0 && tg_z > 2.37f)
+                {
+                    #ifdef ANTICHEAT_EXCEPTION_INFO
+                    sLog->outError("AC2-%s, mountain exception | tg_z=%f", plMover->GetName(), tg_z);
+                    #endif
+                    check_passed = false;
+                    if (vehMover)
+                        vehMover->Die();
+                }
 
-    /* process position-change */
+                // Fly hack checks
+                if (no_fly_auras && !no_fly_flags)
+                {
+                    #ifdef ANTICHEAT_EXCEPTION_INFO // Aura numbers: 201, 206, 207, 208, 209, 211
+                    sLog->outError("AC2-%s, flight exception. {SPELL_AURA_FLY=[%X]} {SPELL_AURA_MOD_INCREASE_MOUNTED_FLIGHT_SPEED=[%X]} {SPELL_AURA_MOD_INCREASE_FLIGHT_SPEED=[%X]} {SPELL_AURA_MOD_MOUNTED_FLIGHT_SPEED_ALWAYS=[%X]} {SPELL_AURA_MOD_FLIGHT_SPEED_NOT_STACK=[%X]} {plMover->GetVehicle()=[%X]}",
+                        plMover->GetName(),
+                        plMover->HasAuraType(SPELL_AURA_FLY), plMover->HasAuraType(SPELL_AURA_MOD_INCREASE_MOUNTED_FLIGHT_SPEED),
+                        plMover->HasAuraType(SPELL_AURA_MOD_INCREASE_FLIGHT_SPEED), plMover->HasAuraType(SPELL_AURA_MOD_MOUNTED_FLIGHT_SPEED_ALWAYS),
+                        plMover->HasAuraType(SPELL_AURA_MOD_FLIGHT_SPEED_NOT_STACK), plMover->GetVehicle());
+                    #endif
+                    check_passed = false;
+                    if (vehMover)
+                        vehMover->Die();
+                    // Tell the player "Sure, you can fly!"
+                    {
+                        WorldPacket data(SMSG_MOVE_SET_CAN_FLY, 12);
+                        data.append(plMover->GetPackGUID());
+                        data << uint32(0);
+                        SendPacket(&data);
+                    }
+                    // Then tell the player "Wait, no, you can't."
+                    {
+                        WorldPacket data(SMSG_MOVE_UNSET_CAN_FLY, 12);
+                        data.append(plMover->GetPackGUID());
+                        data << uint32(0);
+                        SendPacket(&data);
+                    }
+                    //plMover->FallGround(2);
+                }
+
+                // Waterwalk checks
+                if (no_waterwalk_auras && !no_waterwalk_flags)
+                {
+                    #ifdef ANTICHEAT_EXCEPTION_INFO
+                    sLog->outError("AC2-%s, waterwalk exception. [%X]{SPELL_AURA_WATER_WALK=[%X]}",
+                        plMover->GetName(), movementInfo.flags, plMover->HasAuraType(SPELL_AURA_WATER_WALK));
+                    #endif
+                    check_passed = false;
+                    if (vehMover)
+                        vehMover->Die();
+                    // Tell the player "Sure, you can fly!"
+                    {
+                        WorldPacket data(SMSG_MOVE_SET_CAN_FLY, 12);
+                        data.append(plMover->GetPackGUID());
+                        data << uint32(0);
+                        SendPacket(&data);
+                    }
+                    // Then tell the player "Wait, no, you can't."
+                    {
+                        WorldPacket data(SMSG_MOVE_UNSET_CAN_FLY, 12);
+                        data.append(plMover->GetPackGUID());
+                        data << uint32(0);
+                        SendPacket(&data);
+                    }
+                    //plMover->FallGround(2);
+                }
+
+                // Teleport To Plane checks
+                if (no_swim_in_water && movementInfo.pos.GetPositionZ() < 0.0001f && movementInfo.pos.GetPositionZ() > -0.0001f)
+                {
+                    if (const Map *map = plMover->GetMap())
+                    {
+                        float plane_z = map->GetHeight(movementInfo.pos.GetPositionX(), movementInfo.pos.GetPositionY(), MAX_HEIGHT) - movementInfo.pos.GetPositionZ();
+                        plane_z = (plane_z < -500.0f) ? 0.0f : plane_z; // check holes in height map
+                        if (plane_z > 0.1f || plane_z < -0.1f)
+                        {
+                            #ifdef ANTICHEAT_DEBUG
+                            sLog->outDebug("AC2-%s, teleport to plane exception. plane_z: %f", plMover->GetName(), plane_z);
+                            #endif
+                            #ifdef ANTICHEAT_EXCEPTION_INFO
+                            if (plMover->m_anti_TeleToPlane_Count > World::GetTeleportToPlaneAlarms())
+                            {
+                                sLog->outError("AC2-%s, teleport to plane exception. Exception count: %d", plMover->GetName(), plMover->m_anti_TeleToPlane_Count);
+                                /* Disabled, not passive at all, and apparently causing crashes:
+                                sWorld.SendWorldText(3, strcat("Kicking cheater: ", plMover->GetName()));
+                                KickPlayer();
+                                return; */
+                            }
+                            #endif
+                            ++(plMover->m_anti_TeleToPlane_Count);
+                            check_passed = false;
+                            if (vehMover)
+                                vehMover->Die();
+                        }
+                    }
+                }
+                else
+                    plMover->m_anti_TeleToPlane_Count = 0;
+            }
+        }
+    }
+     /* process position-change */
+    if (check_passed)
+    {
     WorldPacket data(opcode, recv_data.size());
     movementInfo.time = getMSTime();
     movementInfo.guid = mover->GetGUID();
@@ -363,7 +724,7 @@ void WorldSession::HandleMovementOpcodes(WorldPacket & recv_data)
 
     mover->SetPosition(movementInfo.pos);
 
-    if (plMover)                                            // nothing is charmed, or player charmed
+    if (plMover && !vehMover)                               // nothing is charmed, or player charmed
     {
         plMover->UpdateFallInformationIfNeed(movementInfo, opcode);
 
@@ -393,7 +754,31 @@ void WorldSession::HandleMovementOpcodes(WorldPacket & recv_data)
                 plMover->RepopAtGraveyard();
             }
         }
+        // movement anticheat
+        if (plMover->m_anti_AlarmCount > 0)
+        {
+            sLog->outError("AC2-%s produce %d anticheat alarms", plMover->GetName(), plMover->m_anti_AlarmCount);
+            plMover->m_anti_AlarmCount = 0;
+        }
+        // end movement anticheat
+ }
+    }
+    else if (plMover)
+    {
+        if (plMover->m_transport)
+        {
+            plMover->m_transport->RemovePassenger(plMover);
+            plMover->m_transport = NULL;
+        }
+        plMover->m_temp_transport = NULL;
+        ++(plMover->m_anti_AlarmCount);
+        WorldPacket data;
+        plMover->SetUnitMovementFlags(0);
+        plMover->SendTeleportAckPacket();
+        plMover->BuildHeartBeatMsg(&data);
+        plMover->SendMessageToSet(&data, true);
     }
+
 }
 
 void WorldSession::HandleForceSpeedChangeAck(WorldPacket &recv_data)
@@ -736,6 +1121,20 @@ void WorldSession::HandleMoveKnockBackAck(WorldPacket & recv_data)
 
     MovementInfo movementInfo;
     ReadMovementInfo(recv_data, &movementInfo);
+
+    // Save movement flags
+    _player->SetUnitMovementFlags(movementInfo.flags);
+    #ifdef ANTICHEAT_DEBUG
+    sLog->outBasic("%s CMSG_MOVE_KNOCK_BACK_ACK: time: %d, fall time: %d | xyzo: %f,%f,%fo(%f) flags[%X]", GetPlayer()->GetName(), movementInfo.time, movementInfo.fallTime, movementInfo.x, movementInfo.y, movementInfo.z, movementInfo.o, movementInfo.flags);
+    sLog->outBasic("%s CMSG_MOVE_KNOCK_BACK_ACK additional: Vspeed: %f, Hspeed: %f", GetPlayer()->GetName(), movementInfo.j_unk, movementInfo.j_xyspeed);
+    #endif
+
+    _player->m_movementInfo = movementInfo;
+    _player->m_anti_Last_HSpeed = movementInfo.j_xyspeed;
+    _player->m_anti_Last_VSpeed = movementInfo.j_zspeed < 3.2f ? movementInfo.j_zspeed - 1.0f : 3.2f;
+
+    const 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);
+    _player->m_anti_LastSpeedChangeTime = movementInfo.time + dt + 1000;
 }
 
 void WorldSession::HandleMoveHoverAck(WorldPacket& recv_data)
diff --git a/src/server/game/Server/Protocol/Handlers/TaxiHandler.cpp b/src/server/game/Server/Protocol/Handlers/TaxiHandler.cpp
index a7bc651..0414a4f 100755
--- a/src/server/game/Server/Protocol/Handlers/TaxiHandler.cpp
+++ b/src/server/game/Server/Protocol/Handlers/TaxiHandler.cpp
@@ -49,7 +49,7 @@ void WorldSession::SendTaxiStatus(uint64 guid)
         return;
     }
 
-    uint32 curloc = sObjectMgr->GetNearestTaxiNode(unit->GetPositionX(),unit->GetPositionY(),unit->GetPositionZ(),unit->GetMapId(),GetPlayer()->GetTeam());
+    uint32 curloc = sObjectMgr->GetNearestTaxiNode(unit->GetPositionX(),unit->GetPositionY(),unit->GetPositionZ(),unit->GetMapId(),GetPlayer()->GetTeam(),0);
 
     // not found nearest
     if (curloc == 0)
@@ -94,7 +94,7 @@ void WorldSession::HandleTaxiQueryAvailableNodes(WorldPacket & recv_data)
 void WorldSession::SendTaxiMenu(Creature* unit)
 {
     // find current node
-    uint32 curloc = sObjectMgr->GetNearestTaxiNode(unit->GetPositionX(),unit->GetPositionY(),unit->GetPositionZ(),unit->GetMapId(),GetPlayer()->GetTeam());
+    uint32 curloc = sObjectMgr->GetNearestTaxiNode(unit->GetPositionX(),unit->GetPositionY(),unit->GetPositionZ(),unit->GetMapId(),GetPlayer()->GetTeam(),0);
 
     if (curloc == 0)
         return;
@@ -134,7 +134,7 @@ void WorldSession::SendDoFlight(uint32 mountDisplayId, uint32 path, uint32 pathN
 bool WorldSession::SendLearnNewTaxiNode(Creature* unit)
 {
     // find current node
-    uint32 curloc = sObjectMgr->GetNearestTaxiNode(unit->GetPositionX(),unit->GetPositionY(),unit->GetPositionZ(),unit->GetMapId(),GetPlayer()->GetTeam());
+    uint32 curloc = sObjectMgr->GetNearestTaxiNode(unit->GetPositionX(),unit->GetPositionY(),unit->GetPositionZ(),unit->GetMapId(),GetPlayer()->GetTeam(),0);
 
     if (curloc == 0)
         return true;                                        // `true` send to avoid WorldSession::SendTaxiMenu call with one more curlock seartch with same false result.
@@ -203,6 +203,13 @@ void WorldSession::HandleMoveSplineDoneOpcode(WorldPacket& recv_data)
     uint64 guid; // used only for proper packet read
     recv_data.readPackGUID(guid);
 
+    // movement anticheat code
+    const Unit *mover = _player->m_mover;
+    const Player *plMover = mover->GetTypeId() == TYPEID_PLAYER ? (Player*)mover : NULL;
+    if (!plMover)
+        return;
+    // end movement anticheat
+
     MovementInfo movementInfo;                              // used only for proper packet read
     ReadMovementInfo(recv_data, &movementInfo);
 
@@ -215,10 +222,75 @@ void WorldSession::HandleMoveSplineDoneOpcode(WorldPacket& recv_data)
 
     uint32 curDest = GetPlayer()->m_taxi.GetTaxiDestination();
     if (!curDest)
-        return;
+    {
+        // movement anticheat code
+        GetPlayer()->SetPosition(movementInfo.pos.GetPositionX(), movementInfo.pos.GetPositionY(), movementInfo.pos.GetPositionZ(), movementInfo.pos.GetOrientation());
+        GetPlayer()->m_movementInfo = movementInfo;
+        GetPlayer()->SetUnitMovementFlags(movementInfo.flags);
+
+        // calc time deltas
+        int32 cClientTimeDelta = 0;
+        if (GetPlayer()->m_anti_LastClientTime != 0)
+        {
+            cClientTimeDelta = movementInfo.time - GetPlayer()->m_anti_LastClientTime;
+            GetPlayer()->m_anti_DeltaClientTime += cClientTimeDelta;
+            GetPlayer()->m_anti_LastClientTime = movementInfo.time;
+        }
+        else
+            GetPlayer()->m_anti_LastClientTime = movementInfo.time;
 
-    TaxiNodesEntry const* curDestNode = sTaxiNodesStore.LookupEntry(curDest);
+        const uint64 cServerTime = getMSTime();
+        uint32 cServerTimeDelta = 0;
+        if (GetPlayer()->m_anti_LastServerTime != 0)
+        {
+            cServerTimeDelta = cServerTime - GetPlayer()->m_anti_LastServerTime;
+            GetPlayer()->m_anti_DeltaServerTime += cServerTimeDelta;
+            GetPlayer()->m_anti_LastServerTime = cServerTime;
+        }
+        else
+            GetPlayer()->m_anti_LastServerTime = cServerTime;
+        // end movement anticheat
+        return;
+ }
+    // movment anticheat
+    const uint32 curloc =
+    sObjectMgr->GetNearestTaxiNode(movementInfo.pos.GetPositionX(),movementInfo.pos.GetPositionY(),movementInfo.pos.GetPositionZ(),GetPlayer()->GetMapId(),GetPlayer()->GetTeam(), curDest);
+    // end movement anticheat
+
+    // sLog.outBasic("AC2-%s > | xyzo: %f,%f,%fo(%f) flags[%X] | curloc: %d | destloc: %d ",
+    // GetPlayer()->GetName(), movementInfo.x, movementInfo.y, movementInfo.z, movementInfo.o,
+    // movementInfo.flags, curloc, curDest);
+     TaxiNodesEntry const* curDestNode = sTaxiNodesStore.LookupEntry(curDest);
+    if (curDestNode && curDestNode->map_id == GetPlayer()->GetMapId())
+        while (GetPlayer()->GetMotionMaster()->GetCurrentMovementGeneratorType() == FLIGHT_MOTION_TYPE)
+            GetPlayer()->GetMotionMaster()->MovementExpired(false);
+
+    // movement anticheat code
+    GetPlayer()->SetPosition(movementInfo.pos.GetPositionX(), movementInfo.pos.GetPositionY(), movementInfo.pos.GetPositionZ(), movementInfo.pos.GetOrientation());
+    GetPlayer()->m_movementInfo = movementInfo;
+    GetPlayer()->SetUnitMovementFlags(movementInfo.flags);
+    // calc time deltas
+    int32 cClientTimeDelta = 0;
+    if (GetPlayer()->m_anti_LastClientTime != 0)
+    {
+        cClientTimeDelta = movementInfo.time - GetPlayer()->m_anti_LastClientTime;
+        GetPlayer()->m_anti_DeltaClientTime += cClientTimeDelta;
+        GetPlayer()->m_anti_LastClientTime = movementInfo.time;
+    }
+    else
+        GetPlayer()->m_anti_LastClientTime = movementInfo.time;
 
+    const uint64 cServerTime = getMSTime();
+    uint32 cServerTimeDelta = 0;
+    if (GetPlayer()->m_anti_LastServerTime != 0)
+    {
+        cServerTimeDelta = cServerTime - GetPlayer()->m_anti_LastServerTime;
+        GetPlayer()->m_anti_DeltaServerTime += cServerTimeDelta;
+        GetPlayer()->m_anti_LastServerTime = cServerTime;
+    }
+    else
+        GetPlayer()->m_anti_LastServerTime = cServerTime;
+    // end movement anticheat
     // far teleport case
     if (curDestNode && curDestNode->map_id != GetPlayer()->GetMapId())
     {
@@ -235,6 +307,23 @@ void WorldSession::HandleMoveSplineDoneOpcode(WorldPacket& recv_data)
         }
         return;
     }
+    // movement anticheat fix - disallow unmount from taxi
+    if (curloc != curDest)
+    {
+         // current source node for next destination
+        uint32 sourcenode = GetPlayer()->m_taxi.GetTaxiSource();
+        uint16 MountId = sObjectMgr->GetTaxiMountDisplayId(sourcenode, GetPlayer()->GetTeam());
+
+        uint32 path, cost;
+        sObjectMgr->GetTaxiPath(sourcenode, curDest, path, cost);
+
+        if (path && MountId)
+            SendDoFlight(MountId, path, 1);                 // skip start fly node
+        else
+            GetPlayer()->m_taxi.ClearTaxiDestinations();    // clear problematic path and next
+        return;
+    }
+    // end movement anticheat
 
     uint32 destinationnode = GetPlayer()->m_taxi.NextTaxiDestination();
     if (destinationnode > 0)                              // if more destinations to go
diff --git a/src/server/game/World/World.cpp b/src/server/game/World/World.cpp
index aa69df8..0c59a53 100755
--- a/src/server/game/World/World.cpp
+++ b/src/server/game/World/World.cpp
@@ -85,7 +85,11 @@ float World::m_MaxVisibleDistanceInBGArenas   = DEFAULT_VISIBILITY_BGARENAS;
 int32 World::m_visibility_notify_periodOnContinents = DEFAULT_VISIBILITY_NOTIFY_PERIOD;
 int32 World::m_visibility_notify_periodInInstances  = DEFAULT_VISIBILITY_NOTIFY_PERIOD;
 int32 World::m_visibility_notify_periodInBGArenas   = DEFAULT_VISIBILITY_NOTIFY_PERIOD;
-
+// movement anticheat
+bool World::m_EnableMvAnticheat = true;
+uint32 World::m_TeleportToPlaneAlarms = 50;
+uint32 World::m_MistimingAlarms = 200;
+uint32 World::m_MistimingDelta = 15000;
 /// World constructor
 World::World()
 {
@@ -560,6 +564,41 @@ void World::LoadConfigSettings(bool reload)
         sLog->outError("DurabilityLossChance.Block (%f) must be >=0. Using 0.0 instead.",rate_values[RATE_DURABILITY_LOSS_BLOCK]);
         rate_values[RATE_DURABILITY_LOSS_BLOCK] = 0.0f;
     }
+    // movement anticheat
+    m_EnableMvAnticheat = sConfig->GetBoolDefault("Anticheat.Movement.Enable", true);
+    m_TeleportToPlaneAlarms = sConfig->GetIntDefault("Anticheat.Movement.TeleportToPlaneAlarms", 50);
+    if (m_TeleportToPlaneAlarms < 20)
+    {
+        sLog->outError("Anticheat.Movement.TeleportToPlaneAlarms (%d) must be >= 20. Using 20 instead.", m_TeleportToPlaneAlarms);
+        m_TeleportToPlaneAlarms = 20;
+    }
+    if (m_TeleportToPlaneAlarms > 100)
+    {
+        sLog->outError("Anticheat.Movement.TeleportToPlaneAlarms (%d) must be <= 100. Using 100 instead.", m_TeleportToPlaneAlarms);
+        m_TeleportToPlaneAlarms = 100;
+    }
+    m_MistimingDelta = sConfig->GetIntDefault("Anticheat.Movement.MistimingDelta", 15000);
+    if (m_MistimingDelta < 5000)
+    {
+        sLog->outError("Anticheat.Movement.m_MistimingDelta (%d) must be >= 5000ms. Using 5000ms instead.", m_MistimingDelta);
+        m_MistimingDelta = 5000;
+    }
+    if (m_MistimingDelta > 50000)
+    {
+        sLog->outError("Anticheat.Movement.m_MistimingDelta (%d) must be <= 50000ms. Using 50000ms instead.", m_MistimingDelta);
+        m_MistimingDelta = 50000;
+    }
+    m_MistimingAlarms = sConfig->GetIntDefault("Anticheat.Movement.MistimingAlarms", 200);
+    if (m_MistimingAlarms < 100)
+    {
+        sLog->outError("Anticheat.Movement.MistimingAlarms (%d) must be >= 100. Using 100 instead.", m_MistimingAlarms);
+        m_MistimingAlarms = 100;
+    }
+    if (m_MistimingAlarms > 500)
+    {
+        sLog->outError("Anticheat.Movement.m_MistimingAlarms (%d) must be <= 500. Using 500 instead.", m_MistimingAlarms);
+        m_MistimingAlarms = 500;
+    }
     ///- Read other configuration items from the config file
 
     m_bool_configs[CONFIG_DURABILITY_LOSS_IN_PVP] = sConfig->GetBoolDefault("DurabilityLoss.InPvP", false);
diff --git a/src/server/game/World/World.h b/src/server/game/World/World.h
index eaf1e46..643b9bf 100755
--- a/src/server/game/World/World.h
+++ b/src/server/game/World/World.h
@@ -729,6 +729,12 @@ class World
         static int32 GetVisibilityNotifyPeriodOnContinents(){ return m_visibility_notify_periodOnContinents; }
         static int32 GetVisibilityNotifyPeriodInInstances() { return m_visibility_notify_periodInInstances;  }
         static int32 GetVisibilityNotifyPeriodInBGArenas()  { return m_visibility_notify_periodInBGArenas;   }
+        // movement anticheat
+        static bool GetEnableMvAnticheat()       { return m_EnableMvAnticheat;     }
+        static uint32 GetTeleportToPlaneAlarms() { return m_TeleportToPlaneAlarms; }
+        static uint32 GetMistimingDelta()        { return m_MistimingDelta;        }
+        static uint32 GetMistimingAlarms()       { return m_MistimingAlarms;       }
+        // end movement anticheat
 
         void ProcessCliCommands();
         void QueueCliCommand(CliCommandHolder* commandHolder) { cliCmdQueue.add(commandHolder); }
@@ -837,7 +843,11 @@ class World
         static int32 m_visibility_notify_periodOnContinents;
         static int32 m_visibility_notify_periodInInstances;
         static int32 m_visibility_notify_periodInBGArenas;
-
+        // movement anticheat enable flag
+        static bool m_EnableMvAnticheat;
+        static uint32 m_TeleportToPlaneAlarms;
+        static uint32 m_MistimingDelta;
+        static uint32 m_MistimingAlarms;
         // CLI command holder to be thread safe
         ACE_Based::LockedQueue<CliCommandHolder*,ACE_Thread_Mutex> cliCmdQueue;
 
diff --git a/src/server/worldserver/worldserver.conf.dist b/src/server/worldserver/worldserver.conf.dist
index 59f1968..6c1a120 100644
--- a/src/server/worldserver/worldserver.conf.dist
+++ b/src/server/worldserver/worldserver.conf.dist
@@ -2486,6 +2486,30 @@ Arena.ArenaStartMatchmakerRating = 1500
 #
 ###################################################################################################
 
+ ###############################################################################
+# MOVEMENT ANTICHEAT
+#
+#    Anticheat.Movement.Enable
+#        Enable Movement Anticheat
+#        Default: 1 - on
+#                 0 - off
+#
+#    Anticheat.Movement.TeleportToPlaneAlarms
+#        maximum alarms before logging mode will be switched from debug to error (default 50, allowed 20 - 100)
+#
+#    Anticheat.Movement.MistimingDelta
+#        mistiming intelval between client and serverside (default 15000 ms, allowed 5000 - 50000 ms)
+#
+#    Anticheat.Movement.MistimingAlarms
+#        mistiming alarms before logging mode will be switched from debug to error (default 200, allowed 100 - 500)
+#
+###############################################################################
+
+Anticheat.Movement.Enable = 1
+Anticheat.Movement.TeleportToPlaneAlarms = 50
+Anticheat.Movement.MistimingDelta = 15000
+Anticheat.Movement.MistimingAlarms = 200
+
 ###################################################################################################
 # NETWORK CONFIG
 #
-- 
1.7.2.3


相关报道:

[关闭] [返回顶部]


  返回首页 | 最新资讯 | 资源下载 | 魔兽图片 | 单机文档 | 技术攻略 | 玩家视频
备案号:蜀ICP备2024062380号-1
免责声明:本网站为热爱怀旧WOW的玩家们建立的魔兽世界资料网站,仅供交流和学习使用,非盈利和商用.如有侵权之处,请联系我们,我们会在24小时内确认删除侵权内容,谢谢合作。
Copyright © 2024 - 2024 WOWAII.COM Corporation, All Rights Reserved

机器人国度