mirror of
https://github.com/mangosfour/server.git
synced 2025-12-16 04:37:00 +00:00
[10284] Fixed memory leaks at guild unload/disband
Signed-off-by: VladimirMangos <vladimir@getmangos.com> Also drop redundent m_PurchasedTabs field.
This commit is contained in:
parent
c6b52bf285
commit
3ca05f9d4d
3 changed files with 62 additions and 36 deletions
|
|
@ -45,7 +45,6 @@ Guild::Guild()
|
||||||
m_CreatedDate = time(0);
|
m_CreatedDate = time(0);
|
||||||
|
|
||||||
m_GuildBankMoney = 0;
|
m_GuildBankMoney = 0;
|
||||||
m_PurchasedTabs = 0;
|
|
||||||
|
|
||||||
m_GuildEventLogNextGuid = 0;
|
m_GuildEventLogNextGuid = 0;
|
||||||
m_GuildBankEventLogNextGuid_Money = 0;
|
m_GuildBankEventLogNextGuid_Money = 0;
|
||||||
|
|
@ -55,7 +54,7 @@ Guild::Guild()
|
||||||
|
|
||||||
Guild::~Guild()
|
Guild::~Guild()
|
||||||
{
|
{
|
||||||
|
DeleteGuildBankItems();
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Guild::Create(Player* leader, std::string gname)
|
bool Guild::Create(Player* leader, std::string gname)
|
||||||
|
|
@ -72,7 +71,6 @@ bool Guild::Create(Player* leader, std::string gname)
|
||||||
GINFO = "";
|
GINFO = "";
|
||||||
MOTD = "No message set.";
|
MOTD = "No message set.";
|
||||||
m_GuildBankMoney = 0;
|
m_GuildBankMoney = 0;
|
||||||
m_PurchasedTabs = 0;
|
|
||||||
m_Id = sObjectMgr.GenerateGuildId();
|
m_Id = sObjectMgr.GenerateGuildId();
|
||||||
|
|
||||||
DEBUG_LOG("GUILD: creating guild %s to leader: %u", gname.c_str(), GUID_LOPART(m_LeaderGuid));
|
DEBUG_LOG("GUILD: creating guild %s to leader: %u", gname.c_str(), GUID_LOPART(m_LeaderGuid));
|
||||||
|
|
@ -230,10 +228,16 @@ bool Guild::LoadGuildFromDB(QueryResult *guildDataResult)
|
||||||
MOTD = fields[9].GetCppString();
|
MOTD = fields[9].GetCppString();
|
||||||
m_CreatedDate = fields[10].GetUInt64();
|
m_CreatedDate = fields[10].GetUInt64();
|
||||||
m_GuildBankMoney = fields[11].GetUInt64();
|
m_GuildBankMoney = fields[11].GetUInt64();
|
||||||
m_PurchasedTabs = fields[12].GetUInt32();
|
|
||||||
|
|
||||||
if (m_PurchasedTabs > GUILD_BANK_MAX_TABS)
|
uint32 purchasedTabs = fields[12].GetUInt32();
|
||||||
m_PurchasedTabs = GUILD_BANK_MAX_TABS;
|
|
||||||
|
if (purchasedTabs > GUILD_BANK_MAX_TABS)
|
||||||
|
purchasedTabs = GUILD_BANK_MAX_TABS;
|
||||||
|
|
||||||
|
m_TabListMap.resize(purchasedTabs);
|
||||||
|
|
||||||
|
for (uint8 i = 0; i < purchasedTabs; ++i)
|
||||||
|
m_TabListMap[i] = new GuildBankTab;
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
@ -613,7 +617,7 @@ void Guild::CreateRank(std::string name_,uint32 rights)
|
||||||
|
|
||||||
// existing records in db should be deleted before calling this procedure and m_PurchasedTabs must be loaded already
|
// existing records in db should be deleted before calling this procedure and m_PurchasedTabs must be loaded already
|
||||||
|
|
||||||
for (uint32 i = 0; i < m_PurchasedTabs; ++i)
|
for (uint32 i = 0; i < uint32(GetPurchasedTabs()); ++i)
|
||||||
{
|
{
|
||||||
// create bank rights with 0
|
// create bank rights with 0
|
||||||
CharacterDatabase.PExecute("INSERT INTO guild_bank_right (guildid,TabId,rid) VALUES ('%u','%u','%u')", m_Id, i, new_rank_id);
|
CharacterDatabase.PExecute("INSERT INTO guild_bank_right (guildid,TabId,rid) VALUES ('%u','%u','%u')", m_Id, i, new_rank_id);
|
||||||
|
|
@ -703,7 +707,10 @@ void Guild::Disband()
|
||||||
CharacterDatabase.PExecute("DELETE FROM guild WHERE guildid = '%u'", m_Id);
|
CharacterDatabase.PExecute("DELETE FROM guild WHERE guildid = '%u'", m_Id);
|
||||||
CharacterDatabase.PExecute("DELETE FROM guild_rank WHERE guildid = '%u'", m_Id);
|
CharacterDatabase.PExecute("DELETE FROM guild_rank WHERE guildid = '%u'", m_Id);
|
||||||
CharacterDatabase.PExecute("DELETE FROM guild_bank_tab WHERE guildid = '%u'", m_Id);
|
CharacterDatabase.PExecute("DELETE FROM guild_bank_tab WHERE guildid = '%u'", m_Id);
|
||||||
// TODO item_instance should be deleted ?
|
|
||||||
|
//Free bank tab used memory and delete items stored in them
|
||||||
|
DeleteGuildBankItems(true);
|
||||||
|
|
||||||
CharacterDatabase.PExecute("DELETE FROM guild_bank_item WHERE guildid = '%u'", m_Id);
|
CharacterDatabase.PExecute("DELETE FROM guild_bank_item WHERE guildid = '%u'", m_Id);
|
||||||
CharacterDatabase.PExecute("DELETE FROM guild_bank_right WHERE guildid = '%u'", m_Id);
|
CharacterDatabase.PExecute("DELETE FROM guild_bank_right WHERE guildid = '%u'", m_Id);
|
||||||
CharacterDatabase.PExecute("DELETE FROM guild_bank_eventlog WHERE guildid = '%u'", m_Id);
|
CharacterDatabase.PExecute("DELETE FROM guild_bank_eventlog WHERE guildid = '%u'", m_Id);
|
||||||
|
|
@ -1044,7 +1051,7 @@ void Guild::DisplayGuildBankContentUpdate(uint8 TabId, GuildItemPosCountVec cons
|
||||||
|
|
||||||
Item* Guild::GetItem(uint8 TabId, uint8 SlotId)
|
Item* Guild::GetItem(uint8 TabId, uint8 SlotId)
|
||||||
{
|
{
|
||||||
if (TabId >= m_TabListMap.size() || SlotId >= GUILD_BANK_MAX_SLOTS)
|
if (TabId >= GetPurchasedTabs() || SlotId >= GUILD_BANK_MAX_SLOTS)
|
||||||
return NULL;
|
return NULL;
|
||||||
return m_TabListMap[TabId]->Slots[SlotId];
|
return m_TabListMap[TabId]->Slots[SlotId];
|
||||||
}
|
}
|
||||||
|
|
@ -1061,9 +1068,9 @@ void Guild::DisplayGuildBankTabsInfo(WorldSession *session)
|
||||||
data << uint32(GetMemberSlotWithdrawRem(session->GetPlayer()->GetGUIDLow(), 0));
|
data << uint32(GetMemberSlotWithdrawRem(session->GetPlayer()->GetGUIDLow(), 0));
|
||||||
data << uint8(1); // Tell client that this packet includes tab info
|
data << uint8(1); // Tell client that this packet includes tab info
|
||||||
|
|
||||||
data << uint8(m_PurchasedTabs); // here is the number of tabs
|
data << uint8(GetPurchasedTabs()); // here is the number of tabs
|
||||||
|
|
||||||
for (uint8 i = 0; i < m_PurchasedTabs; ++i)
|
for (uint8 i = 0; i < GetPurchasedTabs(); ++i)
|
||||||
{
|
{
|
||||||
data << m_TabListMap[i]->Name.c_str();
|
data << m_TabListMap[i]->Name.c_str();
|
||||||
data << m_TabListMap[i]->Icon.c_str();
|
data << m_TabListMap[i]->Icon.c_str();
|
||||||
|
|
@ -1076,19 +1083,15 @@ void Guild::DisplayGuildBankTabsInfo(WorldSession *session)
|
||||||
|
|
||||||
void Guild::CreateNewBankTab()
|
void Guild::CreateNewBankTab()
|
||||||
{
|
{
|
||||||
if (m_PurchasedTabs >= GUILD_BANK_MAX_TABS)
|
if (GetPurchasedTabs() >= GUILD_BANK_MAX_TABS)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
++m_PurchasedTabs;
|
uint32 tabId = GetPurchasedTabs(); // next free id
|
||||||
|
m_TabListMap.push_back(new GuildBankTab);
|
||||||
GuildBankTab* AnotherTab = new GuildBankTab;
|
|
||||||
memset(AnotherTab->Slots, 0, GUILD_BANK_MAX_SLOTS * sizeof(Item*));
|
|
||||||
m_TabListMap.resize(m_PurchasedTabs);
|
|
||||||
m_TabListMap[m_PurchasedTabs-1] = AnotherTab;
|
|
||||||
|
|
||||||
CharacterDatabase.BeginTransaction();
|
CharacterDatabase.BeginTransaction();
|
||||||
CharacterDatabase.PExecute("DELETE FROM guild_bank_tab WHERE guildid='%u' AND TabId='%u'", m_Id, uint32(m_PurchasedTabs-1));
|
CharacterDatabase.PExecute("DELETE FROM guild_bank_tab WHERE guildid='%u' AND TabId='%u'", m_Id, tabId);
|
||||||
CharacterDatabase.PExecute("INSERT INTO guild_bank_tab (guildid,TabId) VALUES ('%u','%u')", m_Id, uint32(m_PurchasedTabs-1));
|
CharacterDatabase.PExecute("INSERT INTO guild_bank_tab (guildid,TabId) VALUES ('%u','%u')", m_Id, tabId);
|
||||||
CharacterDatabase.CommitTransaction();
|
CharacterDatabase.CommitTransaction();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -1123,24 +1126,27 @@ void Guild::LoadGuildBankFromDB()
|
||||||
QueryResult *result = CharacterDatabase.PQuery("SELECT TabId, TabName, TabIcon, TabText FROM guild_bank_tab WHERE guildid='%u' ORDER BY TabId", m_Id);
|
QueryResult *result = CharacterDatabase.PQuery("SELECT TabId, TabName, TabIcon, TabText FROM guild_bank_tab WHERE guildid='%u' ORDER BY TabId", m_Id);
|
||||||
if (!result)
|
if (!result)
|
||||||
{
|
{
|
||||||
m_PurchasedTabs = 0;
|
m_TabListMap.clear();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
m_TabListMap.resize(m_PurchasedTabs);
|
|
||||||
do
|
do
|
||||||
{
|
{
|
||||||
Field *fields = result->Fetch();
|
Field *fields = result->Fetch();
|
||||||
uint8 TabId = fields[0].GetUInt8();
|
uint8 tabId = fields[0].GetUInt8();
|
||||||
|
if (tabId >= GetPurchasedTabs())
|
||||||
|
{
|
||||||
|
sLog.outError("Table `guild_bank_tab` have not purchased tab %u for guild %u, skipped", tabId, m_Id);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
GuildBankTab *NewTab = new GuildBankTab;
|
GuildBankTab *NewTab = new GuildBankTab;
|
||||||
memset(NewTab->Slots, 0, GUILD_BANK_MAX_SLOTS * sizeof(Item*));
|
|
||||||
|
|
||||||
NewTab->Name = fields[1].GetCppString();
|
NewTab->Name = fields[1].GetCppString();
|
||||||
NewTab->Icon = fields[2].GetCppString();
|
NewTab->Icon = fields[2].GetCppString();
|
||||||
NewTab->Text = fields[3].GetCppString();
|
NewTab->Text = fields[3].GetCppString();
|
||||||
|
|
||||||
m_TabListMap[TabId] = NewTab;
|
m_TabListMap[tabId] = NewTab;
|
||||||
} while (result->NextRow());
|
} while (result->NextRow());
|
||||||
|
|
||||||
delete result;
|
delete result;
|
||||||
|
|
@ -1159,7 +1165,7 @@ void Guild::LoadGuildBankFromDB()
|
||||||
uint32 ItemGuid = fields[4].GetUInt32();
|
uint32 ItemGuid = fields[4].GetUInt32();
|
||||||
uint32 ItemEntry = fields[5].GetUInt32();
|
uint32 ItemEntry = fields[5].GetUInt32();
|
||||||
|
|
||||||
if (TabId >= m_PurchasedTabs || TabId >= GUILD_BANK_MAX_TABS)
|
if (TabId >= GetPurchasedTabs())
|
||||||
{
|
{
|
||||||
sLog.outError( "Guild::LoadGuildBankFromDB: Invalid tab for item (GUID: %u id: #%u) in guild bank, skipped.", ItemGuid,ItemEntry);
|
sLog.outError( "Guild::LoadGuildBankFromDB: Invalid tab for item (GUID: %u id: #%u) in guild bank, skipped.", ItemGuid,ItemEntry);
|
||||||
continue;
|
continue;
|
||||||
|
|
@ -1334,9 +1340,7 @@ void Guild::SetBankMoneyPerDay(uint32 rankId, uint32 money)
|
||||||
|
|
||||||
void Guild::SetBankRightsAndSlots(uint32 rankId, uint8 TabId, uint32 right, uint32 nbSlots, bool db)
|
void Guild::SetBankRightsAndSlots(uint32 rankId, uint8 TabId, uint32 right, uint32 nbSlots, bool db)
|
||||||
{
|
{
|
||||||
if (rankId >= m_Ranks.size() ||
|
if (rankId >= m_Ranks.size() || TabId >= GetPurchasedTabs())
|
||||||
TabId >= GUILD_BANK_MAX_TABS ||
|
|
||||||
TabId >= m_PurchasedTabs)
|
|
||||||
{
|
{
|
||||||
// TODO remove next line, It is there just to repair existing bug in deleting guild rank
|
// TODO remove next line, It is there just to repair existing bug in deleting guild rank
|
||||||
CharacterDatabase.PExecute("DELETE FROM guild_bank_right WHERE guildid='%u' AND rid='%u' AND TabId='%u'", m_Id, rankId, TabId);
|
CharacterDatabase.PExecute("DELETE FROM guild_bank_right WHERE guildid='%u' AND rid='%u' AND TabId='%u'", m_Id, rankId, TabId);
|
||||||
|
|
@ -1433,7 +1437,7 @@ void Guild::LoadGuildBankEventLogFromDB()
|
||||||
|
|
||||||
// uint32 configCount = sWorld.getConfig(CONFIG_UINT32_GUILD_BANK_EVENT_LOG_COUNT);
|
// uint32 configCount = sWorld.getConfig(CONFIG_UINT32_GUILD_BANK_EVENT_LOG_COUNT);
|
||||||
// cycle through all purchased guild bank item tabs
|
// cycle through all purchased guild bank item tabs
|
||||||
for (uint32 tabId = 0; tabId < m_PurchasedTabs; ++tabId)
|
for (uint32 tabId = 0; tabId < uint32(GetPurchasedTabs()); ++tabId)
|
||||||
{
|
{
|
||||||
// 0 1 2 3 4 5 6
|
// 0 1 2 3 4 5 6
|
||||||
QueryResult *result = CharacterDatabase.PQuery("SELECT LogGuid, EventType, PlayerGuid, ItemOrMoney, ItemStackCount, DestTabId, TimeStamp FROM guild_bank_eventlog WHERE guildid='%u' AND TabId='%u' ORDER BY TimeStamp DESC,LogGuid DESC LIMIT %u", m_Id, tabId, GUILD_BANK_MAX_LOGS);
|
QueryResult *result = CharacterDatabase.PQuery("SELECT LogGuid, EventType, PlayerGuid, ItemOrMoney, ItemStackCount, DestTabId, TimeStamp FROM guild_bank_eventlog WHERE guildid='%u' AND TabId='%u' ORDER BY TimeStamp DESC,LogGuid DESC LIMIT %u", m_Id, tabId, GUILD_BANK_MAX_LOGS);
|
||||||
|
|
@ -1892,10 +1896,9 @@ uint8 Guild::CanStoreItem( uint8 tab, uint8 slot, GuildItemPosCountVec &dest, ui
|
||||||
|
|
||||||
void Guild::SetGuildBankTabText(uint8 TabId, std::string text)
|
void Guild::SetGuildBankTabText(uint8 TabId, std::string text)
|
||||||
{
|
{
|
||||||
if (TabId >= GUILD_BANK_MAX_TABS)
|
if (TabId >= GetPurchasedTabs())
|
||||||
return;
|
|
||||||
if (TabId >= m_TabListMap.size())
|
|
||||||
return;
|
return;
|
||||||
|
|
||||||
if (!m_TabListMap[TabId])
|
if (!m_TabListMap[TabId])
|
||||||
return;
|
return;
|
||||||
|
|
||||||
|
|
@ -2371,6 +2374,27 @@ void Guild::BroadcastEvent(GuildEvents event, uint64 guid, uint8 strCount, std::
|
||||||
DEBUG_LOG("WORLD: Sent SMSG_GUILD_EVENT");
|
DEBUG_LOG("WORLD: Sent SMSG_GUILD_EVENT");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Guild::DeleteGuildBankItems( bool alsoInDB /*= false*/ )
|
||||||
|
{
|
||||||
|
for (size_t i = 0; i < m_TabListMap.size(); ++i)
|
||||||
|
{
|
||||||
|
for (uint8 j = 0; j < GUILD_BANK_MAX_SLOTS; ++j)
|
||||||
|
{
|
||||||
|
if (Item* pItem = m_TabListMap[i]->Slots[j])
|
||||||
|
{
|
||||||
|
pItem->RemoveFromWorld();
|
||||||
|
|
||||||
|
if (alsoInDB)
|
||||||
|
pItem->DeleteFromDB();
|
||||||
|
|
||||||
|
delete pItem;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
delete m_TabListMap[i];
|
||||||
|
}
|
||||||
|
m_TabListMap.clear();
|
||||||
|
}
|
||||||
|
|
||||||
bool GuildItemPosCount::isContainedIn(GuildItemPosCountVec const &vec) const
|
bool GuildItemPosCount::isContainedIn(GuildItemPosCountVec const &vec) const
|
||||||
{
|
{
|
||||||
for(GuildItemPosCountVec::const_iterator itr = vec.begin(); itr != vec.end(); ++itr)
|
for(GuildItemPosCountVec::const_iterator itr = vec.begin(); itr != vec.end(); ++itr)
|
||||||
|
|
|
||||||
|
|
@ -231,6 +231,8 @@ struct GuildBankEventLogEntry
|
||||||
|
|
||||||
struct GuildBankTab
|
struct GuildBankTab
|
||||||
{
|
{
|
||||||
|
GuildBankTab() { memset(Slots, 0, GUILD_BANK_MAX_SLOTS * sizeof(Item*)); }
|
||||||
|
|
||||||
Item* Slots[GUILD_BANK_MAX_SLOTS];
|
Item* Slots[GUILD_BANK_MAX_SLOTS];
|
||||||
std::string Name;
|
std::string Name;
|
||||||
std::string Icon;
|
std::string Icon;
|
||||||
|
|
@ -293,6 +295,7 @@ class Guild
|
||||||
void CreateDefaultGuildRanks(int locale_idx);
|
void CreateDefaultGuildRanks(int locale_idx);
|
||||||
void Disband();
|
void Disband();
|
||||||
|
|
||||||
|
void DeleteGuildBankItems(bool alsoInDB = false);
|
||||||
typedef std::map<uint32, MemberSlot> MemberList;
|
typedef std::map<uint32, MemberSlot> MemberList;
|
||||||
typedef std::vector<RankInfo> RankList;
|
typedef std::vector<RankInfo> RankList;
|
||||||
|
|
||||||
|
|
@ -402,7 +405,7 @@ class Guild
|
||||||
void SetGuildBankTabText(uint8 TabId, std::string text);
|
void SetGuildBankTabText(uint8 TabId, std::string text);
|
||||||
void SendGuildBankTabText(WorldSession *session, uint8 TabId);
|
void SendGuildBankTabText(WorldSession *session, uint8 TabId);
|
||||||
void SetGuildBankTabInfo(uint8 TabId, std::string name, std::string icon);
|
void SetGuildBankTabInfo(uint8 TabId, std::string name, std::string icon);
|
||||||
uint8 GetPurchasedTabs() const { return m_PurchasedTabs; }
|
uint8 GetPurchasedTabs() const { return m_TabListMap.size(); }
|
||||||
uint32 GetBankRights(uint32 rankId, uint8 TabId) const;
|
uint32 GetBankRights(uint32 rankId, uint8 TabId) const;
|
||||||
bool IsMemberHaveRights(uint32 LowGuid, uint8 TabId,uint32 rights) const;
|
bool IsMemberHaveRights(uint32 LowGuid, uint8 TabId,uint32 rights) const;
|
||||||
bool CanMemberViewTab(uint32 LowGuid, uint8 TabId) const;
|
bool CanMemberViewTab(uint32 LowGuid, uint8 TabId) const;
|
||||||
|
|
@ -465,7 +468,6 @@ class Guild
|
||||||
uint32 m_GuildBankEventLogNextGuid_Item[GUILD_BANK_MAX_TABS];
|
uint32 m_GuildBankEventLogNextGuid_Item[GUILD_BANK_MAX_TABS];
|
||||||
|
|
||||||
uint64 m_GuildBankMoney;
|
uint64 m_GuildBankMoney;
|
||||||
uint8 m_PurchasedTabs;
|
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void UpdateAccountsNumber();
|
void UpdateAccountsNumber();
|
||||||
|
|
|
||||||
|
|
@ -1,4 +1,4 @@
|
||||||
#ifndef __REVISION_NR_H__
|
#ifndef __REVISION_NR_H__
|
||||||
#define __REVISION_NR_H__
|
#define __REVISION_NR_H__
|
||||||
#define REVISION_NR "10283"
|
#define REVISION_NR "10284"
|
||||||
#endif // __REVISION_NR_H__
|
#endif // __REVISION_NR_H__
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue