diff options
Diffstat (limited to 'src/server/shared/Utilities')
-rw-r--r-- | src/server/shared/Utilities/ByteConverter.h | 68 | ||||
-rw-r--r-- | src/server/shared/Utilities/Duration.h | 39 | ||||
-rw-r--r-- | src/server/shared/Utilities/EventMap.cpp | 136 | ||||
-rw-r--r-- | src/server/shared/Utilities/EventMap.h | 342 | ||||
-rw-r--r-- | src/server/shared/Utilities/EventProcessor.cpp | 99 | ||||
-rw-r--r-- | src/server/shared/Utilities/EventProcessor.h | 73 | ||||
-rw-r--r-- | src/server/shared/Utilities/ServiceWin32.cpp | 264 | ||||
-rw-r--r-- | src/server/shared/Utilities/ServiceWin32.h | 29 | ||||
-rw-r--r-- | src/server/shared/Utilities/StringFormat.h | 46 | ||||
-rw-r--r-- | src/server/shared/Utilities/TaskScheduler.cpp | 229 | ||||
-rw-r--r-- | src/server/shared/Utilities/TaskScheduler.h | 650 | ||||
-rw-r--r-- | src/server/shared/Utilities/Timer.h | 203 | ||||
-rw-r--r-- | src/server/shared/Utilities/Util.cpp | 562 | ||||
-rw-r--r-- | src/server/shared/Utilities/Util.h | 545 |
14 files changed, 0 insertions, 3285 deletions
diff --git a/src/server/shared/Utilities/ByteConverter.h b/src/server/shared/Utilities/ByteConverter.h deleted file mode 100644 index a077de3eb0b..00000000000 --- a/src/server/shared/Utilities/ByteConverter.h +++ /dev/null @@ -1,68 +0,0 @@ -/* - * Copyright (C) 2008-2015 TrinityCore <http://www.trinitycore.org/> - * Copyright (C) 2005-2009 MaNGOS <http://getmangos.com/> - * - * This program is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License as published by the - * Free Software Foundation; either version 2 of the License, or (at your - * option) any later version. - * - * This program is distributed in the hope that it will be useful, but WITHOUT - * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for - * more details. - * - * You should have received a copy of the GNU General Public License along - * with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef TRINITY_BYTECONVERTER_H -#define TRINITY_BYTECONVERTER_H - -/** ByteConverter reverse your byte order. This is use - for cross platform where they have different endians. - */ - -#include "Define.h" -#include <algorithm> - -namespace ByteConverter -{ - template<size_t T> - inline void convert(char *val) - { - std::swap(*val, *(val + T - 1)); - convert<T - 2>(val + 1); - } - - template<> inline void convert<0>(char *) { } - template<> inline void convert<1>(char *) { } // ignore central byte - - template<typename T> inline void apply(T *val) - { - convert<sizeof(T)>((char *)(val)); - } -} - -#if TRINITY_ENDIAN == TRINITY_BIGENDIAN -template<typename T> inline void EndianConvert(T& val) { ByteConverter::apply<T>(&val); } -template<typename T> inline void EndianConvertReverse(T&) { } -template<typename T> inline void EndianConvertPtr(void* val) { ByteConverter::apply<T>(val); } -template<typename T> inline void EndianConvertPtrReverse(void*) { } -#else -template<typename T> inline void EndianConvert(T&) { } -template<typename T> inline void EndianConvertReverse(T& val) { ByteConverter::apply<T>(&val); } -template<typename T> inline void EndianConvertPtr(void*) { } -template<typename T> inline void EndianConvertPtrReverse(void* val) { ByteConverter::apply<T>(val); } -#endif - -template<typename T> void EndianConvert(T*); // will generate link error -template<typename T> void EndianConvertReverse(T*); // will generate link error - -inline void EndianConvert(uint8&) { } -inline void EndianConvert( int8&) { } -inline void EndianConvertReverse(uint8&) { } -inline void EndianConvertReverse( int8&) { } - -#endif - diff --git a/src/server/shared/Utilities/Duration.h b/src/server/shared/Utilities/Duration.h deleted file mode 100644 index 58a08e5842f..00000000000 --- a/src/server/shared/Utilities/Duration.h +++ /dev/null @@ -1,39 +0,0 @@ -/* - * Copyright (C) 2008-2015 TrinityCore <http://www.trinitycore.org/> - * - * This program is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License as published by the - * Free Software Foundation; either version 2 of the License, or (at your - * option) any later version. - * - * This program is distributed in the hope that it will be useful, but WITHOUT - * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for - * more details. - * - * You should have received a copy of the GNU General Public License along - * with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef _DURATION_H_ -#define _DURATION_H_ - -#include <chrono> - -/// Milliseconds shorthand typedef. -typedef std::chrono::milliseconds Milliseconds; - -/// Seconds shorthand typedef. -typedef std::chrono::seconds Seconds; - -/// Minutes shorthand typedef. -typedef std::chrono::minutes Minutes; - -/// Hours shorthand typedef. -typedef std::chrono::hours Hours; - -/// Makes std::chrono_literals globally available. -// ToDo: Enable this when TC supports C++14. -// using namespace std::chrono_literals; - -#endif // _DURATION_H_ diff --git a/src/server/shared/Utilities/EventMap.cpp b/src/server/shared/Utilities/EventMap.cpp deleted file mode 100644 index 8c3f60afe82..00000000000 --- a/src/server/shared/Utilities/EventMap.cpp +++ /dev/null @@ -1,136 +0,0 @@ -/* - * Copyright (C) 2008-2015 TrinityCore <http://www.trinitycore.org/> - * - * This program is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License as published by the - * Free Software Foundation; either version 2 of the License, or (at your - * option) any later version. - * - * This program is distributed in the hope that it will be useful, but WITHOUT - * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for - * more details. - * - * You should have received a copy of the GNU General Public License along - * with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#include "EventMap.h" - -void EventMap::Reset() -{ - _eventMap.clear(); - _time = 0; - _phase = 0; -} - -void EventMap::SetPhase(uint8 phase) -{ - if (!phase) - _phase = 0; - else if (phase <= 8) - _phase = uint8(1 << (phase - 1)); -} - -void EventMap::ScheduleEvent(uint32 eventId, uint32 time, uint32 group /*= 0*/, uint8 phase /*= 0*/) -{ - if (group && group <= 8) - eventId |= (1 << (group + 15)); - - if (phase && phase <= 8) - eventId |= (1 << (phase + 23)); - - _eventMap.insert(EventStore::value_type(_time + time, eventId)); -} - -uint32 EventMap::ExecuteEvent() -{ - while (!Empty()) - { - EventStore::iterator itr = _eventMap.begin(); - - if (itr->first > _time) - return 0; - else if (_phase && (itr->second & 0xFF000000) && !((itr->second >> 24) & _phase)) - _eventMap.erase(itr); - else - { - uint32 eventId = (itr->second & 0x0000FFFF); - _lastEvent = itr->second; // include phase/group - _eventMap.erase(itr); - return eventId; - } - } - - return 0; -} - -void EventMap::DelayEvents(uint32 delay, uint32 group) -{ - if (!group || group > 8 || Empty()) - return; - - EventStore delayed; - - for (EventStore::iterator itr = _eventMap.begin(); itr != _eventMap.end();) - { - if (itr->second & (1 << (group + 15))) - { - delayed.insert(EventStore::value_type(itr->first + delay, itr->second)); - _eventMap.erase(itr++); - } - else - ++itr; - } - - _eventMap.insert(delayed.begin(), delayed.end()); -} - -void EventMap::CancelEvent(uint32 eventId) -{ - if (Empty()) - return; - - for (EventStore::iterator itr = _eventMap.begin(); itr != _eventMap.end();) - { - if (eventId == (itr->second & 0x0000FFFF)) - _eventMap.erase(itr++); - else - ++itr; - } -} - -void EventMap::CancelEventGroup(uint32 group) -{ - if (!group || group > 8 || Empty()) - return; - - for (EventStore::iterator itr = _eventMap.begin(); itr != _eventMap.end();) - { - if (itr->second & (1 << (group + 15))) - _eventMap.erase(itr++); - else - ++itr; - } -} - -uint32 EventMap::GetNextEventTime(uint32 eventId) const -{ - if (Empty()) - return 0; - - for (EventStore::const_iterator itr = _eventMap.begin(); itr != _eventMap.end(); ++itr) - if (eventId == (itr->second & 0x0000FFFF)) - return itr->first; - - return 0; -} - -uint32 EventMap::GetTimeUntilEvent(uint32 eventId) const -{ - for (EventStore::const_iterator itr = _eventMap.begin(); itr != _eventMap.end(); ++itr) - if (eventId == (itr->second & 0x0000FFFF)) - return itr->first - _time; - - return std::numeric_limits<uint32>::max(); -} diff --git a/src/server/shared/Utilities/EventMap.h b/src/server/shared/Utilities/EventMap.h deleted file mode 100644 index 021dffc4940..00000000000 --- a/src/server/shared/Utilities/EventMap.h +++ /dev/null @@ -1,342 +0,0 @@ -/* - * Copyright (C) 2008-2015 TrinityCore <http://www.trinitycore.org/> - * - * This program is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License as published by the - * Free Software Foundation; either version 2 of the License, or (at your - * option) any later version. - * - * This program is distributed in the hope that it will be useful, but WITHOUT - * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for - * more details. - * - * You should have received a copy of the GNU General Public License along - * with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef _EVENT_MAP_H_ -#define _EVENT_MAP_H_ - -#include "Common.h" -#include "Duration.h" -#include "Util.h" - -class EventMap -{ - /** - * Internal storage type. - * Key: Time as uint32 when the event should occur. - * Value: The event data as uint32. - * - * Structure of event data: - * - Bit 0 - 15: Event Id. - * - Bit 16 - 23: Group - * - Bit 24 - 31: Phase - * - Pattern: 0xPPGGEEEE - */ - typedef std::multimap<uint32, uint32> EventStore; - -public: - EventMap() : _time(0), _phase(0), _lastEvent(0) { } - - /** - * @name Reset - * @brief Removes all scheduled events and resets time and phase. - */ - void Reset(); - - /** - * @name Update - * @brief Updates the timer of the event map. - * @param time Value in ms to be added to time. - */ - void Update(uint32 time) - { - _time += time; - } - - /** - * @name GetTimer - * @return Current timer in ms value. - */ - uint32 GetTimer() const - { - return _time; - } - - /** - * @name GetPhaseMask - * @return Active phases as mask. - */ - uint8 GetPhaseMask() const - { - return _phase; - } - - /** - * @name Empty - * @return True, if there are no events scheduled. - */ - bool Empty() const - { - return _eventMap.empty(); - } - - /** - * @name SetPhase - * @brief Sets the phase of the map (absolute). - * @param phase Phase which should be set. Values: 1 - 8. 0 resets phase. - */ - void SetPhase(uint8 phase); - - /** - * @name AddPhase - * @brief Activates the given phase (bitwise). - * @param phase Phase which should be activated. Values: 1 - 8 - */ - void AddPhase(uint8 phase) - { - if (phase && phase <= 8) - _phase |= uint8(1 << (phase - 1)); - } - - /** - * @name RemovePhase - * @brief Deactivates the given phase (bitwise). - * @param phase Phase which should be deactivated. Values: 1 - 8. - */ - void RemovePhase(uint8 phase) - { - if (phase && phase <= 8) - _phase &= uint8(~(1 << (phase - 1))); - } - - /** - * @name ScheduleEvent - * @brief Creates new event entry in map. - * @param eventId The id of the new event. - * @param time The time in milliseconds as std::chrono::duration until the event occurs. - * @param group The group which the event is associated to. Has to be between 1 and 8. 0 means it has no group. - * @param phase The phase in which the event can occur. Has to be between 1 and 8. 0 means it can occur in all phases. - */ - void ScheduleEvent(uint32 eventId, Milliseconds const& time, uint32 group = 0, uint8 phase = 0) - { - ScheduleEvent(eventId, time.count(), group, phase); - } - - /** - * @name ScheduleEvent - * @brief Creates new event entry in map. - * @param eventId The id of the new event. - * @param time The time in milliseconds until the event occurs. - * @param group The group which the event is associated to. Has to be between 1 and 8. 0 means it has no group. - * @param phase The phase in which the event can occur. Has to be between 1 and 8. 0 means it can occur in all phases. - */ - void ScheduleEvent(uint32 eventId, uint32 time, uint32 group = 0, uint8 phase = 0); - - /** - * @name RescheduleEvent - * @brief Cancels the given event and reschedules it. - * @param eventId The id of the event. - * @param time The time in milliseconds as std::chrono::duration until the event occurs. - * @param group The group which the event is associated to. Has to be between 1 and 8. 0 means it has no group. - * @param phase The phase in which the event can occur. Has to be between 1 and 8. 0 means it can occur in all phases. - */ - void RescheduleEvent(uint32 eventId, Milliseconds const& time, uint32 group = 0, uint8 phase = 0) - { - RescheduleEvent(eventId, time.count(), group, phase); - } - - /** - * @name RescheduleEvent - * @brief Cancels the given event and reschedules it. - * @param eventId The id of the event. - * @param time The time in milliseconds until the event occurs. - * @param group The group which the event is associated to. Has to be between 1 and 8. 0 means it has no group. - * @param phase The phase in which the event can occur. Has to be between 1 and 8. 0 means it can occur in all phases. - */ - void RescheduleEvent(uint32 eventId, uint32 time, uint32 group = 0, uint8 phase = 0) - { - CancelEvent(eventId); - ScheduleEvent(eventId, time, group, phase); - } - - /** - * @name RepeatEvent - * @brief Repeats the mostly recently executed event. - * @param time Time until in milliseconds as std::chrono::duration the event occurs. - */ - void Repeat(Milliseconds const& time) - { - Repeat(time.count()); - } - - /** - * @name RepeatEvent - * @brief Repeats the mostly recently executed event. - * @param time Time until the event occurs. - */ - void Repeat(uint32 time) - { - _eventMap.insert(EventStore::value_type(_time + time, _lastEvent)); - } - - /** - * @name RepeatEvent - * @brief Repeats the mostly recently executed event. - * @param minTime Minimum time as std::chrono::duration until the event occurs. - * @param maxTime Maximum time as std::chrono::duration until the event occurs. - */ - void Repeat(Milliseconds const& minTime, Milliseconds const& maxTime) - { - Repeat(minTime.count(), maxTime.count()); - } - - /** - * @name RepeatEvent - * @brief Repeats the mostly recently executed event, Equivalent to Repeat(urand(minTime, maxTime). - * @param minTime Minimum time until the event occurs. - * @param maxTime Maximum time until the event occurs. - */ - void Repeat(uint32 minTime, uint32 maxTime) - { - Repeat(urand(minTime, maxTime)); - } - - /** - * @name ExecuteEvent - * @brief Returns the next event to execute and removes it from map. - * @return Id of the event to execute. - */ - uint32 ExecuteEvent(); - - /** - * @name DelayEvents - * @brief Delays all events in the map. If delay is greater than or equal internal timer, delay will be 0. - * @param delay Amount of delay in ms as std::chrono::duration. - */ - void DelayEvents(Milliseconds const& delay) - { - DelayEvents(delay.count()); - } - - /** - * @name DelayEvents - * @brief Delays all events in the map. If delay is greater than or equal internal timer, delay will be 0. - * @param delay Amount of delay. - */ - void DelayEvents(uint32 delay) - { - _time = delay < _time ? _time - delay : 0; - } - - /** - * @name DelayEvents - * @brief Delay all events of the same group. - * @param delay Amount of delay in ms as std::chrono::duration. - * @param group Group of the events. - */ - void DelayEvents(Milliseconds const& delay, uint32 group) - { - DelayEvents(delay.count(), group); - } - - /** - * @name DelayEvents - * @brief Delay all events of the same group. - * @param delay Amount of delay. - * @param group Group of the events. - */ - void DelayEvents(uint32 delay, uint32 group); - - /** - * @name CancelEvent - * @brief Cancels all events of the specified id. - * @param eventId Event id to cancel. - */ - void CancelEvent(uint32 eventId); - - /** - * @name CancelEventGroup - * @brief Cancel events belonging to specified group. - * @param group Group to cancel. - */ - void CancelEventGroup(uint32 group); - - /** - * @name GetNextEventTime - * @brief Returns closest occurence of specified event. - * @param eventId Wanted event id. - * @return Time of found event. - */ - uint32 GetNextEventTime(uint32 eventId) const; - - /** - * @name GetNextEventTime - * @return Time of next event. - */ - uint32 GetNextEventTime() const - { - return Empty() ? 0 : _eventMap.begin()->first; - } - - /** - * @name IsInPhase - * @brief Returns whether event map is in specified phase or not. - * @param phase Wanted phase. - * @return True, if phase of event map contains specified phase. - */ - bool IsInPhase(uint8 phase) const - { - return phase <= 8 && (!phase || _phase & (1 << (phase - 1))); - } - - /** - * @name GetTimeUntilEvent - * @brief Returns time in milliseconds until next event. - * @param eventId of the event. - * @return Time of next event. - */ - uint32 GetTimeUntilEvent(uint32 eventId) const; - -private: - /** - * @name _time - * @brief Internal timer. - * - * This does not represent the real date/time value. - * It's more like a stopwatch: It can run, it can be stopped, - * it can be resetted and so on. Events occur when this timer - * has reached their time value. Its value is changed in the - * Update method. - */ - uint32 _time; - - /** - * @name _phase - * @brief Phase mask of the event map. - * - * Contains the phases the event map is in. Multiple - * phases from 1 to 8 can be set with SetPhase or - * AddPhase. RemovePhase deactives a phase. - */ - uint8 _phase; - - /** - * @name _eventMap - * @brief Internal event storage map. Contains the scheduled events. - * - * See typedef at the beginning of the class for more - * details. - */ - EventStore _eventMap; - - /** - * @name _lastEvent - * @brief Stores information on the most recently executed event - */ - uint32 _lastEvent; -}; - -#endif // _EVENT_MAP_H_ diff --git a/src/server/shared/Utilities/EventProcessor.cpp b/src/server/shared/Utilities/EventProcessor.cpp deleted file mode 100644 index 34695665443..00000000000 --- a/src/server/shared/Utilities/EventProcessor.cpp +++ /dev/null @@ -1,99 +0,0 @@ -/* - * Copyright (C) 2008-2015 TrinityCore <http://www.trinitycore.org/> - * Copyright (C) 2005-2009 MaNGOS <http://getmangos.com/> - * - * This program is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License as published by the - * Free Software Foundation; either version 2 of the License, or (at your - * option) any later version. - * - * This program is distributed in the hope that it will be useful, but WITHOUT - * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for - * more details. - * - * You should have received a copy of the GNU General Public License along - * with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#include "EventProcessor.h" - -EventProcessor::EventProcessor() -{ - m_time = 0; - m_aborting = false; -} - -EventProcessor::~EventProcessor() -{ - KillAllEvents(true); -} - -void EventProcessor::Update(uint32 p_time) -{ - // update time - m_time += p_time; - - // main event loop - EventList::iterator i; - while (((i = m_events.begin()) != m_events.end()) && i->first <= m_time) - { - // get and remove event from queue - BasicEvent* Event = i->second; - m_events.erase(i); - - if (!Event->to_Abort) - { - if (Event->Execute(m_time, p_time)) - { - // completely destroy event if it is not re-added - delete Event; - } - } - else - { - Event->Abort(m_time); - delete Event; - } - } -} - -void EventProcessor::KillAllEvents(bool force) -{ - // prevent event insertions - m_aborting = true; - - // first, abort all existing events - for (EventList::iterator i = m_events.begin(); i != m_events.end();) - { - EventList::iterator i_old = i; - ++i; - - i_old->second->to_Abort = true; - i_old->second->Abort(m_time); - if (force || i_old->second->IsDeletable()) - { - delete i_old->second; - - if (!force) // need per-element cleanup - m_events.erase (i_old); - } - } - - // fast clear event list (in force case) - if (force) - m_events.clear(); -} - -void EventProcessor::AddEvent(BasicEvent* Event, uint64 e_time, bool set_addtime) -{ - if (set_addtime) Event->m_addTime = m_time; - Event->m_execTime = e_time; - m_events.insert(std::pair<uint64, BasicEvent*>(e_time, Event)); -} - -uint64 EventProcessor::CalculateTime(uint64 t_offset) const -{ - return(m_time + t_offset); -} - diff --git a/src/server/shared/Utilities/EventProcessor.h b/src/server/shared/Utilities/EventProcessor.h deleted file mode 100644 index 3d54bd6f9f2..00000000000 --- a/src/server/shared/Utilities/EventProcessor.h +++ /dev/null @@ -1,73 +0,0 @@ -/* - * Copyright (C) 2008-2015 TrinityCore <http://www.trinitycore.org/> - * Copyright (C) 2005-2009 MaNGOS <http://getmangos.com/> - * - * This program is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License as published by the - * Free Software Foundation; either version 2 of the License, or (at your - * option) any later version. - * - * This program is distributed in the hope that it will be useful, but WITHOUT - * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for - * more details. - * - * You should have received a copy of the GNU General Public License along - * with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef __EVENTPROCESSOR_H -#define __EVENTPROCESSOR_H - -#include "Define.h" - -#include <map> - -// Note. All times are in milliseconds here. - -class BasicEvent -{ - public: - BasicEvent() - { - to_Abort = false; - m_addTime = 0; - m_execTime = 0; - } - virtual ~BasicEvent() { } // override destructor to perform some actions on event removal - - // this method executes when the event is triggered - // return false if event does not want to be deleted - // e_time is execution time, p_time is update interval - virtual bool Execute(uint64 /*e_time*/, uint32 /*p_time*/) { return true; } - - virtual bool IsDeletable() const { return true; } // this event can be safely deleted - - virtual void Abort(uint64 /*e_time*/) { } // this method executes when the event is aborted - - bool to_Abort; // set by externals when the event is aborted, aborted events don't execute - // and get Abort call when deleted - - // these can be used for time offset control - uint64 m_addTime; // time when the event was added to queue, filled by event handler - uint64 m_execTime; // planned time of next execution, filled by event handler -}; - -typedef std::multimap<uint64, BasicEvent*> EventList; - -class EventProcessor -{ - public: - EventProcessor(); - ~EventProcessor(); - - void Update(uint32 p_time); - void KillAllEvents(bool force); - void AddEvent(BasicEvent* Event, uint64 e_time, bool set_addtime = true); - uint64 CalculateTime(uint64 t_offset) const; - protected: - uint64 m_time; - EventList m_events; - bool m_aborting; -}; -#endif diff --git a/src/server/shared/Utilities/ServiceWin32.cpp b/src/server/shared/Utilities/ServiceWin32.cpp deleted file mode 100644 index 3e5e416b1a3..00000000000 --- a/src/server/shared/Utilities/ServiceWin32.cpp +++ /dev/null @@ -1,264 +0,0 @@ -/* - * Copyright (C) 2008-2015 TrinityCore <http://www.trinitycore.org/> - * Copyright (C) 2005-2009 MaNGOS <http://getmangos.com> - * - * This program is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License as published by the - * Free Software Foundation; either version 2 of the License, or (at your - * option) any later version. - * - * This program is distributed in the hope that it will be useful, but WITHOUT - * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for - * more details. - * - * You should have received a copy of the GNU General Public License along - * with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifdef _WIN32 - -#include "Common.h" -#include "Log.h" -#include <cstring> -#include <windows.h> -#include <winsvc.h> - -#if !defined(WINADVAPI) -#if !defined(_ADVAPI32_) -#define WINADVAPI DECLSPEC_IMPORT -#else -#define WINADVAPI -#endif -#endif - -extern int main(int argc, char ** argv); -extern char serviceLongName[]; -extern char serviceName[]; -extern char serviceDescription[]; - -extern int m_ServiceStatus; - -SERVICE_STATUS serviceStatus; - -SERVICE_STATUS_HANDLE serviceStatusHandle = 0; - -typedef WINADVAPI BOOL (WINAPI *CSD_T)(SC_HANDLE, DWORD, LPCVOID); - -bool WinServiceInstall() -{ - SC_HANDLE serviceControlManager = OpenSCManager(0, 0, SC_MANAGER_CREATE_SERVICE); - - if (serviceControlManager) - { - char path[_MAX_PATH + 10]; - if (GetModuleFileName( 0, path, sizeof(path)/sizeof(path[0]) ) > 0) - { - SC_HANDLE service; - std::strcat(path, " --service run"); - service = CreateService(serviceControlManager, - serviceName, // name of service - serviceLongName, // service name to display - SERVICE_ALL_ACCESS, // desired access - // service type - SERVICE_WIN32_OWN_PROCESS | SERVICE_INTERACTIVE_PROCESS, - SERVICE_AUTO_START, // start type - SERVICE_ERROR_IGNORE, // error control type - path, // service's binary - 0, // no load ordering group - 0, // no tag identifier - 0, // no dependencies - 0, // LocalSystem account - 0); // no password - if (service) - { - HMODULE advapi32 = GetModuleHandle("ADVAPI32.DLL"); - if (!advapi32) - { - CloseServiceHandle(service); - CloseServiceHandle(serviceControlManager); - return false; - } - - CSD_T ChangeService_Config2 = (CSD_T) GetProcAddress(advapi32, "ChangeServiceConfig2A"); - if (!ChangeService_Config2) - { - CloseServiceHandle(service); - CloseServiceHandle(serviceControlManager); - return false; - } - - SERVICE_DESCRIPTION sdBuf; - sdBuf.lpDescription = serviceDescription; - ChangeService_Config2( - service, // handle to service - SERVICE_CONFIG_DESCRIPTION, // change: description - &sdBuf); // new data - - SC_ACTION _action[1]; - _action[0].Type = SC_ACTION_RESTART; - _action[0].Delay = 10000; - SERVICE_FAILURE_ACTIONS sfa; - ZeroMemory(&sfa, sizeof(SERVICE_FAILURE_ACTIONS)); - sfa.lpsaActions = _action; - sfa.cActions = 1; - sfa.dwResetPeriod =INFINITE; - ChangeService_Config2( - service, // handle to service - SERVICE_CONFIG_FAILURE_ACTIONS, // information level - &sfa); // new data - - CloseServiceHandle(service); - - } - } - CloseServiceHandle(serviceControlManager); - } - - printf("Service installed\n"); - return true; -} - -bool WinServiceUninstall() -{ - SC_HANDLE serviceControlManager = OpenSCManager(0, 0, SC_MANAGER_CONNECT); - - if (serviceControlManager) - { - SC_HANDLE service = OpenService(serviceControlManager, - serviceName, SERVICE_QUERY_STATUS | DELETE); - if (service) - { - SERVICE_STATUS serviceStatus2; - if (QueryServiceStatus(service, &serviceStatus2)) - { - if (serviceStatus2.dwCurrentState == SERVICE_STOPPED) - DeleteService(service); - } - CloseServiceHandle(service); - } - - CloseServiceHandle(serviceControlManager); - } - - printf("Service uninstalled\n"); - return true; -} - -void WINAPI ServiceControlHandler(DWORD controlCode) -{ - switch (controlCode) - { - case SERVICE_CONTROL_INTERROGATE: - break; - - case SERVICE_CONTROL_SHUTDOWN: - case SERVICE_CONTROL_STOP: - serviceStatus.dwCurrentState = SERVICE_STOP_PENDING; - SetServiceStatus(serviceStatusHandle, &serviceStatus); - - m_ServiceStatus = 0; - return; - - case SERVICE_CONTROL_PAUSE: - m_ServiceStatus = 2; - serviceStatus.dwCurrentState = SERVICE_PAUSED; - SetServiceStatus(serviceStatusHandle, &serviceStatus); - break; - - case SERVICE_CONTROL_CONTINUE: - serviceStatus.dwCurrentState = SERVICE_RUNNING; - SetServiceStatus(serviceStatusHandle, &serviceStatus); - m_ServiceStatus = 1; - break; - - default: - if ( controlCode >= 128 && controlCode <= 255 ) - // user defined control code - break; - else - // unrecognized control code - break; - } - - SetServiceStatus(serviceStatusHandle, &serviceStatus); -} - -void WINAPI ServiceMain(DWORD argc, char *argv[]) -{ - // initialise service status - serviceStatus.dwServiceType = SERVICE_WIN32; - serviceStatus.dwCurrentState = SERVICE_START_PENDING; - serviceStatus.dwControlsAccepted = SERVICE_ACCEPT_STOP | SERVICE_ACCEPT_PAUSE_CONTINUE; - serviceStatus.dwWin32ExitCode = NO_ERROR; - serviceStatus.dwServiceSpecificExitCode = NO_ERROR; - serviceStatus.dwCheckPoint = 0; - serviceStatus.dwWaitHint = 0; - - serviceStatusHandle = RegisterServiceCtrlHandler(serviceName, ServiceControlHandler); - - if ( serviceStatusHandle ) - { - char path[_MAX_PATH + 1]; - unsigned int i, last_slash = 0; - - GetModuleFileName(0, path, sizeof(path)/sizeof(path[0])); - - size_t pathLen = std::strlen(path); - for (i = 0; i < pathLen; i++) - { - if (path[i] == '\\') last_slash = i; - } - - path[last_slash] = 0; - - // service is starting - serviceStatus.dwCurrentState = SERVICE_START_PENDING; - SetServiceStatus(serviceStatusHandle, &serviceStatus); - - // do initialisation here - SetCurrentDirectory(path); - - // running - serviceStatus.dwControlsAccepted |= (SERVICE_ACCEPT_STOP | SERVICE_ACCEPT_SHUTDOWN); - serviceStatus.dwCurrentState = SERVICE_RUNNING; - SetServiceStatus( serviceStatusHandle, &serviceStatus ); - - //////////////////////// - // service main cycle // - //////////////////////// - - m_ServiceStatus = 1; - argc = 1; - main(argc, argv); - - // service was stopped - serviceStatus.dwCurrentState = SERVICE_STOP_PENDING; - SetServiceStatus(serviceStatusHandle, &serviceStatus); - - // do cleanup here - - // service is now stopped - serviceStatus.dwControlsAccepted &= ~(SERVICE_ACCEPT_STOP | SERVICE_ACCEPT_SHUTDOWN); - serviceStatus.dwCurrentState = SERVICE_STOPPED; - SetServiceStatus(serviceStatusHandle, &serviceStatus); - } -} - -bool WinServiceRun() -{ - SERVICE_TABLE_ENTRY serviceTable[] = - { - { serviceName, ServiceMain }, - { 0, 0 } - }; - - if (!StartServiceCtrlDispatcher(serviceTable)) - { - TC_LOG_ERROR("server.worldserver", "StartService Failed. Error [%u]", uint32(::GetLastError())); - return false; - } - return true; -} -#endif - diff --git a/src/server/shared/Utilities/ServiceWin32.h b/src/server/shared/Utilities/ServiceWin32.h deleted file mode 100644 index 9d9c732cd20..00000000000 --- a/src/server/shared/Utilities/ServiceWin32.h +++ /dev/null @@ -1,29 +0,0 @@ -/* - * Copyright (C) 2008-2015 TrinityCore <http://www.trinitycore.org/> - * Copyright (C) 2005-2009 MaNGOS <http://getmangos.com> - * - * This program is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License as published by the - * Free Software Foundation; either version 2 of the License, or (at your - * option) any later version. - * - * This program is distributed in the hope that it will be useful, but WITHOUT - * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for - * more details. - * - * You should have received a copy of the GNU General Public License along - * with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifdef _WIN32 -#ifndef _WIN32_SERVICE_ -#define _WIN32_SERVICE_ - -bool WinServiceInstall(); -bool WinServiceUninstall(); -bool WinServiceRun(); - -#endif // _WIN32_SERVICE_ -#endif // _WIN32 - diff --git a/src/server/shared/Utilities/StringFormat.h b/src/server/shared/Utilities/StringFormat.h deleted file mode 100644 index 67e0100e7c8..00000000000 --- a/src/server/shared/Utilities/StringFormat.h +++ /dev/null @@ -1,46 +0,0 @@ -/* - * Copyright (C) 2008-2015 TrinityCore <http://www.trinitycore.org/> - * Copyright (C) 2005-2009 MaNGOS <http://getmangos.com/> - * - * This program is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License as published by the - * Free Software Foundation; either version 2 of the License, or (at your - * option) any later version. - * - * This program is distributed in the hope that it will be useful, but WITHOUT - * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for - * more details. - * - * You should have received a copy of the GNU General Public License along - * with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef TRINITYCORE_STRING_FORMAT_H -#define TRINITYCORE_STRING_FORMAT_H - -#include "format.h" - -namespace Trinity -{ - /// Default TC string format function. - template<typename Format, typename... Args> - inline std::string StringFormat(Format&& fmt, Args&&... args) - { - return fmt::sprintf(std::forward<Format>(fmt), std::forward<Args>(args)...); - } - - /// Returns true if the given char pointer is null. - inline bool IsFormatEmptyOrNull(const char* fmt) - { - return fmt == nullptr; - } - - /// Returns true if the given std::string is empty. - inline bool IsFormatEmptyOrNull(std::string const& fmt) - { - return fmt.empty(); - } -} - -#endif diff --git a/src/server/shared/Utilities/TaskScheduler.cpp b/src/server/shared/Utilities/TaskScheduler.cpp deleted file mode 100644 index 801cc96cf77..00000000000 --- a/src/server/shared/Utilities/TaskScheduler.cpp +++ /dev/null @@ -1,229 +0,0 @@ -/* - * Copyright (C) 2008-2015 TrinityCore <http://www.trinitycore.org/> - * - * This program is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License as published by the - * Free Software Foundation; either version 2 of the License, or (at your - * option) any later version. - * - * This program is distributed in the hope that it will be useful, but WITHOUT - * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for - * more details. - * - * You should have received a copy of the GNU General Public License along - * with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#include "TaskScheduler.h" - -TaskScheduler& TaskScheduler::ClearValidator() -{ - _predicate = EmptyValidator; - return *this; -} - -TaskScheduler& TaskScheduler::Update(success_t const& callback) -{ - _now = clock_t::now(); - Dispatch(callback); - return *this; -} - -TaskScheduler& TaskScheduler::Update(size_t const milliseconds, success_t const& callback) -{ - return Update(std::chrono::milliseconds(milliseconds), callback); -} - -TaskScheduler& TaskScheduler::Async(std::function<void()> const& callable) -{ - _asyncHolder.push(callable); - return *this; -} - -TaskScheduler& TaskScheduler::CancelAll() -{ - /// Clear the task holder - _task_holder.Clear(); - _asyncHolder = AsyncHolder(); - return *this; -} - -TaskScheduler& TaskScheduler::CancelGroup(group_t const group) -{ - _task_holder.RemoveIf([group](TaskContainer const& task) -> bool - { - return task->IsInGroup(group); - }); - return *this; -} - -TaskScheduler& TaskScheduler::CancelGroupsOf(std::vector<group_t> const& groups) -{ - std::for_each(groups.begin(), groups.end(), - std::bind(&TaskScheduler::CancelGroup, this, std::placeholders::_1)); - - return *this; -} - -TaskScheduler& TaskScheduler::InsertTask(TaskContainer task) -{ - _task_holder.Push(std::move(task)); - return *this; -} - -void TaskScheduler::Dispatch(success_t const& callback) -{ - // If the validation failed abort the dispatching here. - if (!_predicate()) - return; - - // Process all asyncs - while (!_asyncHolder.empty()) - { - _asyncHolder.front()(); - _asyncHolder.pop(); - - // If the validation failed abort the dispatching here. - if (!_predicate()) - return; - } - - while (!_task_holder.IsEmpty()) - { - if (_task_holder.First()->_end > _now) - break; - - // Perfect forward the context to the handler - // Use weak references to catch destruction before callbacks. - TaskContext context(_task_holder.Pop(), std::weak_ptr<TaskScheduler>(self_reference)); - - // Invoke the context - context.Invoke(); - - // If the validation failed abort the dispatching here. - if (!_predicate()) - return; - } - - // On finish call the final callback - callback(); -} - -void TaskScheduler::TaskQueue::Push(TaskContainer&& task) -{ - container.insert(task); -} - -auto TaskScheduler::TaskQueue::Pop() -> TaskContainer -{ - TaskContainer result = *container.begin(); - container.erase(container.begin()); - return result; -} - -auto TaskScheduler::TaskQueue::First() const -> TaskContainer const& -{ - return *container.begin(); -} - -void TaskScheduler::TaskQueue::Clear() -{ - container.clear(); -} - -void TaskScheduler::TaskQueue::RemoveIf(std::function<bool(TaskContainer const&)> const& filter) -{ - for (auto itr = container.begin(); itr != container.end();) - if (filter(*itr)) - itr = container.erase(itr); - else - ++itr; -} - -void TaskScheduler::TaskQueue::ModifyIf(std::function<bool(TaskContainer const&)> const& filter) -{ - std::vector<TaskContainer> cache; - for (auto itr = container.begin(); itr != container.end();) - if (filter(*itr)) - { - cache.push_back(*itr); - itr = container.erase(itr); - } - else - ++itr; - - container.insert(cache.begin(), cache.end()); -} - -bool TaskScheduler::TaskQueue::IsEmpty() const -{ - return container.empty(); -} - -TaskContext& TaskContext::Dispatch(std::function<TaskScheduler&(TaskScheduler&)> const& apply) -{ - if (auto const owner = _owner.lock()) - apply(*owner); - - return *this; -} - -bool TaskContext::IsExpired() const -{ - return _owner.expired(); -} - -bool TaskContext::IsInGroup(TaskScheduler::group_t const group) const -{ - return _task->IsInGroup(group); -} - -TaskContext& TaskContext::SetGroup(TaskScheduler::group_t const group) -{ - _task->_group = group; - return *this; -} - -TaskContext& TaskContext::ClearGroup() -{ - _task->_group = boost::none; - return *this; -} - -TaskScheduler::repeated_t TaskContext::GetRepeatCounter() const -{ - return _task->_repeated; -} - -TaskContext& TaskContext::Async(std::function<void()> const& callable) -{ - return Dispatch(std::bind(&TaskScheduler::Async, std::placeholders::_1, callable)); -} - -TaskContext& TaskContext::CancelAll() -{ - return Dispatch(std::mem_fn(&TaskScheduler::CancelAll)); -} - -TaskContext& TaskContext::CancelGroup(TaskScheduler::group_t const group) -{ - return Dispatch(std::bind(&TaskScheduler::CancelGroup, std::placeholders::_1, group)); -} - -TaskContext& TaskContext::CancelGroupsOf(std::vector<TaskScheduler::group_t> const& groups) -{ - return Dispatch(std::bind(&TaskScheduler::CancelGroupsOf, std::placeholders::_1, std::cref(groups))); -} - -void TaskContext::AssertOnConsumed() const -{ - // This was adapted to TC to prevent static analysis tools from complaining. - // If you encounter this assertion check if you repeat a TaskContext more then 1 time! - ASSERT(!(*_consumed) && "Bad task logic, task context was consumed already!"); -} - -void TaskContext::Invoke() -{ - _task->_task(*this); -} diff --git a/src/server/shared/Utilities/TaskScheduler.h b/src/server/shared/Utilities/TaskScheduler.h deleted file mode 100644 index f1fe7ea0a21..00000000000 --- a/src/server/shared/Utilities/TaskScheduler.h +++ /dev/null @@ -1,650 +0,0 @@ -/* - * Copyright (C) 2008-2015 TrinityCore <http://www.trinitycore.org/> - * - * This program is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License as published by the - * Free Software Foundation; either version 2 of the License, or (at your - * option) any later version. - * - * This program is distributed in the hope that it will be useful, but WITHOUT - * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for - * more details. - * - * You should have received a copy of the GNU General Public License along - * with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef _TASK_SCHEDULER_H_ -#define _TASK_SCHEDULER_H_ - -#include <algorithm> -#include <chrono> -#include <vector> -#include <queue> -#include <memory> -#include <utility> -#include <set> - -#include <boost/optional.hpp> - -#include "Util.h" -#include "Duration.h" - -class TaskContext; - -/// The TaskScheduler class provides the ability to schedule std::function's in the near future. -/// Use TaskScheduler::Update to update the scheduler. -/// Popular methods are: -/// * Schedule (Schedules a std::function which will be executed in the near future). -/// * Schedules an asynchronous function which will be executed at the next update tick. -/// * Cancel, Delay & Reschedule (Methods to manipulate already scheduled tasks). -/// Tasks are organized in groups (uint), multiple tasks can have the same group id, -/// you can provide a group or not, but keep in mind that you can only manipulate specific tasks through its group id! -/// Tasks callbacks use the function signature void(TaskContext) where TaskContext provides -/// access to the function schedule plan which makes it possible to repeat the task -/// with the same duration or a new one. -/// It also provides access to the repeat counter which is useful for task that repeat itself often -/// but behave different every time (spoken event dialogs for example). -class TaskScheduler -{ - friend class TaskContext; - - // Time definitions (use steady clock) - typedef std::chrono::steady_clock clock_t; - typedef clock_t::time_point timepoint_t; - typedef clock_t::duration duration_t; - - // Task group type - typedef uint32 group_t; - // Task repeated type - typedef uint32 repeated_t; - // Task handle type - typedef std::function<void(TaskContext)> task_handler_t; - // Predicate type - typedef std::function<bool()> predicate_t; - // Success handle type - typedef std::function<void()> success_t; - - class Task - { - friend class TaskContext; - friend class TaskScheduler; - - timepoint_t _end; - duration_t _duration; - boost::optional<group_t> _group; - repeated_t _repeated; - task_handler_t _task; - - public: - // All Argument construct - Task(timepoint_t const& end, duration_t const& duration, boost::optional<group_t> const& group, - repeated_t const repeated, task_handler_t const& task) - : _end(end), _duration(duration), _group(group), _repeated(repeated), _task(task) { } - - // Minimal Argument construct - Task(timepoint_t const& end, duration_t const& duration, task_handler_t const& task) - : _end(end), _duration(duration), _group(boost::none), _repeated(0), _task(task) { } - - // Copy construct - Task(Task const&) = delete; - // Move construct - Task(Task&&) = delete; - // Copy Assign - Task& operator= (Task const&) = default; - // Move Assign - Task& operator= (Task&& right) = delete; - - // Order tasks by its end - inline bool operator< (Task const& other) const - { - return _end < other._end; - } - - inline bool operator> (Task const& other) const - { - return _end > other._end; - } - - // Compare tasks with its end - inline bool operator== (Task const& other) - { - return _end == other._end; - } - - // Returns true if the task is in the given group - inline bool IsInGroup(group_t const group) const - { - return _group == group; - } - }; - - typedef std::shared_ptr<Task> TaskContainer; - - /// Container which provides Task order, insert and reschedule operations. - struct Compare - { - bool operator() (TaskContainer const& left, TaskContainer const& right) - { - return (*left.get()) < (*right.get()); - }; - }; - - class TaskQueue - { - std::multiset<TaskContainer, Compare> container; - - public: - // Pushes the task in the container - void Push(TaskContainer&& task); - - /// Pops the task out of the container - TaskContainer Pop(); - - TaskContainer const& First() const; - - void Clear(); - - void RemoveIf(std::function<bool(TaskContainer const&)> const& filter); - - void ModifyIf(std::function<bool(TaskContainer const&)> const& filter); - - bool IsEmpty() const; - }; - - /// Contains a self reference to track if this object was deleted or not. - std::shared_ptr<TaskScheduler> self_reference; - - /// The current time point (now) - timepoint_t _now; - - /// The Task Queue which contains all task objects. - TaskQueue _task_holder; - - typedef std::queue<std::function<void()>> AsyncHolder; - - /// Contains all asynchronous tasks which will be invoked at - /// the next update tick. - AsyncHolder _asyncHolder; - - predicate_t _predicate; - - static bool EmptyValidator() - { - return true; - } - - static void EmptyCallback() - { - } - -public: - TaskScheduler() - : self_reference(this, [](TaskScheduler const*) { }), _now(clock_t::now()), _predicate(EmptyValidator) { } - - template<typename P> - TaskScheduler(P&& predicate) - : self_reference(this, [](TaskScheduler const*) { }), _now(clock_t::now()), _predicate(std::forward<P>(predicate)) { } - - TaskScheduler(TaskScheduler const&) = delete; - TaskScheduler(TaskScheduler&&) = delete; - TaskScheduler& operator= (TaskScheduler const&) = delete; - TaskScheduler& operator= (TaskScheduler&&) = delete; - - /// Sets a validator which is asked if tasks are allowed to be executed. - template<typename P> - TaskScheduler& SetValidator(P&& predicate) - { - _predicate = std::forward<P>(predicate); - return *this; - } - - /// Clears the validator which is asked if tasks are allowed to be executed. - TaskScheduler& ClearValidator(); - - /// Update the scheduler to the current time. - /// Calls the optional callback on successfully finish. - TaskScheduler& Update(success_t const& callback = EmptyCallback); - - /// Update the scheduler with a difftime in ms. - /// Calls the optional callback on successfully finish. - TaskScheduler& Update(size_t const milliseconds, success_t const& callback = EmptyCallback); - - /// Update the scheduler with a difftime. - /// Calls the optional callback on successfully finish. - template<class _Rep, class _Period> - TaskScheduler& Update(std::chrono::duration<_Rep, _Period> const& difftime, - success_t const& callback = EmptyCallback) - { - _now += difftime; - Dispatch(callback); - return *this; - } - - /// Schedule an callable function that is executed at the next update tick. - /// Its safe to modify the TaskScheduler from within the callable. - TaskScheduler& Async(std::function<void()> const& callable); - - /// Schedule an event with a fixed rate. - /// Never call this from within a task context! Use TaskContext::Schedule instead! - template<class _Rep, class _Period> - TaskScheduler& Schedule(std::chrono::duration<_Rep, _Period> const& time, - task_handler_t const& task) - { - return ScheduleAt(_now, time, task); - } - - /// Schedule an event with a fixed rate. - /// Never call this from within a task context! Use TaskContext::Schedule instead! - template<class _Rep, class _Period> - TaskScheduler& Schedule(std::chrono::duration<_Rep, _Period> const& time, - group_t const group, task_handler_t const& task) - { - return ScheduleAt(_now, time, group, task); - } - - /// Schedule an event with a randomized rate between min and max rate. - /// Never call this from within a task context! Use TaskContext::Schedule instead! - template<class _RepLeft, class _PeriodLeft, class _RepRight, class _PeriodRight> - TaskScheduler& Schedule(std::chrono::duration<_RepLeft, _PeriodLeft> const& min, - std::chrono::duration<_RepRight, _PeriodRight> const& max, task_handler_t const& task) - { - return Schedule(RandomDurationBetween(min, max), task); - } - - /// Schedule an event with a fixed rate. - /// Never call this from within a task context! Use TaskContext::Schedule instead! - template<class _RepLeft, class _PeriodLeft, class _RepRight, class _PeriodRight> - TaskScheduler& Schedule(std::chrono::duration<_RepLeft, _PeriodLeft> const& min, - std::chrono::duration<_RepRight, _PeriodRight> const& max, group_t const group, - task_handler_t const& task) - { - return Schedule(RandomDurationBetween(min, max), group, task); - } - - /// Cancels all tasks. - /// Never call this from within a task context! Use TaskContext::CancelAll instead! - TaskScheduler& CancelAll(); - - /// Cancel all tasks of a single group. - /// Never call this from within a task context! Use TaskContext::CancelGroup instead! - TaskScheduler& CancelGroup(group_t const group); - - /// Cancels all groups in the given std::vector. - /// Hint: Use std::initializer_list for this: "{1, 2, 3, 4}" - TaskScheduler& CancelGroupsOf(std::vector<group_t> const& groups); - - /// Delays all tasks with the given duration. - template<class _Rep, class _Period> - TaskScheduler& DelayAll(std::chrono::duration<_Rep, _Period> const& duration) - { - _task_holder.ModifyIf([&duration](TaskContainer const& task) -> bool - { - task->_end += duration; - return true; - }); - return *this; - } - - /// Delays all tasks with a random duration between min and max. - template<class _RepLeft, class _PeriodLeft, class _RepRight, class _PeriodRight> - TaskScheduler& DelayAll(std::chrono::duration<_RepLeft, _PeriodLeft> const& min, - std::chrono::duration<_RepRight, _PeriodRight> const& max) - { - return DelayAll(RandomDurationBetween(min, max)); - } - - /// Delays all tasks of a group with the given duration. - template<class _Rep, class _Period> - TaskScheduler& DelayGroup(group_t const group, std::chrono::duration<_Rep, _Period> const& duration) - { - _task_holder.ModifyIf([&duration, group](TaskContainer const& task) -> bool - { - if (task->IsInGroup(group)) - { - task->_end += duration; - return true; - } - else - return false; - }); - return *this; - } - - /// Delays all tasks of a group with a random duration between min and max. - template<class _RepLeft, class _PeriodLeft, class _RepRight, class _PeriodRight> - TaskScheduler& DelayGroup(group_t const group, - std::chrono::duration<_RepLeft, _PeriodLeft> const& min, - std::chrono::duration<_RepRight, _PeriodRight> const& max) - { - return DelayGroup(group, RandomDurationBetween(min, max)); - } - - /// Reschedule all tasks with a given duration. - template<class _Rep, class _Period> - TaskScheduler& RescheduleAll(std::chrono::duration<_Rep, _Period> const& duration) - { - auto const end = _now + duration; - _task_holder.ModifyIf([end](TaskContainer const& task) -> bool - { - task->_end = end; - return true; - }); - return *this; - } - - /// Reschedule all tasks with a random duration between min and max. - template<class _RepLeft, class _PeriodLeft, class _RepRight, class _PeriodRight> - TaskScheduler& RescheduleAll(std::chrono::duration<_RepLeft, _PeriodLeft> const& min, - std::chrono::duration<_RepRight, _PeriodRight> const& max) - { - return RescheduleAll(RandomDurationBetween(min, max)); - } - - /// Reschedule all tasks of a group with the given duration. - template<class _Rep, class _Period> - TaskScheduler& RescheduleGroup(group_t const group, std::chrono::duration<_Rep, _Period> const& duration) - { - auto const end = _now + duration; - _task_holder.ModifyIf([end, group](TaskContainer const& task) -> bool - { - if (task->IsInGroup(group)) - { - task->_end = end; - return true; - } - else - return false; - }); - return *this; - } - - /// Reschedule all tasks of a group with a random duration between min and max. - template<class _RepLeft, class _PeriodLeft, class _RepRight, class _PeriodRight> - TaskScheduler& RescheduleGroup(group_t const group, - std::chrono::duration<_RepLeft, _PeriodLeft> const& min, - std::chrono::duration<_RepRight, _PeriodRight> const& max) - { - return RescheduleGroup(group, RandomDurationBetween(min, max)); - } - -private: - /// Insert a new task to the enqueued tasks. - TaskScheduler& InsertTask(TaskContainer task); - - template<class _Rep, class _Period> - TaskScheduler& ScheduleAt(timepoint_t const& end, - std::chrono::duration<_Rep, _Period> const& time, task_handler_t const& task) - { - return InsertTask(TaskContainer(new Task(end + time, time, task))); - } - - /// Schedule an event with a fixed rate. - /// Never call this from within a task context! Use TaskContext::schedule instead! - template<class _Rep, class _Period> - TaskScheduler& ScheduleAt(timepoint_t const& end, - std::chrono::duration<_Rep, _Period> const& time, - group_t const group, task_handler_t const& task) - { - static repeated_t const DEFAULT_REPEATED = 0; - return InsertTask(TaskContainer(new Task(end + time, time, group, DEFAULT_REPEATED, task))); - } - - // Returns a random duration between min and max - template<class _RepLeft, class _PeriodLeft, class _RepRight, class _PeriodRight> - static std::chrono::milliseconds - RandomDurationBetween(std::chrono::duration<_RepLeft, _PeriodLeft> const& min, - std::chrono::duration<_RepRight, _PeriodRight> const& max) - { - auto const milli_min = std::chrono::duration_cast<std::chrono::milliseconds>(min); - auto const milli_max = std::chrono::duration_cast<std::chrono::milliseconds>(max); - - // TC specific: use SFMT URandom - return std::chrono::milliseconds(urand(milli_min.count(), milli_max.count())); - } - - /// Dispatch remaining tasks - void Dispatch(success_t const& callback); -}; - -class TaskContext -{ - friend class TaskScheduler; - - /// Associated task - TaskScheduler::TaskContainer _task; - - /// Owner - std::weak_ptr<TaskScheduler> _owner; - - /// Marks the task as consumed - std::shared_ptr<bool> _consumed; - - /// Dispatches an action safe on the TaskScheduler - TaskContext& Dispatch(std::function<TaskScheduler&(TaskScheduler&)> const& apply); - -public: - // Empty constructor - TaskContext() - : _task(), _owner(), _consumed(std::make_shared<bool>(true)) { } - - // Construct from task and owner - explicit TaskContext(TaskScheduler::TaskContainer&& task, std::weak_ptr<TaskScheduler>&& owner) - : _task(task), _owner(owner), _consumed(std::make_shared<bool>(false)) { } - - // Copy construct - TaskContext(TaskContext const& right) - : _task(right._task), _owner(right._owner), _consumed(right._consumed) { } - - // Move construct - TaskContext(TaskContext&& right) - : _task(std::move(right._task)), _owner(std::move(right._owner)), _consumed(std::move(right._consumed)) { } - - // Copy assign - TaskContext& operator= (TaskContext const& right) - { - _task = right._task; - _owner = right._owner; - _consumed = right._consumed; - return *this; - } - - // Move assign - TaskContext& operator= (TaskContext&& right) - { - _task = std::move(right._task); - _owner = std::move(right._owner); - _consumed = std::move(right._consumed); - return *this; - } - - /// Returns true if the owner was deallocated and this context has expired. - bool IsExpired() const; - - /// Returns true if the event is in the given group - bool IsInGroup(TaskScheduler::group_t const group) const; - - /// Sets the event in the given group - TaskContext& SetGroup(TaskScheduler::group_t const group); - - /// Removes the group from the event - TaskContext& ClearGroup(); - - /// Returns the repeat counter which increases every time the task is repeated. - TaskScheduler::repeated_t GetRepeatCounter() const; - - /// Repeats the event and sets a new duration. - /// std::chrono::seconds(5) for example. - /// This will consume the task context, its not possible to repeat the task again - /// from the same task context! - template<class _Rep, class _Period> - TaskContext& Repeat(std::chrono::duration<_Rep, _Period> const& duration) - { - AssertOnConsumed(); - - // Set new duration, in-context timing and increment repeat counter - _task->_duration = duration; - _task->_end += duration; - _task->_repeated += 1; - (*_consumed) = true; - return Dispatch(std::bind(&TaskScheduler::InsertTask, std::placeholders::_1, _task)); - } - - /// Repeats the event with the same duration. - /// This will consume the task context, its not possible to repeat the task again - /// from the same task context! - TaskContext& Repeat() - { - return Repeat(_task->_duration); - } - - /// Repeats the event and set a new duration that is randomized between min and max. - /// std::chrono::seconds(5) for example. - /// This will consume the task context, its not possible to repeat the task again - /// from the same task context! - template<class _RepLeft, class _PeriodLeft, class _RepRight, class _PeriodRight> - TaskContext& Repeat(std::chrono::duration<_RepLeft, _PeriodLeft> const& min, - std::chrono::duration<_RepRight, _PeriodRight> const& max) - { - return Repeat(TaskScheduler::RandomDurationBetween(min, max)); - } - - /// Schedule a callable function that is executed at the next update tick from within the context. - /// Its safe to modify the TaskScheduler from within the callable. - TaskContext& Async(std::function<void()> const& callable); - - /// Schedule an event with a fixed rate from within the context. - /// Its possible that the new event is executed immediately! - /// Use TaskScheduler::Async to create a task - /// which will be called at the next update tick. - template<class _Rep, class _Period> - TaskContext& Schedule(std::chrono::duration<_Rep, _Period> const& time, - TaskScheduler::task_handler_t const& task) - { - auto const end = _task->_end; - return Dispatch([end, time, task](TaskScheduler& scheduler) -> TaskScheduler& - { - return scheduler.ScheduleAt<_Rep, _Period>(end, time, task); - }); - } - - /// Schedule an event with a fixed rate from within the context. - /// Its possible that the new event is executed immediately! - /// Use TaskScheduler::Async to create a task - /// which will be called at the next update tick. - template<class _Rep, class _Period> - TaskContext& Schedule(std::chrono::duration<_Rep, _Period> const& time, - TaskScheduler::group_t const group, TaskScheduler::task_handler_t const& task) - { - auto const end = _task->_end; - return Dispatch([end, time, group, task](TaskScheduler& scheduler) -> TaskScheduler& - { - return scheduler.ScheduleAt<_Rep, _Period>(end, time, group, task); - }); - } - - /// Schedule an event with a randomized rate between min and max rate from within the context. - /// Its possible that the new event is executed immediately! - /// Use TaskScheduler::Async to create a task - /// which will be called at the next update tick. - template<class _RepLeft, class _PeriodLeft, class _RepRight, class _PeriodRight> - TaskContext& Schedule(std::chrono::duration<_RepLeft, _PeriodLeft> const& min, - std::chrono::duration<_RepRight, _PeriodRight> const& max, TaskScheduler::task_handler_t const& task) - { - return Schedule(TaskScheduler::RandomDurationBetween(min, max), task); - } - - /// Schedule an event with a randomized rate between min and max rate from within the context. - /// Its possible that the new event is executed immediately! - /// Use TaskScheduler::Async to create a task - /// which will be called at the next update tick. - template<class _RepLeft, class _PeriodLeft, class _RepRight, class _PeriodRight> - TaskContext& Schedule(std::chrono::duration<_RepLeft, _PeriodLeft> const& min, - std::chrono::duration<_RepRight, _PeriodRight> const& max, TaskScheduler::group_t const group, - TaskScheduler::task_handler_t const& task) - { - return Schedule(TaskScheduler::RandomDurationBetween(min, max), group, task); - } - - /// Cancels all tasks from within the context. - TaskContext& CancelAll(); - - /// Cancel all tasks of a single group from within the context. - TaskContext& CancelGroup(TaskScheduler::group_t const group); - - /// Cancels all groups in the given std::vector from within the context. - /// Hint: Use std::initializer_list for this: "{1, 2, 3, 4}" - TaskContext& CancelGroupsOf(std::vector<TaskScheduler::group_t> const& groups); - - /// Delays all tasks with the given duration from within the context. - template<class _Rep, class _Period> - TaskContext& DelayAll(std::chrono::duration<_Rep, _Period> const& duration) - { - return Dispatch(std::bind(&TaskScheduler::DelayAll<_Rep, _Period>, std::placeholders::_1, duration)); - } - - /// Delays all tasks with a random duration between min and max from within the context. - template<class _RepLeft, class _PeriodLeft, class _RepRight, class _PeriodRight> - TaskContext& DelayAll(std::chrono::duration<_RepLeft, _PeriodLeft> const& min, - std::chrono::duration<_RepRight, _PeriodRight> const& max) - { - return DelayAll(TaskScheduler::RandomDurationBetween(min, max)); - } - - /// Delays all tasks of a group with the given duration from within the context. - template<class _Rep, class _Period> - TaskContext& DelayGroup(TaskScheduler::group_t const group, std::chrono::duration<_Rep, _Period> const& duration) - { - return Dispatch(std::bind(&TaskScheduler::DelayGroup<_Rep, _Period>, std::placeholders::_1, group, duration)); - } - - /// Delays all tasks of a group with a random duration between min and max from within the context. - template<class _RepLeft, class _PeriodLeft, class _RepRight, class _PeriodRight> - TaskContext& DelayGroup(TaskScheduler::group_t const group, - std::chrono::duration<_RepLeft, _PeriodLeft> const& min, - std::chrono::duration<_RepRight, _PeriodRight> const& max) - { - return DelayGroup(group, TaskScheduler::RandomDurationBetween(min, max)); - } - - /// Reschedule all tasks with the given duration. - template<class _Rep, class _Period> - TaskContext& RescheduleAll(std::chrono::duration<_Rep, _Period> const& duration) - { - return Dispatch(std::bind(&TaskScheduler::RescheduleAll, std::placeholders::_1, duration)); - } - - /// Reschedule all tasks with a random duration between min and max. - template<class _RepLeft, class _PeriodLeft, class _RepRight, class _PeriodRight> - TaskContext& RescheduleAll(std::chrono::duration<_RepLeft, _PeriodLeft> const& min, - std::chrono::duration<_RepRight, _PeriodRight> const& max) - { - return RescheduleAll(TaskScheduler::RandomDurationBetween(min, max)); - } - - /// Reschedule all tasks of a group with the given duration. - template<class _Rep, class _Period> - TaskContext& RescheduleGroup(TaskScheduler::group_t const group, std::chrono::duration<_Rep, _Period> const& duration) - { - return Dispatch(std::bind(&TaskScheduler::RescheduleGroup<_Rep, _Period>, std::placeholders::_1, group, duration)); - } - - /// Reschedule all tasks of a group with a random duration between min and max. - template<class _RepLeft, class _PeriodLeft, class _RepRight, class _PeriodRight> - TaskContext& RescheduleGroup(TaskScheduler::group_t const group, - std::chrono::duration<_RepLeft, _PeriodLeft> const& min, - std::chrono::duration<_RepRight, _PeriodRight> const& max) - { - return RescheduleGroup(group, TaskScheduler::RandomDurationBetween(min, max)); - } - -private: - /// Asserts if the task was consumed already. - void AssertOnConsumed() const; - - /// Invokes the associated hook of the task. - void Invoke(); -}; - -#endif /// _TASK_SCHEDULER_H_ diff --git a/src/server/shared/Utilities/Timer.h b/src/server/shared/Utilities/Timer.h deleted file mode 100644 index c54903d7be2..00000000000 --- a/src/server/shared/Utilities/Timer.h +++ /dev/null @@ -1,203 +0,0 @@ -/* - * Copyright (C) 2008-2015 TrinityCore <http://www.trinitycore.org/> - * Copyright (C) 2005-2009 MaNGOS <http://getmangos.com/> - * - * This program is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License as published by the - * Free Software Foundation; either version 2 of the License, or (at your - * option) any later version. - * - * This program is distributed in the hope that it will be useful, but WITHOUT - * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for - * more details. - * - * You should have received a copy of the GNU General Public License along - * with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef TRINITY_TIMER_H -#define TRINITY_TIMER_H - -#include <chrono> - -inline uint32 getMSTime() -{ - using namespace std::chrono; - - static const system_clock::time_point ApplicationStartTime = system_clock::now(); - - return uint32(duration_cast<milliseconds>(system_clock::now() - ApplicationStartTime).count()); -} - -inline uint32 getMSTimeDiff(uint32 oldMSTime, uint32 newMSTime) -{ - // getMSTime() have limited data range and this is case when it overflow in this tick - if (oldMSTime > newMSTime) - return (0xFFFFFFFF - oldMSTime) + newMSTime; - else - return newMSTime - oldMSTime; -} - -inline uint32 GetMSTimeDiffToNow(uint32 oldMSTime) -{ - return getMSTimeDiff(oldMSTime, getMSTime()); -} - -struct IntervalTimer -{ -public: - - IntervalTimer() - : _interval(0), _current(0) - { - } - - void Update(time_t diff) - { - _current += diff; - if (_current < 0) - _current = 0; - } - - bool Passed() - { - return _current >= _interval; - } - - void Reset() - { - if (_current >= _interval) - _current %= _interval; - } - - void SetCurrent(time_t current) - { - _current = current; - } - - void SetInterval(time_t interval) - { - _interval = interval; - } - - time_t GetInterval() const - { - return _interval; - } - - time_t GetCurrent() const - { - return _current; - } - -private: - - time_t _interval; - time_t _current; -}; - -struct TimeTracker -{ -public: - - TimeTracker(time_t expiry) - : i_expiryTime(expiry) - { - } - - void Update(time_t diff) - { - i_expiryTime -= diff; - } - - bool Passed() const - { - return i_expiryTime <= 0; - } - - void Reset(time_t interval) - { - i_expiryTime = interval; - } - - time_t GetExpiry() const - { - return i_expiryTime; - } - -private: - - time_t i_expiryTime; -}; - -struct TimeTrackerSmall -{ -public: - - TimeTrackerSmall(uint32 expiry = 0) - : i_expiryTime(expiry) - { - } - - void Update(int32 diff) - { - i_expiryTime -= diff; - } - - bool Passed() const - { - return i_expiryTime <= 0; - } - - void Reset(uint32 interval) - { - i_expiryTime = interval; - } - - int32 GetExpiry() const - { - return i_expiryTime; - } - -private: - - int32 i_expiryTime; -}; - -struct PeriodicTimer -{ -public: - - PeriodicTimer(int32 period, int32 start_time) - : i_period(period), i_expireTime(start_time) - { - } - - bool Update(const uint32 diff) - { - if ((i_expireTime -= diff) > 0) - return false; - - i_expireTime += i_period > int32(diff) ? i_period : diff; - return true; - } - - void SetPeriodic(int32 period, int32 start_time) - { - i_expireTime = start_time; - i_period = period; - } - - // Tracker interface - void TUpdate(int32 diff) { i_expireTime -= diff; } - bool TPassed() const { return i_expireTime <= 0; } - void TReset(int32 diff, int32 period) { i_expireTime += period > diff ? period : diff; } - -private: - - int32 i_period; - int32 i_expireTime; -}; - -#endif diff --git a/src/server/shared/Utilities/Util.cpp b/src/server/shared/Utilities/Util.cpp deleted file mode 100644 index 33c273fb05f..00000000000 --- a/src/server/shared/Utilities/Util.cpp +++ /dev/null @@ -1,562 +0,0 @@ -/* - * Copyright (C) 2008-2015 TrinityCore <http://www.trinitycore.org/> - * Copyright (C) 2005-2009 MaNGOS <http://getmangos.com/> - * - * This program is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License as published by the - * Free Software Foundation; either version 2 of the License, or (at your - * option) any later version. - * - * This program is distributed in the hope that it will be useful, but WITHOUT - * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for - * more details. - * - * You should have received a copy of the GNU General Public License along - * with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#include "Util.h" -#include "Common.h" -#include "CompilerDefs.h" -#include "utf8.h" -#include "SFMT.h" -#include "Errors.h" // for ASSERT -#include <stdarg.h> -#include <boost/thread/tss.hpp> - -#if COMPILER == COMPILER_GNU - #include <sys/socket.h> - #include <netinet/in.h> - #include <arpa/inet.h> -#endif - -static boost::thread_specific_ptr<SFMTRand> sfmtRand; - -static SFMTRand* GetRng() -{ - SFMTRand* rand = sfmtRand.get(); - - if (!rand) - { - rand = new SFMTRand(); - sfmtRand.reset(rand); - } - - return rand; -} - -int32 irand(int32 min, int32 max) -{ - ASSERT(max >= min); - return int32(GetRng()->IRandom(min, max)); -} - -uint32 urand(uint32 min, uint32 max) -{ - ASSERT(max >= min); - return GetRng()->URandom(min, max); -} - -float frand(float min, float max) -{ - ASSERT(max >= min); - return float(GetRng()->Random() * (max - min) + min); -} - -uint32 rand32() -{ - return GetRng()->BRandom(); -} - -double rand_norm() -{ - return GetRng()->Random(); -} - -double rand_chance() -{ - return GetRng()->Random() * 100.0; -} - -Tokenizer::Tokenizer(const std::string &src, const char sep, uint32 vectorReserve) -{ - m_str = new char[src.length() + 1]; - memcpy(m_str, src.c_str(), src.length() + 1); - - if (vectorReserve) - m_storage.reserve(vectorReserve); - - char* posold = m_str; - char* posnew = m_str; - - for (;;) - { - if (*posnew == sep) - { - m_storage.push_back(posold); - posold = posnew + 1; - - *posnew = '\0'; - } - else if (*posnew == '\0') - { - // Hack like, but the old code accepted these kind of broken strings, - // so changing it would break other things - if (posold != posnew) - m_storage.push_back(posold); - - break; - } - - ++posnew; - } -} - -void stripLineInvisibleChars(std::string &str) -{ - static std::string const invChars = " \t\7\n"; - - size_t wpos = 0; - - bool space = false; - for (size_t pos = 0; pos < str.size(); ++pos) - { - if (invChars.find(str[pos])!=std::string::npos) - { - if (!space) - { - str[wpos++] = ' '; - space = true; - } - } - else - { - if (wpos!=pos) - str[wpos++] = str[pos]; - else - ++wpos; - space = false; - } - } - - if (wpos < str.size()) - str.erase(wpos, str.size()); - if (str.find("|TInterface")!=std::string::npos) - str.clear(); - -} - -#if (defined(WIN32) || defined(_WIN32) || defined(__WIN32__)) -struct tm* localtime_r(const time_t* time, struct tm *result) -{ - localtime_s(result, time); - return result; -} -#endif - -std::string secsToTimeString(uint64 timeInSecs, bool shortText, bool hoursOnly) -{ - uint64 secs = timeInSecs % MINUTE; - uint64 minutes = timeInSecs % HOUR / MINUTE; - uint64 hours = timeInSecs % DAY / HOUR; - uint64 days = timeInSecs / DAY; - - std::ostringstream ss; - if (days) - ss << days << (shortText ? "d" : " Day(s) "); - if (hours || hoursOnly) - ss << hours << (shortText ? "h" : " Hour(s) "); - if (!hoursOnly) - { - if (minutes) - ss << minutes << (shortText ? "m" : " Minute(s) "); - if (secs || (!days && !hours && !minutes) ) - ss << secs << (shortText ? "s" : " Second(s)."); - } - - return ss.str(); -} - -int32 MoneyStringToMoney(const std::string& moneyString) -{ - int32 money = 0; - - if (!(std::count(moneyString.begin(), moneyString.end(), 'g') == 1 || - std::count(moneyString.begin(), moneyString.end(), 's') == 1 || - std::count(moneyString.begin(), moneyString.end(), 'c') == 1)) - return 0; // Bad format - - Tokenizer tokens(moneyString, ' '); - for (Tokenizer::const_iterator itr = tokens.begin(); itr != tokens.end(); ++itr) - { - std::string tokenString(*itr); - size_t gCount = std::count(tokenString.begin(), tokenString.end(), 'g'); - size_t sCount = std::count(tokenString.begin(), tokenString.end(), 's'); - size_t cCount = std::count(tokenString.begin(), tokenString.end(), 'c'); - if (gCount + sCount + cCount != 1) - return 0; - - uint32 amount = atoi(*itr); - if (gCount == 1) - money += amount * 100 * 100; - else if (sCount == 1) - money += amount * 100; - else if (cCount == 1) - money += amount; - } - - return money; -} - -uint32 TimeStringToSecs(const std::string& timestring) -{ - uint32 secs = 0; - uint32 buffer = 0; - uint32 multiplier = 0; - - for (std::string::const_iterator itr = timestring.begin(); itr != timestring.end(); ++itr) - { - if (isdigit(*itr)) - { - buffer*=10; - buffer+= (*itr)-'0'; - } - else - { - switch (*itr) - { - case 'd': multiplier = DAY; break; - case 'h': multiplier = HOUR; break; - case 'm': multiplier = MINUTE; break; - case 's': multiplier = 1; break; - default : return 0; //bad format - } - buffer*=multiplier; - secs+=buffer; - buffer=0; - } - } - - return secs; -} - -std::string TimeToTimestampStr(time_t t) -{ - tm aTm; - localtime_r(&t, &aTm); - // YYYY year - // MM month (2 digits 01-12) - // DD day (2 digits 01-31) - // HH hour (2 digits 00-23) - // MM minutes (2 digits 00-59) - // SS seconds (2 digits 00-59) - char buf[20]; - snprintf(buf, 20, "%04d-%02d-%02d_%02d-%02d-%02d", aTm.tm_year+1900, aTm.tm_mon+1, aTm.tm_mday, aTm.tm_hour, aTm.tm_min, aTm.tm_sec); - return std::string(buf); -} - -/// Check if the string is a valid ip address representation -bool IsIPAddress(char const* ipaddress) -{ - if (!ipaddress) - return false; - - // Let the big boys do it. - // Drawback: all valid ip address formats are recognized e.g.: 12.23, 121234, 0xABCD) - return inet_addr(ipaddress) != INADDR_NONE; -} - -/// create PID file -uint32 CreatePIDFile(const std::string& filename) -{ - FILE* pid_file = fopen (filename.c_str(), "w" ); - if (pid_file == NULL) - return 0; - -#ifdef _WIN32 - DWORD pid = GetCurrentProcessId(); -#else - pid_t pid = getpid(); -#endif - - fprintf(pid_file, "%u", pid ); - fclose(pid_file); - - return (uint32)pid; -} - -size_t utf8length(std::string& utf8str) -{ - try - { - return utf8::distance(utf8str.c_str(), utf8str.c_str()+utf8str.size()); - } - catch(std::exception) - { - utf8str.clear(); - return 0; - } -} - -void utf8truncate(std::string& utf8str, size_t len) -{ - try - { - size_t wlen = utf8::distance(utf8str.c_str(), utf8str.c_str()+utf8str.size()); - if (wlen <= len) - return; - - std::wstring wstr; - wstr.resize(wlen); - utf8::utf8to16(utf8str.c_str(), utf8str.c_str()+utf8str.size(), &wstr[0]); - wstr.resize(len); - char* oend = utf8::utf16to8(wstr.c_str(), wstr.c_str()+wstr.size(), &utf8str[0]); - utf8str.resize(oend-(&utf8str[0])); // remove unused tail - } - catch(std::exception) - { - utf8str.clear(); - } -} - -bool Utf8toWStr(char const* utf8str, size_t csize, wchar_t* wstr, size_t& wsize) -{ - try - { - size_t len = utf8::distance(utf8str, utf8str+csize); - if (len > wsize) - { - if (wsize > 0) - wstr[0] = L'\0'; - wsize = 0; - return false; - } - - wsize = len; - utf8::utf8to16(utf8str, utf8str+csize, wstr); - wstr[len] = L'\0'; - } - catch(std::exception) - { - if (wsize > 0) - wstr[0] = L'\0'; - wsize = 0; - return false; - } - - return true; -} - -bool Utf8toWStr(const std::string& utf8str, std::wstring& wstr) -{ - try - { - if (size_t len = utf8::distance(utf8str.c_str(), utf8str.c_str()+utf8str.size())) - { - wstr.resize(len); - utf8::utf8to16(utf8str.c_str(), utf8str.c_str()+utf8str.size(), &wstr[0]); - } - } - catch(std::exception) - { - wstr.clear(); - return false; - } - - return true; -} - -bool WStrToUtf8(wchar_t* wstr, size_t size, std::string& utf8str) -{ - try - { - std::string utf8str2; - utf8str2.resize(size*4); // allocate for most long case - - if (size) - { - char* oend = utf8::utf16to8(wstr, wstr+size, &utf8str2[0]); - utf8str2.resize(oend-(&utf8str2[0])); // remove unused tail - } - utf8str = utf8str2; - } - catch(std::exception) - { - utf8str.clear(); - return false; - } - - return true; -} - -bool WStrToUtf8(std::wstring const& wstr, std::string& utf8str) -{ - try - { - std::string utf8str2; - utf8str2.resize(wstr.size()*4); // allocate for most long case - - if (wstr.size()) - { - char* oend = utf8::utf16to8(wstr.c_str(), wstr.c_str()+wstr.size(), &utf8str2[0]); - utf8str2.resize(oend-(&utf8str2[0])); // remove unused tail - } - utf8str = utf8str2; - } - catch(std::exception) - { - utf8str.clear(); - return false; - } - - return true; -} - -typedef wchar_t const* const* wstrlist; - -std::wstring GetMainPartOfName(std::wstring const& wname, uint32 declension) -{ - // supported only Cyrillic cases - if (wname.size() < 1 || !isCyrillicCharacter(wname[0]) || declension > 5) - return wname; - - // Important: end length must be <= MAX_INTERNAL_PLAYER_NAME-MAX_PLAYER_NAME (3 currently) - - static wchar_t const a_End[] = { wchar_t(1), wchar_t(0x0430), wchar_t(0x0000)}; - static wchar_t const o_End[] = { wchar_t(1), wchar_t(0x043E), wchar_t(0x0000)}; - static wchar_t const ya_End[] = { wchar_t(1), wchar_t(0x044F), wchar_t(0x0000)}; - static wchar_t const ie_End[] = { wchar_t(1), wchar_t(0x0435), wchar_t(0x0000)}; - static wchar_t const i_End[] = { wchar_t(1), wchar_t(0x0438), wchar_t(0x0000)}; - static wchar_t const yeru_End[] = { wchar_t(1), wchar_t(0x044B), wchar_t(0x0000)}; - static wchar_t const u_End[] = { wchar_t(1), wchar_t(0x0443), wchar_t(0x0000)}; - static wchar_t const yu_End[] = { wchar_t(1), wchar_t(0x044E), wchar_t(0x0000)}; - static wchar_t const oj_End[] = { wchar_t(2), wchar_t(0x043E), wchar_t(0x0439), wchar_t(0x0000)}; - static wchar_t const ie_j_End[] = { wchar_t(2), wchar_t(0x0435), wchar_t(0x0439), wchar_t(0x0000)}; - static wchar_t const io_j_End[] = { wchar_t(2), wchar_t(0x0451), wchar_t(0x0439), wchar_t(0x0000)}; - static wchar_t const o_m_End[] = { wchar_t(2), wchar_t(0x043E), wchar_t(0x043C), wchar_t(0x0000)}; - static wchar_t const io_m_End[] = { wchar_t(2), wchar_t(0x0451), wchar_t(0x043C), wchar_t(0x0000)}; - static wchar_t const ie_m_End[] = { wchar_t(2), wchar_t(0x0435), wchar_t(0x043C), wchar_t(0x0000)}; - static wchar_t const soft_End[] = { wchar_t(1), wchar_t(0x044C), wchar_t(0x0000)}; - static wchar_t const j_End[] = { wchar_t(1), wchar_t(0x0439), wchar_t(0x0000)}; - - static wchar_t const* const dropEnds[6][8] = { - { &a_End[1], &o_End[1], &ya_End[1], &ie_End[1], &soft_End[1], &j_End[1], NULL, NULL }, - { &a_End[1], &ya_End[1], &yeru_End[1], &i_End[1], NULL, NULL, NULL, NULL }, - { &ie_End[1], &u_End[1], &yu_End[1], &i_End[1], NULL, NULL, NULL, NULL }, - { &u_End[1], &yu_End[1], &o_End[1], &ie_End[1], &soft_End[1], &ya_End[1], &a_End[1], NULL }, - { &oj_End[1], &io_j_End[1], &ie_j_End[1], &o_m_End[1], &io_m_End[1], &ie_m_End[1], &yu_End[1], NULL }, - { &ie_End[1], &i_End[1], NULL, NULL, NULL, NULL, NULL, NULL } - }; - - for (wchar_t const* const* itr = &dropEnds[declension][0]; *itr; ++itr) - { - size_t len = size_t((*itr)[-1]); // get length from string size field - - if (wname.substr(wname.size()-len, len)==*itr) - return wname.substr(0, wname.size()-len); - } - - return wname; -} - -bool utf8ToConsole(const std::string& utf8str, std::string& conStr) -{ -#if PLATFORM == PLATFORM_WINDOWS - std::wstring wstr; - if (!Utf8toWStr(utf8str, wstr)) - return false; - - conStr.resize(wstr.size()); - CharToOemBuffW(&wstr[0], &conStr[0], wstr.size()); -#else - // not implemented yet - conStr = utf8str; -#endif - - return true; -} - -bool consoleToUtf8(const std::string& conStr, std::string& utf8str) -{ -#if PLATFORM == PLATFORM_WINDOWS - std::wstring wstr; - wstr.resize(conStr.size()); - OemToCharBuffW(&conStr[0], &wstr[0], conStr.size()); - - return WStrToUtf8(wstr, utf8str); -#else - // not implemented yet - utf8str = conStr; - return true; -#endif -} - -bool Utf8FitTo(const std::string& str, std::wstring const& search) -{ - std::wstring temp; - - if (!Utf8toWStr(str, temp)) - return false; - - // converting to lower case - wstrToLower( temp ); - - if (temp.find(search) == std::wstring::npos) - return false; - - return true; -} - -void utf8printf(FILE* out, const char *str, ...) -{ - va_list ap; - va_start(ap, str); - vutf8printf(out, str, &ap); - va_end(ap); -} - -void vutf8printf(FILE* out, const char *str, va_list* ap) -{ -#if PLATFORM == PLATFORM_WINDOWS - char temp_buf[32*1024]; - wchar_t wtemp_buf[32*1024]; - - size_t temp_len = vsnprintf(temp_buf, 32*1024, str, *ap); - //vsnprintf returns -1 if the buffer is too small - if (temp_len == size_t(-1)) - temp_len = 32*1024-1; - - size_t wtemp_len = 32*1024-1; - Utf8toWStr(temp_buf, temp_len, wtemp_buf, wtemp_len); - - CharToOemBuffW(&wtemp_buf[0], &temp_buf[0], wtemp_len+1); - fprintf(out, "%s", temp_buf); -#else - vfprintf(out, str, *ap); -#endif -} - -std::string ByteArrayToHexStr(uint8 const* bytes, uint32 arrayLen, bool reverse /* = false */) -{ - int32 init = 0; - int32 end = arrayLen; - int8 op = 1; - - if (reverse) - { - init = arrayLen - 1; - end = -1; - op = -1; - } - - std::ostringstream ss; - for (int32 i = init; i != end; i += op) - { - char buffer[4]; - sprintf(buffer, "%02X", bytes[i]); - ss << buffer; - } - - return ss.str(); -} diff --git a/src/server/shared/Utilities/Util.h b/src/server/shared/Utilities/Util.h deleted file mode 100644 index 3da1c800410..00000000000 --- a/src/server/shared/Utilities/Util.h +++ /dev/null @@ -1,545 +0,0 @@ -/* - * Copyright (C) 2008-2015 TrinityCore <http://www.trinitycore.org/> - * Copyright (C) 2005-2009 MaNGOS <http://getmangos.com/> - * - * This program is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License as published by the - * Free Software Foundation; either version 2 of the License, or (at your - * option) any later version. - * - * This program is distributed in the hope that it will be useful, but WITHOUT - * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for - * more details. - * - * You should have received a copy of the GNU General Public License along - * with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef _UTIL_H -#define _UTIL_H - -#include "Define.h" -#include "Errors.h" - -#include <algorithm> -#include <string> -#include <vector> -#include <list> -#include <map> - -// Searcher for map of structs -template<typename T, class S> struct Finder -{ - T val_; - T S::* idMember_; - - Finder(T val, T S::* idMember) : val_(val), idMember_(idMember) {} - bool operator()(const std::pair<int, S> &obj) { return obj.second.*idMember_ == val_; } -}; - -class Tokenizer -{ -public: - typedef std::vector<char const*> StorageType; - - typedef StorageType::size_type size_type; - - typedef StorageType::const_iterator const_iterator; - typedef StorageType::reference reference; - typedef StorageType::const_reference const_reference; - -public: - Tokenizer(const std::string &src, char const sep, uint32 vectorReserve = 0); - ~Tokenizer() { delete[] m_str; } - - const_iterator begin() const { return m_storage.begin(); } - const_iterator end() const { return m_storage.end(); } - - size_type size() const { return m_storage.size(); } - - reference operator [] (size_type i) { return m_storage[i]; } - const_reference operator [] (size_type i) const { return m_storage[i]; } - -private: - char* m_str; - StorageType m_storage; -}; - -void stripLineInvisibleChars(std::string &src); - -int32 MoneyStringToMoney(const std::string& moneyString); - -struct tm* localtime_r(const time_t* time, struct tm *result); - -std::string secsToTimeString(uint64 timeInSecs, bool shortText = false, bool hoursOnly = false); -uint32 TimeStringToSecs(const std::string& timestring); -std::string TimeToTimestampStr(time_t t); - -/* Return a random number in the range min..max. */ -int32 irand(int32 min, int32 max); - -/* Return a random number in the range min..max (inclusive). */ -uint32 urand(uint32 min, uint32 max); - -/* Return a random number in the range 0 .. UINT32_MAX. */ -uint32 rand32(); - -/* Return a random number in the range min..max */ -float frand(float min, float max); - -/* Return a random double from 0.0 to 1.0 (exclusive). */ -double rand_norm(); - -/* Return a random double from 0.0 to 100.0 (exclusive). */ -double rand_chance(); - -/* Return true if a random roll fits in the specified chance (range 0-100). */ -inline bool roll_chance_f(float chance) -{ - return chance > rand_chance(); -} - -/* Return true if a random roll fits in the specified chance (range 0-100). */ -inline bool roll_chance_i(int chance) -{ - return chance > irand(0, 99); -} - -inline void ApplyPercentModFloatVar(float& var, float val, bool apply) -{ - if (val == -100.0f) // prevent set var to zero - val = -99.99f; - var *= (apply ? (100.0f + val) / 100.0f : 100.0f / (100.0f + val)); -} - -// Percentage calculation -template <class T, class U> -inline T CalculatePct(T base, U pct) -{ - return T(base * static_cast<float>(pct) / 100.0f); -} - -template <class T, class U> -inline T AddPct(T &base, U pct) -{ - return base += CalculatePct(base, pct); -} - -template <class T, class U> -inline T ApplyPct(T &base, U pct) -{ - return base = CalculatePct(base, pct); -} - -template <class T> -inline T RoundToInterval(T& num, T floor, T ceil) -{ - return num = std::min(std::max(num, floor), ceil); -} - -// UTF8 handling -bool Utf8toWStr(const std::string& utf8str, std::wstring& wstr); -// in wsize==max size of buffer, out wsize==real string size -bool Utf8toWStr(char const* utf8str, size_t csize, wchar_t* wstr, size_t& wsize); -inline bool Utf8toWStr(const std::string& utf8str, wchar_t* wstr, size_t& wsize) -{ - return Utf8toWStr(utf8str.c_str(), utf8str.size(), wstr, wsize); -} - -bool WStrToUtf8(std::wstring const& wstr, std::string& utf8str); -// size==real string size -bool WStrToUtf8(wchar_t* wstr, size_t size, std::string& utf8str); - -size_t utf8length(std::string& utf8str); // set string to "" if invalid utf8 sequence -void utf8truncate(std::string& utf8str, size_t len); - -inline bool isBasicLatinCharacter(wchar_t wchar) -{ - if (wchar >= L'a' && wchar <= L'z') // LATIN SMALL LETTER A - LATIN SMALL LETTER Z - return true; - if (wchar >= L'A' && wchar <= L'Z') // LATIN CAPITAL LETTER A - LATIN CAPITAL LETTER Z - return true; - return false; -} - -inline bool isExtendedLatinCharacter(wchar_t wchar) -{ - if (isBasicLatinCharacter(wchar)) - return true; - if (wchar >= 0x00C0 && wchar <= 0x00D6) // LATIN CAPITAL LETTER A WITH GRAVE - LATIN CAPITAL LETTER O WITH DIAERESIS - return true; - if (wchar >= 0x00D8 && wchar <= 0x00DE) // LATIN CAPITAL LETTER O WITH STROKE - LATIN CAPITAL LETTER THORN - return true; - if (wchar == 0x00DF) // LATIN SMALL LETTER SHARP S - return true; - if (wchar >= 0x00E0 && wchar <= 0x00F6) // LATIN SMALL LETTER A WITH GRAVE - LATIN SMALL LETTER O WITH DIAERESIS - return true; - if (wchar >= 0x00F8 && wchar <= 0x00FE) // LATIN SMALL LETTER O WITH STROKE - LATIN SMALL LETTER THORN - return true; - if (wchar >= 0x0100 && wchar <= 0x012F) // LATIN CAPITAL LETTER A WITH MACRON - LATIN SMALL LETTER I WITH OGONEK - return true; - if (wchar == 0x1E9E) // LATIN CAPITAL LETTER SHARP S - return true; - return false; -} - -inline bool isCyrillicCharacter(wchar_t wchar) -{ - if (wchar >= 0x0410 && wchar <= 0x044F) // CYRILLIC CAPITAL LETTER A - CYRILLIC SMALL LETTER YA - return true; - if (wchar == 0x0401 || wchar == 0x0451) // CYRILLIC CAPITAL LETTER IO, CYRILLIC SMALL LETTER IO - return true; - return false; -} - -inline bool isEastAsianCharacter(wchar_t wchar) -{ - if (wchar >= 0x1100 && wchar <= 0x11F9) // Hangul Jamo - return true; - if (wchar >= 0x3041 && wchar <= 0x30FF) // Hiragana + Katakana - return true; - if (wchar >= 0x3131 && wchar <= 0x318E) // Hangul Compatibility Jamo - return true; - if (wchar >= 0x31F0 && wchar <= 0x31FF) // Katakana Phonetic Ext. - return true; - if (wchar >= 0x3400 && wchar <= 0x4DB5) // CJK Ideographs Ext. A - return true; - if (wchar >= 0x4E00 && wchar <= 0x9FC3) // Unified CJK Ideographs - return true; - if (wchar >= 0xAC00 && wchar <= 0xD7A3) // Hangul Syllables - return true; - if (wchar >= 0xFF01 && wchar <= 0xFFEE) // Halfwidth forms - return true; - return false; -} - -inline bool isNumeric(wchar_t wchar) -{ - return (wchar >= L'0' && wchar <=L'9'); -} - -inline bool isNumeric(char c) -{ - return (c >= '0' && c <='9'); -} - -inline bool isNumeric(char const* str) -{ - for (char const* c = str; *c; ++c) - if (!isNumeric(*c)) - return false; - - return true; -} - -inline bool isNumericOrSpace(wchar_t wchar) -{ - return isNumeric(wchar) || wchar == L' '; -} - -inline bool isBasicLatinString(const std::wstring &wstr, bool numericOrSpace) -{ - for (size_t i = 0; i < wstr.size(); ++i) - if (!isBasicLatinCharacter(wstr[i]) && (!numericOrSpace || !isNumericOrSpace(wstr[i]))) - return false; - return true; -} - -inline bool isExtendedLatinString(const std::wstring &wstr, bool numericOrSpace) -{ - for (size_t i = 0; i < wstr.size(); ++i) - if (!isExtendedLatinCharacter(wstr[i]) && (!numericOrSpace || !isNumericOrSpace(wstr[i]))) - return false; - return true; -} - -inline bool isCyrillicString(const std::wstring &wstr, bool numericOrSpace) -{ - for (size_t i = 0; i < wstr.size(); ++i) - if (!isCyrillicCharacter(wstr[i]) && (!numericOrSpace || !isNumericOrSpace(wstr[i]))) - return false; - return true; -} - -inline bool isEastAsianString(const std::wstring &wstr, bool numericOrSpace) -{ - for (size_t i = 0; i < wstr.size(); ++i) - if (!isEastAsianCharacter(wstr[i]) && (!numericOrSpace || !isNumericOrSpace(wstr[i]))) - return false; - return true; -} - -inline wchar_t wcharToUpper(wchar_t wchar) -{ - if (wchar >= L'a' && wchar <= L'z') // LATIN SMALL LETTER A - LATIN SMALL LETTER Z - return wchar_t(uint16(wchar)-0x0020); - if (wchar == 0x00DF) // LATIN SMALL LETTER SHARP S - return wchar_t(0x1E9E); - if (wchar >= 0x00E0 && wchar <= 0x00F6) // LATIN SMALL LETTER A WITH GRAVE - LATIN SMALL LETTER O WITH DIAERESIS - return wchar_t(uint16(wchar)-0x0020); - if (wchar >= 0x00F8 && wchar <= 0x00FE) // LATIN SMALL LETTER O WITH STROKE - LATIN SMALL LETTER THORN - return wchar_t(uint16(wchar)-0x0020); - if (wchar >= 0x0101 && wchar <= 0x012F) // LATIN SMALL LETTER A WITH MACRON - LATIN SMALL LETTER I WITH OGONEK (only %2=1) - { - if (wchar % 2 == 1) - return wchar_t(uint16(wchar)-0x0001); - } - if (wchar >= 0x0430 && wchar <= 0x044F) // CYRILLIC SMALL LETTER A - CYRILLIC SMALL LETTER YA - return wchar_t(uint16(wchar)-0x0020); - if (wchar == 0x0451) // CYRILLIC SMALL LETTER IO - return wchar_t(0x0401); - - return wchar; -} - -inline wchar_t wcharToUpperOnlyLatin(wchar_t wchar) -{ - return isBasicLatinCharacter(wchar) ? wcharToUpper(wchar) : wchar; -} - -inline wchar_t wcharToLower(wchar_t wchar) -{ - if (wchar >= L'A' && wchar <= L'Z') // LATIN CAPITAL LETTER A - LATIN CAPITAL LETTER Z - return wchar_t(uint16(wchar)+0x0020); - if (wchar >= 0x00C0 && wchar <= 0x00D6) // LATIN CAPITAL LETTER A WITH GRAVE - LATIN CAPITAL LETTER O WITH DIAERESIS - return wchar_t(uint16(wchar)+0x0020); - if (wchar >= 0x00D8 && wchar <= 0x00DE) // LATIN CAPITAL LETTER O WITH STROKE - LATIN CAPITAL LETTER THORN - return wchar_t(uint16(wchar)+0x0020); - if (wchar >= 0x0100 && wchar <= 0x012E) // LATIN CAPITAL LETTER A WITH MACRON - LATIN CAPITAL LETTER I WITH OGONEK (only %2=0) - { - if (wchar % 2 == 0) - return wchar_t(uint16(wchar)+0x0001); - } - if (wchar == 0x1E9E) // LATIN CAPITAL LETTER SHARP S - return wchar_t(0x00DF); - if (wchar == 0x0401) // CYRILLIC CAPITAL LETTER IO - return wchar_t(0x0451); - if (wchar >= 0x0410 && wchar <= 0x042F) // CYRILLIC CAPITAL LETTER A - CYRILLIC CAPITAL LETTER YA - return wchar_t(uint16(wchar)+0x0020); - - return wchar; -} - -inline void wstrToUpper(std::wstring& str) -{ - std::transform( str.begin(), str.end(), str.begin(), wcharToUpper ); -} - -inline void wstrToLower(std::wstring& str) -{ - std::transform( str.begin(), str.end(), str.begin(), wcharToLower ); -} - -std::wstring GetMainPartOfName(std::wstring const& wname, uint32 declension); - -bool utf8ToConsole(const std::string& utf8str, std::string& conStr); -bool consoleToUtf8(const std::string& conStr, std::string& utf8str); -bool Utf8FitTo(const std::string& str, std::wstring const& search); -void utf8printf(FILE* out, const char *str, ...); -void vutf8printf(FILE* out, const char *str, va_list* ap); - -bool IsIPAddress(char const* ipaddress); - -uint32 CreatePIDFile(const std::string& filename); - -std::string ByteArrayToHexStr(uint8 const* bytes, uint32 length, bool reverse = false); - -// simple class for not-modifyable list -template <typename T> -class HookList -{ - typedef typename std::list<T>::iterator ListIterator; - private: - typename std::list<T> m_list; - public: - HookList<T> & operator+=(T t) - { - m_list.push_back(t); - return *this; - } - HookList<T> & operator-=(T t) - { - m_list.remove(t); - return *this; - } - size_t size() - { - return m_list.size(); - } - ListIterator begin() - { - return m_list.begin(); - } - ListIterator end() - { - return m_list.end(); - } -}; - -class flag96 -{ -private: - uint32 part[3]; - -public: - flag96(uint32 p1 = 0, uint32 p2 = 0, uint32 p3 = 0) - { - part[0] = p1; - part[1] = p2; - part[2] = p3; - } - - inline bool IsEqual(uint32 p1 = 0, uint32 p2 = 0, uint32 p3 = 0) const - { - return (part[0] == p1 && part[1] == p2 && part[2] == p3); - } - - inline bool HasFlag(uint32 p1 = 0, uint32 p2 = 0, uint32 p3 = 0) const - { - return (part[0] & p1 || part[1] & p2 || part[2] & p3); - } - - inline void Set(uint32 p1 = 0, uint32 p2 = 0, uint32 p3 = 0) - { - part[0] = p1; - part[1] = p2; - part[2] = p3; - } - - inline bool operator <(const flag96 &right) const - { - for (uint8 i = 3; i > 0; --i) - { - if (part[i - 1] < right.part[i - 1]) - return true; - else if (part[i - 1] > right.part[i - 1]) - return false; - } - return false; - } - - inline bool operator ==(const flag96 &right) const - { - return - ( - part[0] == right.part[0] && - part[1] == right.part[1] && - part[2] == right.part[2] - ); - } - - inline bool operator !=(const flag96 &right) const - { - return !this->operator ==(right); - } - - inline flag96 & operator =(const flag96 &right) - { - part[0] = right.part[0]; - part[1] = right.part[1]; - part[2] = right.part[2]; - return *this; - } - - inline flag96 operator &(const flag96 &right) const - { - return flag96(part[0] & right.part[0], part[1] & right.part[1], - part[2] & right.part[2]); - } - - inline flag96 & operator &=(const flag96 &right) - { - part[0] &= right.part[0]; - part[1] &= right.part[1]; - part[2] &= right.part[2]; - return *this; - } - - inline flag96 operator |(const flag96 &right) const - { - return flag96(part[0] | right.part[0], part[1] | right.part[1], - part[2] | right.part[2]); - } - - inline flag96 & operator |=(const flag96 &right) - { - part[0] |= right.part[0]; - part[1] |= right.part[1]; - part[2] |= right.part[2]; - return *this; - } - - inline flag96 operator ~() const - { - return flag96(~part[0], ~part[1], ~part[2]); - } - - inline flag96 operator ^(const flag96 &right) const - { - return flag96(part[0] ^ right.part[0], part[1] ^ right.part[1], - part[2] ^ right.part[2]); - } - - inline flag96 & operator ^=(const flag96 &right) - { - part[0] ^= right.part[0]; - part[1] ^= right.part[1]; - part[2] ^= right.part[2]; - return *this; - } - - inline operator bool() const - { - return (part[0] != 0 || part[1] != 0 || part[2] != 0); - } - - inline bool operator !() const - { - return !this->operator bool(); - } - - inline uint32 & operator [](uint8 el) - { - return part[el]; - } - - inline const uint32 & operator [](uint8 el) const - { - return part[el]; - } -}; - -enum ComparisionType -{ - COMP_TYPE_EQ = 0, - COMP_TYPE_HIGH, - COMP_TYPE_LOW, - COMP_TYPE_HIGH_EQ, - COMP_TYPE_LOW_EQ, - COMP_TYPE_MAX -}; - -template <class T> -bool CompareValues(ComparisionType type, T val1, T val2) -{ - switch (type) - { - case COMP_TYPE_EQ: - return val1 == val2; - case COMP_TYPE_HIGH: - return val1 > val2; - case COMP_TYPE_LOW: - return val1 < val2; - case COMP_TYPE_HIGH_EQ: - return val1 >= val2; - case COMP_TYPE_LOW_EQ: - return val1 <= val2; - default: - // incorrect parameter - ASSERT(false); - return false; - } -} - -#endif |