diff options
Diffstat (limited to 'Runtime/Threads/ProfilerMutex.h')
-rw-r--r-- | Runtime/Threads/ProfilerMutex.h | 118 |
1 files changed, 118 insertions, 0 deletions
diff --git a/Runtime/Threads/ProfilerMutex.h b/Runtime/Threads/ProfilerMutex.h new file mode 100644 index 0000000..1e82b7c --- /dev/null +++ b/Runtime/Threads/ProfilerMutex.h @@ -0,0 +1,118 @@ +#ifndef __PROFILERMUTEX_H +#define __PROFILERMUTEX_H + +#include "Mutex.h" + +#if ENABLE_PROFILER +#include "Runtime/Profiler/Profiler.h" +#endif + +#define THREAD_LOCK_WARNINGS 0 +#define THREAD_LOCK_TIMING 0 + +#if THREAD_LOCK_WARNINGS || (ENABLE_PROFILER && SUPPORT_THREADS) + +#define AQUIRE_AUTOLOCK(mutex,profilerInformation) ProfilerMutexAutoLock aquireAutoLock (mutex, #mutex, profilerInformation, __FILE__, __LINE__) +#define AQUIRE_AUTOLOCK_WARN_MAIN_THREAD(mutex,profilerInformation) ProfilerMutexAutoLock aquireAutoLock (mutex, #mutex, Thread::mainThreadId, profilerInformation, __FILE__, __LINE__) +#define LOCK_MUTEX(mutex,profilerInformation) ProfilerMutexLock(mutex,#mutex,profilerInformation,__FILE__,__LINE__) + +double GetTimeSinceStartup (); + +inline void ProfilerMutexLock (Mutex& mutex, char const* mutexName, ProfilerInformation& information, char const* file, int line) +{ +#if ENABLE_PROFILER || THREAD_LOCK_WARNINGS + + if (mutex.TryLock()) + return; + + #if THREAD_LOCK_WARNINGS + DebugStringToFile (std::string ("Mutex '") + mutexName + "' already locked: " + information.name, 0, file, line, kScriptingWarning); + #endif + + PROFILER_AUTO_THREAD_SAFE(information, NULL) + +#if THREAD_LOCK_TIMING + double start = GetTimeSinceStartup (); + while (!mutex.TryLock()) + Sleep (10); + + double duration = GetTimeSinceStartup () - start; + DebugStringToFile (std::string ("Mutex '") + mutexName + "' obtained after: " + FloatToString(duration, "%6.3f") + " s", 0, file, line, kScriptingWarning); +#else + mutex.Lock(); +#endif + +#else + mutex.Lock(); +#endif +} + +inline void ProfilerMutexLock (Mutex& mutex, char const* mutexName, Thread::ThreadID threadID, ProfilerInformation& information, char const* file, int line) +{ +#if ENABLE_PROFILER || THREAD_LOCK_WARNINGS + if (mutex.TryLock()) + return; + + #if THREAD_LOCK_WARNINGS + if (Thread::EqualsCurrentThreadID(threadID)) + { + DebugStringToFile (std::string ("Mutex '") + mutexName + "' already locked: " + information.name, 0, file, line, kScriptingWarning); + } + #endif + + PROFILER_AUTO_THREAD_SAFE(information, NULL) + +#if THREAD_LOCK_TIMING + double start = GetTimeSinceStartup (); + while (!mutex.TryLock()) + Sleep (10); + + double duration = GetTimeSinceStartup () - start; + DebugStringToFile (std::string ("Mutex '") + mutexName + "' obtained after: " + FloatToString(duration, "%6.3f") + " s", 0, file, line, kScriptingWarning); +#else + mutex.Lock(); +#endif + +#else + mutex.Lock(); +#endif +} + +class ProfilerMutexAutoLock +{ +public: + ProfilerMutexAutoLock (Mutex& mutex, char const* mutexName, ProfilerInformation& profilerInformation, char const* file, int line) + : m_Mutex (&mutex) + { + ProfilerMutexLock(mutex, mutexName, profilerInformation, file, line); + } + + ProfilerMutexAutoLock (Mutex& mutex, char const* mutexName, Thread::ThreadID threadID, ProfilerInformation& profilerInformation, char const* file, int line) + : m_Mutex (&mutex) + { + ProfilerMutexLock(mutex, mutexName, threadID, profilerInformation, file, line); + } + + ~ProfilerMutexAutoLock() + { + m_Mutex->Unlock(); + } + +private: + ProfilerMutexAutoLock(const ProfilerMutexAutoLock&); + ProfilerMutexAutoLock& operator=(const ProfilerMutexAutoLock&); + +private: + Mutex* m_Mutex; +}; + +#else + +#define AQUIRE_AUTOLOCK(mutex,profilerInformation) Mutex::AutoLock aquireAutoLock (mutex) +#define AQUIRE_AUTOLOCK_WARN_MAIN_THREAD(mutex,profilerInformation) Mutex::AutoLock aquireAutoLock (mutex) +#define LOCK_MUTEX(mutex,profilerInformation) (mutex).Lock () + + +#endif + +#endif |