diff options
| author | Vincent_Michael <Vincent_Michael@gmx.de> | 2013-02-15 14:23:21 +0100 |
|---|---|---|
| committer | Vincent_Michael <Vincent_Michael@gmx.de> | 2013-02-15 14:23:21 +0100 |
| commit | 6beda05e3d5cdf77a49fa1fcdfd5e64070d7a10c (patch) | |
| tree | 6106a48422550d02d501b276024c9c8306cff84e /src/server/game | |
| parent | 3c5bf554ffa58e46eb88aebd46af21335d581432 (diff) | |
| parent | 45363b8216f03f2dd4ce21cfb5ce183560374dd8 (diff) | |
Merge branch 'master' of github.com:TrinityCore/TrinityCore into 4.3.4
Conflicts:
src/server/game/Handlers/CharacterHandler.cpp
src/server/game/World/World.h
Diffstat (limited to 'src/server/game')
| -rw-r--r-- | src/server/game/DungeonFinding/LFGScripts.cpp | 14 | ||||
| -rw-r--r-- | src/server/game/Entities/Creature/Creature.cpp | 2 | ||||
| -rw-r--r-- | src/server/game/Entities/GameObject/GameObject.cpp | 2 | ||||
| -rw-r--r-- | src/server/game/Entities/Player/Player.cpp | 3 | ||||
| -rw-r--r-- | src/server/game/Handlers/CharacterHandler.cpp | 35 | ||||
| -rw-r--r-- | src/server/game/Maps/MapManager.cpp | 9 | ||||
| -rw-r--r-- | src/server/game/Scripting/ScriptMgr.cpp | 4 | ||||
| -rw-r--r-- | src/server/game/Server/WorldSession.h | 6 | ||||
| -rw-r--r-- | src/server/game/World/World.h | 2 |
9 files changed, 62 insertions, 15 deletions
diff --git a/src/server/game/DungeonFinding/LFGScripts.cpp b/src/server/game/DungeonFinding/LFGScripts.cpp index a4716de9524..22b86a094dd 100644 --- a/src/server/game/DungeonFinding/LFGScripts.cpp +++ b/src/server/game/DungeonFinding/LFGScripts.cpp @@ -95,6 +95,20 @@ void LFGPlayerScript::OnMapChanged(Player* player) if (sLFGMgr->inLfgDungeonMap(player->GetGUID(), map->GetId(), map->GetDifficulty())) { Group* group = player->GetGroup(); + // This function is also called when players log in + // if for some reason the LFG system recognises the player as being in a LFG dungeon, + // but the player was loaded without a valid group, we'll teleport to homebind to prevent + // crashes or other undefined behaviour + if (!group) + { + sLFGMgr->LeaveLfg(player->GetGUID()); + player->RemoveAurasDueToSpell(LFG_SPELL_LUCK_OF_THE_DRAW); + player->TeleportTo(player->m_homebindMapId, player->m_homebindX, player->m_homebindY, player->m_homebindZ, 0.0f); + sLog->outError(LOG_FILTER_LFG, "LFGPlayerScript::OnMapChanged, Player %s (%u) is in LFG dungeon map but does not have a valid group! " + "Teleporting to homebind.", player->GetName().c_str(), player->GetGUIDLow()); + return; + } + for (GroupReference* itr = group->GetFirstMember(); itr != NULL; itr = itr->next()) if (Player* member = itr->getSource()) player->GetSession()->SendNameQueryOpcode(member->GetGUID()); diff --git a/src/server/game/Entities/Creature/Creature.cpp b/src/server/game/Entities/Creature/Creature.cpp index fd87054b2d8..97d414b9915 100644 --- a/src/server/game/Entities/Creature/Creature.cpp +++ b/src/server/game/Entities/Creature/Creature.cpp @@ -290,7 +290,7 @@ bool Creature::InitEntry(uint32 Entry, uint32 /*team*/, const CreatureData* data } // Initialize loot duplicate count depending on raid difficulty - if (GetMap()->IsRaid() && GetMap()->GetSpawnMode() & RAID_DIFFICULTY_MASK_25MAN) + if (GetMap()->Is25ManRaid()) loot.maxDuplicates = 3; SetEntry(Entry); // normal entry always diff --git a/src/server/game/Entities/GameObject/GameObject.cpp b/src/server/game/Entities/GameObject/GameObject.cpp index 7f9e317c2d2..e333c8bb211 100644 --- a/src/server/game/Entities/GameObject/GameObject.cpp +++ b/src/server/game/Entities/GameObject/GameObject.cpp @@ -260,7 +260,7 @@ bool GameObject::Create(uint32 guidlow, uint32 name_id, Map* map, uint32 phaseMa AIM_Initialize(); // Initialize loot duplicate count depending on raid difficulty - if (map->IsRaid() && map->GetSpawnMode() & RAID_DIFFICULTY_MASK_25MAN) + if (map->Is25ManRaid()) loot.maxDuplicates = 3; return true; diff --git a/src/server/game/Entities/Player/Player.cpp b/src/server/game/Entities/Player/Player.cpp index a520ae67442..19de01ffd41 100644 --- a/src/server/game/Entities/Player/Player.cpp +++ b/src/server/game/Entities/Player/Player.cpp @@ -7662,6 +7662,9 @@ uint32 Player::GetZoneIdFromDB(uint64 guid) float posy = fields[2].GetFloat(); float posz = fields[3].GetFloat(); + if (!sMapStore.LookupEntry(map)) + return 0; + zone = sMapMgr->GetZoneId(map, posx, posy, posz); if (zone > 0) diff --git a/src/server/game/Handlers/CharacterHandler.cpp b/src/server/game/Handlers/CharacterHandler.cpp index ace5a0b68eb..5dfba797448 100644 --- a/src/server/game/Handlers/CharacterHandler.cpp +++ b/src/server/game/Handlers/CharacterHandler.cpp @@ -229,7 +229,7 @@ void WorldSession::HandleCharEnum(PreparedQueryResult result) bitBuffer.WriteBit(1); if (result) { - _allowedCharsToLogin.clear(); + _legitCharacters.clear(); charCount = uint32(result->GetRowCount()); bitBuffer.reserve(24 * charCount / 8); @@ -245,7 +245,9 @@ void WorldSession::HandleCharEnum(PreparedQueryResult result) Player::BuildEnumData(result, &dataBuffer, &bitBuffer); - _allowedCharsToLogin.insert(guidLow); + _legitCharacters.insert(guidLow); + if (!sWorld->HasCharacterNameData(guidLow)) // This can happen if characters are inserted into the database manually. Core hasn't loaded name data yet. + sWorld->AddCharacterNameData(guidLow, (*result)[1].GetString(), (*result)[4].GetUInt8(), (*result)[2].GetUInt8(), (*result)[3].GetUInt8(), (*result)[7].GetUInt8()); } while (result->NextRow()); bitBuffer.FlushBits(); @@ -800,7 +802,7 @@ void WorldSession::HandlePlayerLoginOpcode(WorldPacket& recvData) sLog->outDebug(LOG_FILTER_NETWORKIO, "Character (Guid: %u) logging in", GUID_LOPART(playerGuid)); - if (!CharCanLogin(GUID_LOPART(playerGuid))) + if (!IsLegitCharacterForAccount(GUID_LOPART(playerGuid))) { sLog->outError(LOG_FILTER_NETWORKIO, "Account (%u) can't login with that character (%u).", GetAccountId(), GUID_LOPART(playerGuid)); KickPlayer(); @@ -1473,6 +1475,15 @@ void WorldSession::HandleCharCustomize(WorldPacket& recvData) std::string newName; recvData >> guid; + if (!IsLegitCharacterForAccount(GUID_LOPART(guid))) + { + sLog->outError(LOG_FILTER_NETWORKIO, "Account %u, IP: %s tried to customise character %u, but it does not belong to their account!", + GetAccountId(), GetRemoteAddress().c_str(), GUID_LOPART(guid)); + recvData.rfinish(); + KickPlayer(); + return; + } + recvData >> newName; uint8 gender, skin, face, hairStyle, hairColor, facialHair; @@ -1704,6 +1715,16 @@ void WorldSession::HandleCharFactionOrRaceChange(WorldPacket& recvData) std::string newname; uint8 gender, skin, face, hairStyle, hairColor, facialHair, race; recvData >> guid; + + if (!IsLegitCharacterForAccount(GUID_LOPART(guid))) + { + sLog->outError(LOG_FILTER_NETWORKIO, "Account %u, IP: %s tried to factionchange character %u, but it does not belong to their account!", + GetAccountId(), GetRemoteAddress().c_str(), GUID_LOPART(guid)); + recvData.rfinish(); + KickPlayer(); + return; + } + recvData >> newname; recvData >> gender >> skin >> hairColor >> hairStyle >> facialHair >> face >> race; @@ -1711,6 +1732,14 @@ void WorldSession::HandleCharFactionOrRaceChange(WorldPacket& recvData) // get the players old (at this moment current) race CharacterNameData const* nameData = sWorld->GetCharacterNameData(lowGuid); + if (!nameData) + { + WorldPacket data(SMSG_CHAR_FACTION_CHANGE, 1); + data << uint8(CHAR_CREATE_ERROR); + SendPacket(&data); + return; + } + uint8 oldRace = nameData->m_race; uint8 playerClass = nameData->m_class; uint8 level = nameData->m_level; diff --git a/src/server/game/Maps/MapManager.cpp b/src/server/game/Maps/MapManager.cpp index b42a2f3c0ed..32824addff2 100644 --- a/src/server/game/Maps/MapManager.cpp +++ b/src/server/game/Maps/MapManager.cpp @@ -105,16 +105,17 @@ Map* MapManager::CreateBaseMap(uint32 id) { TRINITY_GUARD(ACE_Thread_Mutex, Lock); - const MapEntry* entry = sMapStore.LookupEntry(id); - if (entry && entry->Instanceable()) - { + MapEntry const* entry = sMapStore.LookupEntry(id); + ASSERT(entry); + + if (entry->Instanceable()) map = new MapInstanced(id, i_gridCleanUpDelay); - } else { map = new Map(id, i_gridCleanUpDelay, 0, REGULAR_DIFFICULTY); map->LoadRespawnTimes(); } + i_maps[id] = map; } diff --git a/src/server/game/Scripting/ScriptMgr.cpp b/src/server/game/Scripting/ScriptMgr.cpp index 5a973395c68..dd479984178 100644 --- a/src/server/game/Scripting/ScriptMgr.cpp +++ b/src/server/game/Scripting/ScriptMgr.cpp @@ -489,14 +489,14 @@ void ScriptMgr::OnGroupRateCalculation(float& rate, uint32 count, bool isRaid) } #define SCR_MAP_BGN(M, V, I, E, C, T) \ - if (V->GetEntry()->T()) \ + if (V->GetEntry() && V->GetEntry()->T()) \ { \ FOR_SCRIPTS(M, I, E) \ { \ MapEntry const* C = I->second->GetEntry(); \ if (!C) \ continue; \ - if (entry->MapID == V->GetId()) \ + if (C->MapID == V->GetId()) \ { #define SCR_MAP_END \ diff --git a/src/server/game/Server/WorldSession.h b/src/server/game/Server/WorldSession.h index 419de3a466e..70a405fd808 100644 --- a/src/server/game/Server/WorldSession.h +++ b/src/server/game/Server/WorldSession.h @@ -974,14 +974,14 @@ class WorldSession void LogUnprocessedTail(WorldPacket* packet); // EnumData helpers - bool CharCanLogin(uint32 lowGUID) + bool IsLegitCharacterForAccount(uint32 lowGUID) { - return _allowedCharsToLogin.find(lowGUID) != _allowedCharsToLogin.end(); + return _legitCharacters.find(lowGUID) != _legitCharacters.end(); } // this stores the GUIDs of the characters who can login // characters who failed on Player::BuildEnumData shouldn't login - std::set<uint32> _allowedCharsToLogin; + std::set<uint32> _legitCharacters; uint32 m_GUIDLow; // set loggined or recently logout player (while m_playerRecentlyLogout set) Player* _player; diff --git a/src/server/game/World/World.h b/src/server/game/World/World.h index 6c86057eefb..872a6c7afb3 100644 --- a/src/server/game/World/World.h +++ b/src/server/game/World/World.h @@ -753,8 +753,8 @@ class World void AddCharacterNameData(uint32 guid, std::string const& name, uint8 gender, uint8 race, uint8 playerClass, uint8 level); void UpdateCharacterNameData(uint32 guid, std::string const& name, uint8 gender = GENDER_NONE, uint8 race = RACE_NONE); void UpdateCharacterNameDataLevel(uint32 guid, uint8 level); - void DeleteCharacterNameData(uint32 guid) { _characterNameDataMap.erase(guid); } + bool HasCharacterNameData(uint32 guid) { return _characterNameDataMap.find(guid) != _characterNameDataMap.end(); } uint32 GetCleaningFlags() const { return m_CleaningFlags; } void SetCleaningFlags(uint32 flags) { m_CleaningFlags = flags; } |
