diff --git a/src/game/Opcodes.h b/src/game/Opcodes.h index 6ab1eb322..323e639da 100644 --- a/src/game/Opcodes.h +++ b/src/game/Opcodes.h @@ -1327,15 +1327,15 @@ enum Opcodes SMSG_CAMERA_SHAKE = 0x50A, // uint32 SpellEffectCameraShakes.dbc index, uint32 SMSG_UNKNOWN_1291 = 0x50B, // some item update packet? UMSG_UNKNOWN_1292 = 0x50C, // not found - SMSG_UNKNOWN_1293 = 0x50D, // + SMSG_REDIRECT_CLIENT = 0x50D, // uint32 ip, uint16 port, uint32 unk, uint8[20] hash CMSG_UNKNOWN_1294 = 0x50E, // something with networking SMSG_UNKNOWN_1295 = 0x50F, // CMSG_UNKNOWN_1296 = 0x510, // something with networking SMSG_UNKNOWN_1297 = 0x511, // CMSG_UNKNOWN_1298 = 0x512, // something with networking UMSG_UNKNOWN_1299 = 0x513, // not found - SMSG_UNKNOWN_1300 = 0x514, // SMSG, multi combatlog - SMSG_UNKNOWN_1301 = 0x515, // event EVENT_LFG_OPEN_FROM_GOSSIP (opens dungeon finder, probably for outdoor bosses) + SMSG_COMBAT_LOG_MULTIPLE = 0x514, // SMSG, multi combatlog + SMSG_LFG_OPEN_FROM_GOSSIP = 0x515, // event EVENT_LFG_OPEN_FROM_GOSSIP (opens dungeon finder, probably for outdoor bosses) SMSG_UNKNOWN_1302 = 0x516, // something with player movement (move event 58?) CMSG_UNKNOWN_1303 = 0x517, // something with player movement (move event 58?) SMSG_UNKNOWN_1304 = 0x518, // something with player movement (move event 58?), speed packet diff --git a/src/game/WorldSession.cpp b/src/game/WorldSession.cpp index 228102b14..8d59fc836 100644 --- a/src/game/WorldSession.cpp +++ b/src/game/WorldSession.cpp @@ -35,6 +35,8 @@ #include "BattleGroundMgr.h" #include "MapManager.h" #include "SocialMgr.h" +#include "Auth/AuthCrypt.h" +#include "Auth/HMACSHA1.h" #include "zlib/zlib.h" /// WorldSession constructor @@ -856,3 +858,22 @@ void WorldSession::SetPlayer( Player *plr ) if(_player) m_GUIDLow = _player->GetGUIDLow(); } + +void WorldSession::SendRedirectClient(std::string& ip, uint16 port) +{ + uint32 ip2 = ACE_OS::inet_addr(ip.c_str()); + WorldPacket pkt(SMSG_REDIRECT_CLIENT, 4 + 2 + 4 + 20); + + pkt << uint32(ip2); // inet_addr(ipstr) + pkt << uint16(port); // port + + pkt << uint32(GetLatency()); // latency-related? + + HMACSHA1 sha1(20, m_Socket->GetSessionKey().AsByteArray()); + sha1.UpdateData((uint8*)&ip2, 4); + sha1.UpdateData((uint8*)&port, 2); + sha1.Finalize(); + pkt.append(sha1.GetDigest(), 20); // hmacsha1(ip+port) w/ sessionkey as seed + + SendPacket(&pkt); +} diff --git a/src/game/WorldSession.h b/src/game/WorldSession.h index 5551eed2f..e15b35f7c 100644 --- a/src/game/WorldSession.h +++ b/src/game/WorldSession.h @@ -158,6 +158,7 @@ class MANGOS_DLL_SPEC WorldSession void SendAreaTriggerMessage(const char* Text, ...) ATTR_PRINTF(2,3); void SendSetPhaseShift(uint32 phaseShift); void SendQueryTimeResponse(); + void SendRedirectClient(std::string& ip, uint16 port); AccountTypes GetSecurity() const { return _security; } uint32 GetAccountId() const { return _accountId; } diff --git a/src/game/WorldSocket.cpp b/src/game/WorldSocket.cpp index 2638595a8..f9840a539 100644 --- a/src/game/WorldSocket.cpp +++ b/src/game/WorldSocket.cpp @@ -37,7 +37,6 @@ #include "ByteBuffer.h" #include "Opcodes.h" #include "Database/DatabaseEnv.h" -#include "Auth/BigNumber.h" #include "Auth/Sha1.h" #include "WorldSession.h" #include "WorldSocketMgr.h" @@ -826,7 +825,8 @@ int WorldSocket::HandleAuthSession (WorldPacket& recvPacket) g.SetDword (7); v.SetHexStr(fields[5].GetString()); - s.SetHexStr (fields[6].GetString ()); + s.SetHexStr (fields[6].GetString()); + m_s = s; const char* sStr = s.AsHexStr (); //Must be freed by OPENSSL_free() const char* vStr = v.AsHexStr (); //Must be freed by OPENSSL_free() diff --git a/src/game/WorldSocket.h b/src/game/WorldSocket.h index 584982cf3..41b09de3a 100644 --- a/src/game/WorldSocket.h +++ b/src/game/WorldSocket.h @@ -42,6 +42,7 @@ #include "Common.h" #include "Auth/AuthCrypt.h" +#include "Auth/BigNumber.h" class ACE_Message_Block; class WorldPacket; @@ -121,6 +122,9 @@ class WorldSocket : protected WorldHandler /// Remove reference to this object. long RemoveReference (void); + /// Return the session key + BigNumber& GetSessionKey() { return m_s; } + protected: /// things called by ACE framework. WorldSocket (void); @@ -212,6 +216,8 @@ class WorldSocket : protected WorldHandler bool m_OutActive; uint32 m_Seed; + + BigNumber m_s; }; #endif /* _WORLDSOCKET_H */ diff --git a/src/game/WorldSocketMgr.cpp b/src/game/WorldSocketMgr.cpp index 24a54a752..232d7d88f 100644 --- a/src/game/WorldSocketMgr.cpp +++ b/src/game/WorldSocketMgr.cpp @@ -273,12 +273,15 @@ WorldSocketMgr::StartReactiveIO (ACE_UINT16 port, const char* address) } int -WorldSocketMgr::StartNetwork (ACE_UINT16 port, const char* address) +WorldSocketMgr::StartNetwork (ACE_UINT16 port, std::string& address) { + m_addr = address; + m_port = port; + if (!sLog.IsOutDebug ()) ACE_Log_Msg::instance ()->priority_mask (LM_ERROR, ACE_Log_Msg::PROCESS); - if (StartReactiveIO (port, address) == -1) + if (StartReactiveIO (port, address.c_str()) == -1) return -1; return 0; diff --git a/src/game/WorldSocketMgr.h b/src/game/WorldSocketMgr.h index 98c97f5b0..c28e3897d 100644 --- a/src/game/WorldSocketMgr.h +++ b/src/game/WorldSocketMgr.h @@ -29,6 +29,8 @@ #include #include +#include + class WorldSocket; class ReactorRunnable; class ACE_Event_Handler; @@ -41,7 +43,7 @@ public: friend class ACE_Singleton; /// Start network, listen at address:port . - int StartNetwork (ACE_UINT16 port, const char* address); + int StartNetwork (ACE_UINT16 port, std::string& address); /// Stops all network threads, It will wait for all running threads . void StopNetwork (); @@ -49,6 +51,9 @@ public: /// Wait untill all network threads have "joined" . void Wait (); + std::string& GetBindAddress() { return m_addr; } + ACE_UINT16 GetBindPort() { return m_port; } + /// Make this class singleton . static WorldSocketMgr* Instance (); @@ -68,6 +73,9 @@ private: int m_SockOutUBuff; bool m_UseNoDelay; + std::string m_addr; + ACE_UINT16 m_port; + ACE_Event_Handler* m_Acceptor; }; diff --git a/src/mangosd/Master.cpp b/src/mangosd/Master.cpp index 4bb67e2d5..99f5836e7 100644 --- a/src/mangosd/Master.cpp +++ b/src/mangosd/Master.cpp @@ -312,7 +312,7 @@ int Master::Run() uint16 wsport = sWorld.getConfig (CONFIG_UINT32_PORT_WORLD); std::string bind_ip = sConfig.GetStringDefault ("BindIP", "0.0.0.0"); - if (sWorldSocketMgr->StartNetwork (wsport, bind_ip.c_str ()) == -1) + if (sWorldSocketMgr->StartNetwork (wsport, bind_ip) == -1) { sLog.outError ("Failed to start network"); World::StopNow(ERROR_EXIT_CODE); diff --git a/src/shared/Common.h b/src/shared/Common.h index 91032c807..d7d21430e 100644 --- a/src/shared/Common.h +++ b/src/shared/Common.h @@ -94,6 +94,7 @@ #include #include #include +#include #if PLATFORM == PLATFORM_WINDOWS # define FD_SETSIZE 4096 diff --git a/src/shared/Util.cpp b/src/shared/Util.cpp index 50a7bc14e..577fe62df 100644 --- a/src/shared/Util.cpp +++ b/src/shared/Util.cpp @@ -206,7 +206,7 @@ bool IsIPAddress(char const* ipaddress) // Let the big boys do it. // Drawback: all valid ip address formats are recognized e.g.: 12.23,121234,0xABCD) - return inet_addr(ipaddress) != INADDR_NONE; + return ACE_OS::inet_addr(ipaddress) != INADDR_NONE; } /// create PID file diff --git a/src/shared/revision_nr.h b/src/shared/revision_nr.h index 22d46e5de..5f0cb64b8 100644 --- a/src/shared/revision_nr.h +++ b/src/shared/revision_nr.h @@ -1,4 +1,4 @@ #ifndef __REVISION_NR_H__ #define __REVISION_NR_H__ - #define REVISION_NR "9749" + #define REVISION_NR "9750" #endif // __REVISION_NR_H__