TrinityCore
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Modules Pages
InstanceSaveMgr.h
Go to the documentation of this file.
1 /*
2  * Copyright (C) 2008-2016 TrinityCore <http://www.trinitycore.org/>
3  * Copyright (C) 2005-2009 MaNGOS <http://getmangos.com/>
4  *
5  * This program is free software; you can redistribute it and/or modify it
6  * under the terms of the GNU General Public License as published by the
7  * Free Software Foundation; either version 2 of the License, or (at your
8  * option) any later version.
9  *
10  * This program is distributed in the hope that it will be useful, but WITHOUT
11  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
12  * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
13  * more details.
14  *
15  * You should have received a copy of the GNU General Public License along
16  * with this program. If not, see <http://www.gnu.org/licenses/>.
17  */
18 
19 #ifndef _INSTANCESAVEMGR_H
20 #define _INSTANCESAVEMGR_H
21 
22 #include <list>
23 #include <map>
24 #include <mutex>
25 #include <unordered_map>
26 
27 #include "Define.h"
28 #include "DatabaseEnv.h"
29 #include "DBCEnums.h"
30 #include "ObjectDefines.h"
31 
32 struct InstanceTemplate;
33 struct MapEntry;
34 class Player;
35 class Group;
36 
37 /*
38  Holds the information necessary for creating a new map for an existing instance
39  Is referenced in three cases:
40  - player-instance binds for solo players (not in group)
41  - player-instance binds for permanent heroic/raid saves
42  - group-instance binds (both solo and permanent) cache the player binds for the group leader
43 */
45 {
46  friend class InstanceSaveManager;
47  public:
48  /* Created either when:
49  - any new instance is being generated
50  - the first time a player bound to InstanceId logs in
51  - when a group bound to the instance is loaded */
52  InstanceSave(uint16 MapId, uint32 InstanceId, Difficulty difficulty, time_t resetTime, bool canReset);
53 
54  /* Unloaded when m_playerList and m_groupList become empty
55  or when the instance is reset */
56  ~InstanceSave();
57 
58  uint32 GetPlayerCount() const { return uint32(m_playerList.size()); }
59  uint32 GetGroupCount() const { return uint32(m_groupList.size()); }
60 
61  /* A map corresponding to the InstanceId/MapId does not always exist.
62  InstanceSave objects may be created on player logon but the maps are
63  created and loaded only when a player actually enters the instance. */
64  uint32 GetInstanceId() const { return m_instanceid; }
65  uint32 GetMapId() const { return m_mapid; }
66 
67  /* Saved when the instance is generated for the first time */
68  void SaveToDB();
69  /* When the instance is being reset (permanently deleted) */
70  void DeleteFromDB();
71 
72  /* for normal instances this corresponds to max(creature respawn time) + X hours
73  for raid/heroic instances this caches the global respawn time for the map */
74  time_t GetResetTime() const { return m_resetTime; }
75  void SetResetTime(time_t resetTime) { m_resetTime = resetTime; }
76  time_t GetResetTimeForDB();
77 
78  InstanceTemplate const* GetTemplate();
79  MapEntry const* GetMapEntry();
80 
81  /* online players bound to the instance (perm/solo)
82  does not include the members of the group unless they have permanent saves */
83  void AddPlayer(Player* player)
84  {
85  std::lock_guard<std::mutex> lock(_playerListLock);
86  m_playerList.push_back(player);
87  }
88 
89  bool RemovePlayer(Player* player)
90  {
91  _playerListLock.lock();
92  m_playerList.remove(player);
93  bool isStillValid = UnloadIfEmpty();
94  _playerListLock.unlock();
95 
96  //delete here if needed, after releasing the lock
97  if (m_toDelete)
98  delete this;
99 
100  return isStillValid;
101  }
102  /* all groups bound to the instance */
103  void AddGroup(Group* group) { m_groupList.push_back(group); }
104  bool RemoveGroup(Group* group)
105  {
106  m_groupList.remove(group);
107  bool isStillValid = UnloadIfEmpty();
108  if (m_toDelete)
109  delete this;
110  return isStillValid;
111  }
112 
113  /* instances cannot be reset (except at the global reset time)
114  if there are players permanently bound to it
115  this is cached for the case when those players are offline */
116  bool CanReset() const { return m_canReset; }
117  void SetCanReset(bool canReset) { m_canReset = canReset; }
118 
119  /* currently it is possible to omit this information from this structure
120  but that would depend on a lot of things that can easily change in future */
121  Difficulty GetDifficultyID() const { return m_difficulty; }
122 
123  /* used to flag the InstanceSave as to be deleted, so the caller can delete it */
124  void SetToDelete(bool toDelete)
125  {
126  m_toDelete = toDelete;
127  }
128 
129  typedef std::list<Player*> PlayerListType;
130  typedef std::list<Group*> GroupListType;
131  private:
132  bool UnloadIfEmpty();
133  /* the only reason the instSave-object links are kept is because
134  the object-instSave links need to be broken at reset time */
136  PlayerListType m_playerList;
137  GroupListType m_groupList;
138  time_t m_resetTime;
144 
145  std::mutex _playerListLock;
146 };
147 
148 typedef std::unordered_map<uint64 /*PAIR64(map, difficulty)*/, time_t /*resetTime*/> ResetTimeByMapDifficultyMap;
149 
151 {
152  friend class InstanceSave;
153 
154  private:
155  InstanceSaveManager() : lock_instLists(false) { };
157 
158  public:
159  typedef std::unordered_map<uint32 /*InstanceId*/, InstanceSave*> InstanceSaveHashMap;
160 
161  static InstanceSaveManager* instance();
162 
163  void Unload();
164 
165  /* resetTime is a global propery of each (raid/heroic) map
166  all instances of that map reset at the same time */
168  {
170  Difficulty difficulty:8;
171  uint32 mapid;
172  uint32 instanceId;
173 
174  InstResetEvent() : type(0), difficulty(DIFFICULTY_NORMAL), mapid(0), instanceId(0) { }
175  InstResetEvent(uint8 t, uint32 _mapid, Difficulty d, uint32 _instanceid)
176  : type(t), difficulty(d), mapid(_mapid), instanceId(_instanceid) { }
177  bool operator == (const InstResetEvent& e) const { return e.instanceId == instanceId; }
178  };
179  typedef std::multimap<time_t /*resetTime*/, InstResetEvent> ResetTimeQueue;
180 
181  void LoadInstances();
182 
183  void LoadResetTimes();
184  time_t GetResetTimeFor(uint32 mapid, Difficulty d) const
185  {
186  ResetTimeByMapDifficultyMap::const_iterator itr = m_resetTimeByMapDifficulty.find(MAKE_PAIR64(mapid, d));
187  return itr != m_resetTimeByMapDifficulty.end() ? itr->second : 0;
188  }
189  time_t GetSubsequentResetTime(uint32 mapid, Difficulty difficulty, time_t resetTime) const;
190 
191  // Use this on startup when initializing reset times
192  void InitializeResetTimeFor(uint32 mapid, Difficulty d, time_t t)
193  {
194  m_resetTimeByMapDifficulty[MAKE_PAIR64(mapid, d)] = t;
195  }
196 
197  // Use this only when updating existing reset times
198  void SetResetTimeFor(uint32 mapid, Difficulty d, time_t t)
199  {
200  ResetTimeByMapDifficultyMap::iterator itr = m_resetTimeByMapDifficulty.find(MAKE_PAIR64(mapid, d));
201  ASSERT(itr != m_resetTimeByMapDifficulty.end());
202  itr->second = t;
203  }
204 
206  {
207  return m_resetTimeByMapDifficulty;
208  }
209  void ScheduleReset(bool add, time_t time, InstResetEvent event);
210  void ForceGlobalReset(uint32 mapId, Difficulty difficulty);
211 
212  void Update();
213 
214  InstanceSave* AddInstanceSave(uint32 mapId, uint32 instanceId, Difficulty difficulty, time_t resetTime,
215  bool canReset, bool load = false);
216  void RemoveInstanceSave(uint32 InstanceId);
217  void UnloadInstanceSave(uint32 InstanceId);
218  static void DeleteInstanceFromDB(uint32 instanceid);
219 
220  InstanceSave* GetInstanceSave(uint32 InstanceId);
221 
222  /* statistics */
223  uint32 GetNumInstanceSaves() const { return uint32(m_instanceSaveById.size()); }
224  uint32 GetNumBoundPlayersTotal() const;
225  uint32 GetNumBoundGroupsTotal() const;
226 
227  protected:
228  static uint16 ResetTimeDelay[];
229 
230  private:
231  void _ResetOrWarnAll(uint32 mapid, Difficulty difficulty, bool warn, time_t resetTime);
232  void _ResetInstance(uint32 mapid, uint32 instanceId);
233  void _ResetSave(InstanceSaveHashMap::iterator &itr);
234  // used during global instance resets
236  // fast lookup by instance id
237  InstanceSaveHashMap m_instanceSaveById;
238  // fast lookup for reset times (always use existed functions for access/set)
240  ResetTimeQueue m_resetTimeQueue;
241 };
242 
243 #define sInstanceSaveMgr InstanceSaveManager::instance()
244 #endif
uint8 type
Definition: InstanceSaveMgr.h:169
Difficulty
Definition: DBCEnums.h:402
InstResetEvent(uint8 t, uint32 _mapid, Difficulty d, uint32 _instanceid)
Definition: InstanceSaveMgr.h:175
PlayerListType m_playerList
Definition: InstanceSaveMgr.h:136
Definition: Map.h:222
uint32 instanceId
Definition: InstanceSaveMgr.h:172
uint32 GetNumInstanceSaves() const
Definition: InstanceSaveMgr.h:223
std::unordered_map< uint64, time_t > ResetTimeByMapDifficultyMap
Definition: InstanceSaveMgr.h:148
ResetTimeByMapDifficultyMap m_resetTimeByMapDifficulty
Definition: InstanceSaveMgr.h:239
Definition: InstanceSaveMgr.h:167
time_t GetResetTimeFor(uint32 mapid, Difficulty d) const
Definition: InstanceSaveMgr.h:184
Definition: DBCStructure.h:830
#define false
Definition: CascPort.h:18
void SetResetTime(time_t resetTime)
Definition: InstanceSaveMgr.h:75
ResetTimeByMapDifficultyMap const & GetResetTimeMap() const
Definition: InstanceSaveMgr.h:205
friend class InstanceSave
Definition: InstanceSaveMgr.h:152
Difficulty m_difficulty
Definition: InstanceSaveMgr.h:141
uint64 MAKE_PAIR64(uint32 l, uint32 h)
Definition: ObjectDefines.h:34
uint32 mapid
Definition: InstanceSaveMgr.h:171
void SetCanReset(bool canReset)
Definition: InstanceSaveMgr.h:117
void AddGroup(Group *group)
Definition: InstanceSaveMgr.h:103
ResetTimeQueue m_resetTimeQueue
Definition: InstanceSaveMgr.h:240
void SetResetTimeFor(uint32 mapid, Difficulty d, time_t t)
Definition: InstanceSaveMgr.h:198
InstanceSaveHashMap m_instanceSaveById
Definition: InstanceSaveMgr.h:237
bool m_canReset
Definition: InstanceSaveMgr.h:142
uint32 GetGroupCount() const
Definition: InstanceSaveMgr.h:59
uint32 m_instanceid
Definition: InstanceSaveMgr.h:139
std::unordered_map< uint32, InstanceSave * > InstanceSaveHashMap
Definition: InstanceSaveMgr.h:159
std::mutex _playerListLock
Definition: InstanceSaveMgr.h:145
bool operator==(const CoordPair< LIMIT > &p1, const CoordPair< LIMIT > &p2)
Definition: GridDefines.h:160
uint32_t uint32
Definition: Define.h:150
uint64_t uint64
Definition: Define.h:149
uint16_t uint16
Definition: Define.h:151
InstResetEvent()
Definition: InstanceSaveMgr.h:174
std::list< Group * > GroupListType
Definition: InstanceSaveMgr.h:130
std::list< Player * > PlayerListType
Definition: InstanceSaveMgr.h:129
Definition: InstanceSaveMgr.h:44
std::multimap< time_t, InstResetEvent > ResetTimeQueue
Definition: InstanceSaveMgr.h:179
uint32 m_mapid
Definition: InstanceSaveMgr.h:140
uint32 GetMapId() const
Definition: InstanceSaveMgr.h:65
bool m_toDelete
Definition: InstanceSaveMgr.h:143
uint32 GetPlayerCount() const
Definition: InstanceSaveMgr.h:58
void SetToDelete(bool toDelete)
Definition: InstanceSaveMgr.h:124
Definition: InstanceSaveMgr.h:150
Difficulty GetDifficultyID() const
Definition: InstanceSaveMgr.h:121
void InitializeResetTimeFor(uint32 mapid, Difficulty d, time_t t)
Definition: InstanceSaveMgr.h:192
#define TC_GAME_API
Definition: Define.h:134
bool lock_instLists
Definition: InstanceSaveMgr.h:235
uint8_t uint8
Definition: Define.h:152
#define ASSERT
Definition: Errors.h:55
InstanceSaveManager()
Definition: InstanceSaveMgr.h:155
bool RemovePlayer(Player *player)
Definition: InstanceSaveMgr.h:89
bool CanReset() const
Definition: InstanceSaveMgr.h:116
uint32_t uint32
Definition: g3dmath.h:168
time_t m_resetTime
Definition: InstanceSaveMgr.h:138
void AddPlayer(Player *player)
Definition: InstanceSaveMgr.h:83
bool RemoveGroup(Group *group)
Definition: InstanceSaveMgr.h:104
GroupListType m_groupList
Definition: InstanceSaveMgr.h:137
uint32 GetInstanceId() const
Definition: InstanceSaveMgr.h:64
void Update(uint32 diff)
Definition: WeatherMgr.cpp:150
time_t GetResetTime() const
Definition: InstanceSaveMgr.h:74
Definition: Group.h:191
Definition: DBCEnums.h:405