1
0
mirror of https://github.com/vcmi/vcmi.git synced 2025-06-17 00:07:41 +02:00

- proper destructors for handlers and lib objects

This commit is contained in:
Ivan Savenko
2013-04-21 16:38:31 +00:00
parent 2ea1051395
commit 4db13ba845
13 changed files with 79 additions and 10 deletions

View File

@ -146,6 +146,8 @@ CArtHandler::CArtHandler()
CArtHandler::~CArtHandler() CArtHandler::~CArtHandler()
{ {
BOOST_FOREACH(CArtifact * art, artifacts)
delete art;
} }
std::vector<JsonNode> CArtHandler::loadLegacyData(size_t dataSize) std::vector<JsonNode> CArtHandler::loadLegacyData(size_t dataSize)

View File

@ -1002,6 +1002,8 @@ int CCreatureHandler::stringToNumber(std::string & s)
CCreatureHandler::~CCreatureHandler() CCreatureHandler::~CCreatureHandler()
{ {
BOOST_FOREACH(auto & creature, creatures)
creature.dellNull();
} }
CreatureID CCreatureHandler::pickRandomMonster(const boost::function<int()> &randGen, int tier) const CreatureID CCreatureHandler::pickRandomMonster(const boost::function<int()> &randGen, int tier) const

View File

@ -161,7 +161,7 @@ public:
void addToSlot(SlotID slot, CreatureID cre, TQuantity count, bool allowMerging = true); //Adds stack to slot. Slot must be empty or with same type creature void addToSlot(SlotID slot, CreatureID cre, TQuantity count, bool allowMerging = true); //Adds stack to slot. Slot must be empty or with same type creature
void addToSlot(SlotID slot, CStackInstance *stack, bool allowMerging = true); //Adds stack to slot. Slot must be empty or with same type creature void addToSlot(SlotID slot, CStackInstance *stack, bool allowMerging = true); //Adds stack to slot. Slot must be empty or with same type creature
void clear() OVERRIDE; void clear() override;
void setFormation(bool tight); void setFormation(bool tight);
CArmedInstance *castToArmyObj(); CArmedInstance *castToArmyObj();
@ -177,7 +177,7 @@ public:
void eraseStack(SlotID slot); //slot must be occupied void eraseStack(SlotID slot); //slot must be occupied
void joinStack(SlotID slot, CStackInstance * stack); //adds new stack to the existing stack of the same type void joinStack(SlotID slot, CStackInstance * stack); //adds new stack to the existing stack of the same type
void changeStackCount(SlotID slot, TQuantity toAdd); //stack must exist! void changeStackCount(SlotID slot, TQuantity toAdd); //stack must exist!
bool setCreature (SlotID slot, CreatureID type, TQuantity quantity) OVERRIDE; //replaces creature in stack; slots 0 to 6, if quantity=0 erases stack bool setCreature (SlotID slot, CreatureID type, TQuantity quantity) override; //replaces creature in stack; slots 0 to 6, if quantity=0 erases stack
void setToArmy(CSimpleArmy &src); //erases all our army and moves stacks from src to us; src MUST NOT be an armed object! WARNING: use it wisely. Or better do not use at all. void setToArmy(CSimpleArmy &src); //erases all our army and moves stacks from src to us; src MUST NOT be an armed object! WARNING: use it wisely. Or better do not use at all.
const CStackInstance& getStack(SlotID slot) const; //stack must exist const CStackInstance& getStack(SlotID slot) const; //stack must exist

View File

@ -763,6 +763,9 @@ CGameState::~CGameState()
//delete initialOpts; //delete initialOpts;
delete applierGs; delete applierGs;
delete objCaller; delete objCaller;
BOOST_FOREACH(auto ptr, hpool.heroesPool) // clean hero pool
ptr.second.dellNull();
} }
BattleInfo * CGameState::setupBattle(int3 tile, const CArmedInstance *armies[2], const CGHeroInstance * heroes[2], bool creatureBank, const CGTownInstance *town) BattleInfo * CGameState::setupBattle(int3 tile, const CArmedInstance *armies[2], const CGHeroInstance * heroes[2], bool creatureBank, const CGTownInstance *town)

View File

