[8754] Some guld back related packets data correctness checks

* Move when possible checks from deep code to packer/DB read level.
* Check real existed guild bank tabs amount instead just max possible amount.
* Check guild bank loaded state for packets expected to be called only after
  guild bank data loadin by another packet.

Thanks to elecyb and NetSky for original fix versions.
This commit is contained in:
VladimirMangos 2009-10-30 05:23:44 +03:00
parent 4284bcc2da
commit f35be9519c
5 changed files with 157 additions and 120 deletions

View file

@ -859,7 +859,7 @@ void WorldSession::HandleGuildBankerActivate( WorldPacket & recv_data )
{
if(Guild *pGuild = objmgr.GetGuildById(GuildId))
{
pGuild->DisplayGuildBankTabsInfo(this);
pGuild->DisplayGuildBankTabsInfo(this); // this also will load guild bank if not yet
return;
}
}
@ -879,17 +879,21 @@ void WorldSession::HandleGuildBankQueryTab( WorldPacket & recv_data )
if (!GetPlayer()->GetGameObjectIfCanInteractWith(GoGuid, GAMEOBJECT_TYPE_GUILD_BANK))
return;
if(uint32 GuildId = GetPlayer()->GetGuildId())
{
if(Guild *pGuild = objmgr.GetGuildById(GuildId))
{
// Let's update the amount of gold the player can withdraw before displaying the content
// This is useful if money withdraw right has changed
pGuild->SendMoneyInfo(this, GetPlayer()->GetGUIDLow());
uint32 GuildId = GetPlayer()->GetGuildId();
if (!GuildId)
return;
pGuild->DisplayGuildBankContent(this, TabId);
}
}
Guild *pGuild = objmgr.GetGuildById(GuildId);
if (!pGuild)
return;
if (!pGuild->IsGuildBankLoaded() || TabId >= pGuild->GetPurchasedTabs())
return;
// Let's update the amount of gold the player can withdraw before displaying the content
// This is useful if money withdraw right has changed
pGuild->SendMoneyInfo(this, GetPlayer()->GetGUIDLow());
pGuild->DisplayGuildBankContent(this, TabId);
}
void WorldSession::HandleGuildBankDepositMoney( WorldPacket & recv_data )
@ -909,33 +913,38 @@ void WorldSession::HandleGuildBankDepositMoney( WorldPacket & recv_data )
if (GetPlayer()->GetMoney() < money)
return;
if(uint32 GuildId = GetPlayer()->GetGuildId())
uint32 GuildId = GetPlayer()->GetGuildId();
if (!GuildId)
return;
Guild *pGuild = objmgr.GetGuildById(GuildId);
if (!pGuild)
return;
if (!pGuild->IsGuildBankLoaded() || !pGuild->GetPurchasedTabs())
return;
CharacterDatabase.BeginTransaction();
pGuild->SetBankMoney(pGuild->GetGuildBankMoney()+money);
GetPlayer()->ModifyMoney(-int(money));
GetPlayer()->SaveGoldToDB();
CharacterDatabase.CommitTransaction();
// logging money
if(_player->GetSession()->GetSecurity() > SEC_PLAYER && sWorld.getConfig(CONFIG_GM_LOG_TRADE))
{
if(Guild *pGuild = objmgr.GetGuildById(GuildId))
{
CharacterDatabase.BeginTransaction();
pGuild->SetBankMoney(pGuild->GetGuildBankMoney()+money);
GetPlayer()->ModifyMoney(-int(money));
GetPlayer()->SaveGoldToDB();
CharacterDatabase.CommitTransaction();
// logging money
if(_player->GetSession()->GetSecurity() > SEC_PLAYER && sWorld.getConfig(CONFIG_GM_LOG_TRADE))
{
sLog.outCommand(_player->GetSession()->GetAccountId(),"GM %s (Account: %u) deposit money (Amount: %u) to guild bank (Guild ID %u)",
_player->GetName(),_player->GetSession()->GetAccountId(),money,GuildId);
}
// log
pGuild->LogBankEvent(GUILD_BANK_LOG_DEPOSIT_MONEY, uint8(0), GetPlayer()->GetGUIDLow(), money);
pGuild->DisplayGuildBankTabsInfo(this);
pGuild->DisplayGuildBankContent(this, 0);
pGuild->DisplayGuildBankMoneyUpdate();
}
sLog.outCommand(_player->GetSession()->GetAccountId(),"GM %s (Account: %u) deposit money (Amount: %u) to guild bank (Guild ID %u)",
_player->GetName(),_player->GetSession()->GetAccountId(),money,GuildId);
}
// log
pGuild->LogBankEvent(GUILD_BANK_LOG_DEPOSIT_MONEY, uint8(0), GetPlayer()->GetGUIDLow(), money);
pGuild->DisplayGuildBankTabsInfo(this);
pGuild->DisplayGuildBankContent(this, 0);
pGuild->DisplayGuildBankMoneyUpdate();
}
void WorldSession::HandleGuildBankWithdrawMoney( WorldPacket & recv_data )
@ -960,6 +969,9 @@ void WorldSession::HandleGuildBankWithdrawMoney( WorldPacket & recv_data )
if(!pGuild)
return;
if (!pGuild->IsGuildBankLoaded() || !pGuild->GetPurchasedTabs())
return;
if (pGuild->GetGuildBankMoney()<money) // not enough money in bank
return;
@ -1005,6 +1017,21 @@ void WorldSession::HandleGuildBankSwapItems( WorldPacket & recv_data )
uint32 SplitedAmount = 0;
recv_data >> GoGuid >> BankToBank;
uint32 GuildId = GetPlayer()->GetGuildId();
if (!GuildId)
{
recv_data.rpos(recv_data.wpos()); // prevent additional spam at rejected packet
return;
}
Guild *pGuild = objmgr.GetGuildById(GuildId);
if (!pGuild || !pGuild->IsGuildBankLoaded())
{
recv_data.rpos(recv_data.wpos()); // prevent additional spam at rejected packet
return;
}
if (BankToBank)
{
recv_data >> BankTabDst;
@ -1016,7 +1043,10 @@ void WorldSession::HandleGuildBankSwapItems( WorldPacket & recv_data )
recv_data >> unk2; // always 0
recv_data >> SplitedAmount;
if (BankTabSlotDst >= GUILD_BANK_MAX_SLOTS || (BankTabDst == BankTab && BankTabSlotDst == BankTabSlot))
if (BankTabSlotDst >= GUILD_BANK_MAX_SLOTS ||
(BankTabDst == BankTab && BankTabSlotDst == BankTabSlot) ||
BankTab >= pGuild->GetPurchasedTabs() ||
BankTabDst >= pGuild->GetPurchasedTabs())
{
recv_data.rpos(recv_data.wpos()); // prevent additional spam at rejected packet
return;
@ -1042,7 +1072,8 @@ void WorldSession::HandleGuildBankSwapItems( WorldPacket & recv_data )
recv_data >> SplitedAmount;
}
if (BankTabSlot >= GUILD_BANK_MAX_SLOTS && BankTabSlot != 0xFF)
if (BankTabSlot >= GUILD_BANK_MAX_SLOTS && BankTabSlot != 0xFF ||
BankTab >= pGuild->GetPurchasedTabs())
{
recv_data.rpos(recv_data.wpos()); // prevent additional spam at rejected packet
return;
@ -1052,33 +1083,27 @@ void WorldSession::HandleGuildBankSwapItems( WorldPacket & recv_data )
if (!GetPlayer()->GetGameObjectIfCanInteractWith(GoGuid, GAMEOBJECT_TYPE_GUILD_BANK))
return;
if(uint32 GuildId = GetPlayer()->GetGuildId())
// Bank <-> Bank
if (BankToBank)
{
if(Guild *pGuild = objmgr.GetGuildById(GuildId))
{
// Bank <-> Bank
if (BankToBank)
{
pGuild->SwapItems(_player, BankTab, BankTabSlot, BankTabDst, BankTabSlotDst, SplitedAmount);
return;
}
// Player <-> Bank
// allow work with inventory only
if(!Player::IsInventoryPos(PlayerBag, PlayerSlot) && !(PlayerBag == NULL_BAG && PlayerSlot == NULL_SLOT) )
{
_player->SendEquipError( EQUIP_ERR_NONE, NULL, NULL );
return;
}
// BankToChar swap or char to bank remaining
if (ToChar) // Bank -> Char cases
pGuild->MoveFromBankToChar(_player, BankTab, BankTabSlot, PlayerBag, PlayerSlot, SplitedAmount);
else // Char -> Bank cases
pGuild->MoveFromCharToBank(_player, PlayerBag, PlayerSlot, BankTab, BankTabSlot, SplitedAmount);
}
pGuild->SwapItems(_player, BankTab, BankTabSlot, BankTabDst, BankTabSlotDst, SplitedAmount);
return;
}
// Player <-> Bank
// allow work with inventory only
if(!Player::IsInventoryPos(PlayerBag, PlayerSlot) && !(PlayerBag == NULL_BAG && PlayerSlot == NULL_SLOT) )
{
_player->SendEquipError( EQUIP_ERR_NONE, NULL, NULL );
return;
}
// BankToChar swap or char to bank remaining
if (ToChar) // Bank -> Char cases
pGuild->MoveFromBankToChar(_player, BankTab, BankTabSlot, PlayerBag, PlayerSlot, SplitedAmount);
else // Char -> Bank cases
pGuild->MoveFromCharToBank(_player, PlayerBag, PlayerSlot, BankTab, BankTabSlot, SplitedAmount);
}
void WorldSession::HandleGuildBankBuyTab( WorldPacket & recv_data )
@ -1095,26 +1120,21 @@ void WorldSession::HandleGuildBankBuyTab( WorldPacket & recv_data )
return;
uint32 GuildId = GetPlayer()->GetGuildId();
if (GuildId==0)
if (!GuildId)
return;
Guild *pGuild = objmgr.GetGuildById(GuildId);
if(!pGuild)
return;
// m_PurchasedTabs = 0 when buying Tab 0, that is why this check can be made
if (!pGuild->IsGuildBankLoaded() || TabId != pGuild->GetPurchasedTabs())
return;
uint32 TabCost = GetGuildBankTabPrice(TabId) * GOLD;
if (!TabCost)
return;
if (pGuild->GetPurchasedTabs() >= GUILD_BANK_MAX_TABS)
return;
if (TabId != pGuild->GetPurchasedTabs()) // m_PurchasedTabs = 0 when buying Tab 0, that is why this check can be made
{
sLog.outError("Error: trying to buy a tab non contiguous to owned ones");
return;
}
if (GetPlayer()->GetMoney() < TabCost) // Should not happen, this is checked by client
return;
@ -1149,15 +1169,20 @@ void WorldSession::HandleGuildBankUpdateTab( WorldPacket & recv_data )
if (!GetPlayer()->GetGameObjectIfCanInteractWith(GoGuid, GAMEOBJECT_TYPE_GUILD_BANK))
return;
if(uint32 GuildId = GetPlayer()->GetGuildId())
{
if(Guild *pGuild = objmgr.GetGuildById(GuildId))
{
pGuild->SetGuildBankTabInfo(TabId, Name, IconIndex);
pGuild->DisplayGuildBankTabsInfo(this);
pGuild->DisplayGuildBankContent(this, TabId);
}
}
uint32 GuildId = GetPlayer()->GetGuildId();
if (!GuildId)
return;
Guild *pGuild = objmgr.GetGuildById(GuildId);
if (!pGuild)
return;
if (!pGuild->IsGuildBankLoaded() || TabId >= pGuild->GetPurchasedTabs())
return;
pGuild->SetGuildBankTabInfo(TabId, Name, IconIndex);
pGuild->DisplayGuildBankTabsInfo(this);
pGuild->DisplayGuildBankContent(this, TabId);
}
void WorldSession::HandleGuildBankLogQuery( WorldPacket & recv_data )
@ -1167,9 +1192,22 @@ void WorldSession::HandleGuildBankLogQuery( WorldPacket & recv_data )
uint8 TabId;
recv_data >> TabId;
if(uint32 GuildId = GetPlayer()->GetGuildId())
if(Guild *pGuild = objmgr.GetGuildById(GuildId))
pGuild->DisplayGuildBankLogs(this, TabId);
uint32 GuildId = GetPlayer()->GetGuildId();
if (!GuildId)
return;
Guild *pGuild = objmgr.GetGuildById(GuildId);
if (!pGuild)
return;
if (!pGuild->IsGuildBankLoaded())
return;
// GUILD_BANK_MAX_TABS send by client for money log
if (TabId >= pGuild->GetPurchasedTabs() && TabId != GUILD_BANK_MAX_TABS)
return;
pGuild->DisplayGuildBankLogs(this, TabId);
}
void WorldSession::HandleQueryGuildBankTabText(WorldPacket &recv_data)
@ -1179,9 +1217,18 @@ void WorldSession::HandleQueryGuildBankTabText(WorldPacket &recv_data)
uint8 TabId;
recv_data >> TabId;
if(uint32 GuildId = GetPlayer()->GetGuildId())
if(Guild *pGuild = objmgr.GetGuildById(GuildId))
pGuild->SendGuildBankTabText(this, TabId);
uint32 GuildId = GetPlayer()->GetGuildId();
if (!GuildId)
return;
Guild *pGuild = objmgr.GetGuildById(GuildId);
if (!pGuild)
return;
if (!pGuild->IsGuildBankLoaded() || TabId >= pGuild->GetPurchasedTabs())
return;
pGuild->SendGuildBankTabText(this, TabId);
}
void WorldSession::HandleSetGuildBankTabText(WorldPacket &recv_data)
@ -1193,9 +1240,18 @@ void WorldSession::HandleSetGuildBankTabText(WorldPacket &recv_data)
recv_data >> TabId;
recv_data >> Text;
if(uint32 GuildId = GetPlayer()->GetGuildId())
if(Guild *pGuild = objmgr.GetGuildById(GuildId))
pGuild->SetGuildBankTabText(TabId, Text);
uint32 GuildId = GetPlayer()->GetGuildId();
if (!GuildId)
return;
Guild *pGuild = objmgr.GetGuildById(GuildId);
if (!pGuild)
return;
if (!pGuild->IsGuildBankLoaded() || TabId >= pGuild->GetPurchasedTabs())
return;
pGuild->SetGuildBankTabText(TabId, Text);
}
void WorldSession::SendSaveGuildEmblem( uint32 msg )