@ -255,6 +255,17 @@ CObjectHandler::CObjectHandler()
logGlobal->traceStream() << "\t\tDone loading banks configs"; logGlobal->traceStream() << "\t\tDone loading banks configs";
} }
CObjectHandler::~CObjectHandler()
{
BOOST_FOREACH(auto & mapEntry, banksInfo)
{
BOOST_FOREACH(auto & vecEntry, mapEntry.second)
{
vecEntry.dellNull();
}
}
}
int CObjectHandler::bankObjToIndex (const CGObjectInstance * obj) int CObjectHandler::bankObjToIndex (const CGObjectInstance * obj)
{ {
switch (obj->ID) //find appriopriate key switch (obj->ID) //find appriopriate key
@ -817,6 +828,8 @@ void CGHeroInstance::initHero()
commander->setArmyObj (castToArmyObj()); //TODO: separate function for setting commanders commander->setArmyObj (castToArmyObj()); //TODO: separate function for setting commanders
commander->giveStackExp (exp); //after our exp is set commander->giveStackExp (exp); //after our exp is set
} }
else
commander = nullptr;
hoverName = VLC->generaltexth->allTexts[15]; hoverName = VLC->generaltexth->allTexts[15];
boost::algorithm::replace_first(hoverName,"%s",name); boost::algorithm::replace_first(hoverName,"%s",name);
@ -904,12 +917,14 @@ void CGHeroInstance::initHeroDefInfo()
} }
CGHeroInstance::~CGHeroInstance() CGHeroInstance::~CGHeroInstance()
{ {
commander.dellNull();
} }
bool CGHeroInstance::needsLastStack() const bool CGHeroInstance::needsLastStack() const
{ {
return true; return true;
} }
void CGHeroInstance::onHeroVisit(const CGHeroInstance * h) const void CGHeroInstance::onHeroVisit(const CGHeroInstance * h) const
{ {
if(h == this) return; //exclude potential self-visiting if(h == this) return; //exclude potential self-visiting

View File

@ -1404,6 +1404,7 @@ public:
std::vector<ui32> resVals; //default values of resources in gold std::vector<ui32> resVals; //default values of resources in gold
CObjectHandler(); CObjectHandler();
~CObjectHandler();
int bankObjToIndex (const CGObjectInstance * obj); int bankObjToIndex (const CGObjectInstance * obj);

View File

@ -131,6 +131,15 @@ CSpell::CSpell()
isOffensive = false; isOffensive = false;
} }
CSpell::~CSpell()
{
for (size_t i=0; i<effects.size(); i++)
{
for (size_t j=0; j<effects[i].size(); j++)
delete effects[i][j];
}
}
std::vector<BattleHex> CSpell::rangeInHexes(BattleHex centralHex, ui8 schoolLvl, ui8 side, bool *outDroppedHexes) const std::vector<BattleHex> CSpell::rangeInHexes(BattleHex centralHex, ui8 schoolLvl, ui8 side, bool *outDroppedHexes) const
{ {
std::vector<BattleHex> ret; std::vector<BattleHex> ret;
@ -479,7 +488,7 @@ CSpellHandler::CSpellHandler()
auto v = v_node.convertTo<std::vector<int> >(); auto v = v_node.convertTo<std::vector<int> >();
auto a = a_node.convertTo<std::vector<int> >(); auto a = a_node.convertTo<std::vector<int> >();
for (int i=0; i<4 ; i++) for (int i=0; i<s->effects.size() ; i++)
{ {
Bonus * b = JsonUtils::parseBonus(bonus_node); Bonus * b = JsonUtils::parseBonus(bonus_node);
b->sid = s->id; //for all b->sid = s->id; //for all
@ -493,10 +502,8 @@ CSpellHandler::CSpellHandler()
s->effects[i].push_back(b); s->effects[i].push_back(b);
} }
} }
auto find_in_map = [](std::string name, std::vector<Bonus::BonusType> &vec) auto find_in_map = [](std::string name, std::vector<Bonus::BonusType> &vec)
{ {
auto it = bonusNameMap.find(name); auto it = bonusNameMap.find(name);
@ -533,6 +540,14 @@ CSpellHandler::CSpellHandler()
} }
} }
CSpellHandler::~CSpellHandler()
{
BOOST_FOREACH(auto & spell, spells)
{
spell.dellNull();
}
}
std::vector<bool> CSpellHandler::getDefaultAllowed() const std::vector<bool> CSpellHandler::getDefaultAllowed() const
{ {
std::vector<bool> allowedSpells; std::vector<bool> allowedSpells;

View File

@ -46,6 +46,7 @@ public:
std::vector<SpellID> counteredSpells; //spells that are removed when effect of this spell is placed on creature (for bless-curse, haste-slow, and similar pairs) std::vector<SpellID> counteredSpells; //spells that are removed when effect of this spell is placed on creature (for bless-curse, haste-slow, and similar pairs)
CSpell(); CSpell();
~CSpell();
std::vector<BattleHex> rangeInHexes(BattleHex centralHex, ui8 schoolLvl, ui8 side, bool *outDroppedHexes = NULL ) const; //convert range to specific hexes; last optional out parameter is set to true, if spell would cover unavailable hexes (that are not included in ret) std::vector<BattleHex> rangeInHexes(BattleHex centralHex, ui8 schoolLvl, ui8 side, bool *outDroppedHexes = NULL ) const; //convert range to specific hexes; last optional out parameter is set to true, if spell would cover unavailable hexes (that are not included in ret)
si16 mainEffectAnim; //main spell effect animation, in AC format (or -1 when none) si16 mainEffectAnim; //main spell effect animation, in AC format (or -1 when none)
@ -96,7 +97,7 @@ private:
ETargetType targetType; ETargetType targetType;
std::vector<Bonus *> effects [4]; std::vector<std::vector<Bonus *> > effects; // [level 0-3][list of effects]
std::vector<Bonus::BonusType> immunities; //any of these grants immunity std::vector<Bonus::BonusType> immunities; //any of these grants immunity
std::vector<Bonus::BonusType> limiters; //all of them are required to be affected std::vector<Bonus::BonusType> limiters; //all of them are required to be affected
@ -166,6 +167,7 @@ class DLL_LINKAGE CSpellHandler
public: public:
CSpellHandler(); CSpellHandler();
~CSpellHandler();
std::vector< ConstTransitivePtr<CSpell> > spells; std::vector< ConstTransitivePtr<CSpell> > spells;
/** /**

View File

@ -73,11 +73,11 @@ CTown::CTown()
CTown::~CTown() CTown::~CTown()
{ {
BOOST_FOREACH(auto build, buildings) BOOST_FOREACH(auto & build, buildings)
build.second.dellNull(); build.second.dellNull();
BOOST_FOREACH(CStructure * str, clientInfo.structures) BOOST_FOREACH(auto & str, clientInfo.structures)
delete str; str.dellNull();
} }
CTownHandler::CTownHandler() CTownHandler::CTownHandler()
@ -85,6 +85,12 @@ CTownHandler::CTownHandler()
VLC->townh = this; VLC->townh = this;
} }
CTownHandler::~CTownHandler()
{
BOOST_FOREACH(auto faction, factions)
faction.dellNull();
}
JsonNode readBuilding(CLegacyConfigParser & parser) JsonNode readBuilding(CLegacyConfigParser & parser)
{ {
JsonNode ret; JsonNode ret;

View File

@ -225,6 +225,7 @@ public:
std::vector<ConstTransitivePtr<CFaction> > factions; std::vector<ConstTransitivePtr<CFaction> > factions;
CTownHandler(); //c-tor, set pointer in VLC to this CTownHandler(); //c-tor, set pointer in VLC to this
~CTownHandler();
std::vector<JsonNode> loadLegacyData(size_t dataSize) override; std::vector<JsonNode> loadLegacyData(size_t dataSize) override;

View File

@ -193,6 +193,12 @@ CResourceLoader * CResourceHandler::get()
} }
} }
void CResourceHandler::clear()
{
delete resourceLoader;
delete initialLoader;
}
//void CResourceLoaderFactory::setInstance(CResourceLoader * resourceLoader) //void CResourceLoaderFactory::setInstance(CResourceLoader * resourceLoader)
//{ //{
// CResourceLoaderFactory::resourceLoader = resourceLoader; // CResourceLoaderFactory::resourceLoader = resourceLoader;

View File

@ -375,6 +375,13 @@ public:
*/ */
static void initialize(); static void initialize();
/**
* Semi-debug method to track all possible cases of memory leaks
* Used before exiting application
*
*/
static void clear();
/** /**
* Will load all filesystem data from Json data at this path (config/filesystem.json) * Will load all filesystem data from Json data at this path (config/filesystem.json)
* @param prefix - prefix for all paths in filesystem config * @param prefix - prefix for all paths in filesystem config

View File

@ -30,6 +30,7 @@
#include "../lib/GameConstants.h" #include "../lib/GameConstants.h"
#include "../lib/logging/CBasicLogConfigurator.h" #include "../lib/logging/CBasicLogConfigurator.h"
#include "../lib/CConfigHandler.h" #include "../lib/CConfigHandler.h"
#include "../lib/ScopeGuard.h"
#include "../lib/UnlockGuard.h" #include "../lib/UnlockGuard.h"
@ -315,6 +316,7 @@ CVCMIServer::~CVCMIServer()
{ {
//delete io; //delete io;
//delete acceptor; //delete acceptor;
/delete firstConnection;
} }
CGameHandler * CVCMIServer::initGhFromHostingConnection(CConnection &c) CGameHandler * CVCMIServer::initGhFromHostingConnection(CConnection &c)
@ -351,8 +353,13 @@ void CVCMIServer::newGame()
assert(clients == 1); //multi goes now by newPregame, TODO: custom lobbies assert(clients == 1); //multi goes now by newPregame, TODO: custom lobbies
CGameHandler *gh = initGhFromHostingConnection(c); CGameHandler *gh = initGhFromHostingConnection(c);
gh->run(false);
auto onExit = vstd::makeScopeGuard([&]()
{
vstd::clear_pointer(gh); vstd::clear_pointer(gh);
});
gh->run(false);
} }
void CVCMIServer::newPregame() void CVCMIServer::newPregame()
@ -544,6 +551,8 @@ int main(int argc, char** argv)
//and return non-zero status so client can detect error //and return non-zero status so client can detect error
throw; throw;
} }
//delete VLC; //can't be re-enabled due to access to already freed memory in bonus system
CResourceHandler::clear();
return 0; return 0;
} }