From 735fde8c742188d019e41faf26ff67aab6a24d25 Mon Sep 17 00:00:00 2001 From: Richard Linden Date: Fri, 21 Sep 2012 18:52:08 -0700 Subject: SH-3275 WIP Run viewer metrics for object update messages added LLThreadLocalPtr broke llmutex out into llmutex.h got primary sampling buffer under thread local storage --- indra/llcommon/llthread.cpp | 214 ++++---------------------------------------- 1 file changed, 19 insertions(+), 195 deletions(-) (limited to 'indra/llcommon/llthread.cpp') diff --git a/indra/llcommon/llthread.cpp b/indra/llcommon/llthread.cpp index a6ad6b125c..f3ab8aa40c 100644 --- a/indra/llcommon/llthread.cpp +++ b/indra/llcommon/llthread.cpp @@ -29,6 +29,7 @@ #include "apr_portable.h" #include "llthread.h" +#include "llmutex.h" #include "lltimer.h" @@ -56,12 +57,20 @@ // //---------------------------------------------------------------------------- -#if !LL_DARWIN -U32 ll_thread_local sThreadID = 0; -#endif +#if LL_DARWIN +// statically allocated thread local storage not supported in Darwin executable formats +#elif LL_WINDOWS +U32 __declspec(thread) LLThread::sThreadIndex = 0; +#elif LL_LINUX +U32 __thread LLThread::sThreadID = 0; +#endif U32 LLThread::sIDIter = 0; +LLTrace::MasterThreadTrace gMasterThreadTrace; +LLThreadLocalPtr LLThread::sTraceData(&gMasterThreadTrace); + + LL_COMMON_API void assert_main_thread() { static U32 s_thread_id = LLThread::currentID(); @@ -78,8 +87,10 @@ void *APR_THREAD_FUNC LLThread::staticRun(apr_thread_t *apr_threadp, void *datap { LLThread *threadp = (LLThread *)datap; + sTraceData = new LLTrace::SlaveThreadTrace(gMasterThreadTrace); + #if !LL_DARWIN - sThreadID = threadp->mID; + sThreadIndex = threadp->mID; #endif // Run the user supplied function @@ -93,7 +104,6 @@ void *APR_THREAD_FUNC LLThread::staticRun(apr_thread_t *apr_threadp, void *datap return NULL; } - LLThread::LLThread(const std::string& name, apr_pool_t *poolp) : mPaused(FALSE), mName(name), @@ -301,198 +311,12 @@ void LLThread::wakeLocked() } } -//============================================================================ - -LLMutex::LLMutex(apr_pool_t *poolp) : - mAPRMutexp(NULL), mCount(0), mLockingThread(NO_THREAD) -{ - //if (poolp) - //{ - // mIsLocalPool = FALSE; - // mAPRPoolp = poolp; - //} - //else - { - mIsLocalPool = TRUE; - apr_pool_create(&mAPRPoolp, NULL); // Create a subpool for this thread - } - apr_thread_mutex_create(&mAPRMutexp, APR_THREAD_MUTEX_UNNESTED, mAPRPoolp); -} - - -LLMutex::~LLMutex() -{ -#if MUTEX_DEBUG - //bad assertion, the subclass LLSignal might be "locked", and that's OK - //llassert_always(!isLocked()); // better not be locked! -#endif - apr_thread_mutex_destroy(mAPRMutexp); - mAPRMutexp = NULL; - if (mIsLocalPool) - { - apr_pool_destroy(mAPRPoolp); - } -} - - -void LLMutex::lock() -{ - if(isSelfLocked()) - { //redundant lock - mCount++; - return; - } - - apr_thread_mutex_lock(mAPRMutexp); - -#if MUTEX_DEBUG - // Have to have the lock before we can access the debug info - U32 id = LLThread::currentID(); - if (mIsLocked[id] != FALSE) - llerrs << "Already locked in Thread: " << id << llendl; - mIsLocked[id] = TRUE; -#endif - -#if LL_DARWIN - mLockingThread = LLThread::currentID(); -#else - mLockingThread = sThreadID; -#endif -} - -void LLMutex::unlock() -{ - if (mCount > 0) - { //not the root unlock - mCount--; - return; - } - -#if MUTEX_DEBUG - // Access the debug info while we have the lock - U32 id = LLThread::currentID(); - if (mIsLocked[id] != TRUE) - llerrs << "Not locked in Thread: " << id << llendl; - mIsLocked[id] = FALSE; -#endif - - mLockingThread = NO_THREAD; - apr_thread_mutex_unlock(mAPRMutexp); -} - -bool LLMutex::isLocked() -{ - apr_status_t status = apr_thread_mutex_trylock(mAPRMutexp); - if (APR_STATUS_IS_EBUSY(status)) - { - return true; - } - else - { - apr_thread_mutex_unlock(mAPRMutexp); - return false; - } -} - -bool LLMutex::isSelfLocked() -{ -#if LL_DARWIN - return mLockingThread == LLThread::currentID(); -#else - return mLockingThread == sThreadID; -#endif -} - -U32 LLMutex::lockingThread() const -{ - return mLockingThread; -} - -//============================================================================ - -LLCondition::LLCondition(apr_pool_t *poolp) : - LLMutex(poolp) -{ - // base class (LLMutex) has already ensured that mAPRPoolp is set up. - - apr_thread_cond_create(&mAPRCondp, mAPRPoolp); -} - - -LLCondition::~LLCondition() -{ - apr_thread_cond_destroy(mAPRCondp); - mAPRCondp = NULL; -} - - -void LLCondition::wait() -{ - if (!isLocked()) - { //mAPRMutexp MUST be locked before calling apr_thread_cond_wait - apr_thread_mutex_lock(mAPRMutexp); -#if MUTEX_DEBUG - // avoid asserts on destruction in non-release builds - U32 id = LLThread::currentID(); - mIsLocked[id] = TRUE; -#endif - } - apr_thread_cond_wait(mAPRCondp, mAPRMutexp); -} - -void LLCondition::signal() -{ - apr_thread_cond_signal(mAPRCondp); -} - -void LLCondition::broadcast() -{ - apr_thread_cond_broadcast(mAPRCondp); -} - -//============================================================================ - -//---------------------------------------------------------------------------- - -//static -LLMutex* LLThreadSafeRefCount::sMutex = 0; - -//static -void LLThreadSafeRefCount::initThreadSafeRefCount() -{ - if (!sMutex) - { - sMutex = new LLMutex(0); - } -} - -//static -void LLThreadSafeRefCount::cleanupThreadSafeRefCount() +void LLThread::lockData() { - delete sMutex; - sMutex = NULL; -} - - -//---------------------------------------------------------------------------- - -LLThreadSafeRefCount::LLThreadSafeRefCount() : - mRef(0) -{ -} - -LLThreadSafeRefCount::~LLThreadSafeRefCount() -{ - if (mRef != 0) - { - llerrs << "deleting non-zero reference" << llendl; - } + mRunCondition->lock(); } -//============================================================================ - -LLResponder::~LLResponder() +void LLThread::unlockData() { + mRunCondition->unlock(); } - -//============================================================================ -- cgit v1.2.3 From adeeabfc13c91dc99a1ea1949cd2f820c4150995 Mon Sep 17 00:00:00 2001 From: Richard Linden Date: Mon, 24 Sep 2012 18:56:01 -0700 Subject: SH-3275 WIP Run viewer metrics for object update messages moved LLThreadLocalPtr to llapr fixed various startup race conditions for LLThreadLocalPtr --- indra/llcommon/llthread.cpp | 8 +++----- 1 file changed, 3 insertions(+), 5 deletions(-) (limited to 'indra/llcommon/llthread.cpp') diff --git a/indra/llcommon/llthread.cpp b/indra/llcommon/llthread.cpp index f3ab8aa40c..023004eedd 100644 --- a/indra/llcommon/llthread.cpp +++ b/indra/llcommon/llthread.cpp @@ -66,9 +66,7 @@ U32 __thread LLThread::sThreadID = 0; #endif U32 LLThread::sIDIter = 0; - -LLTrace::MasterThreadTrace gMasterThreadTrace; -LLThreadLocalPtr LLThread::sTraceData(&gMasterThreadTrace); +LLThreadLocalPtr LLThread::sTraceData; LL_COMMON_API void assert_main_thread() @@ -87,7 +85,7 @@ void *APR_THREAD_FUNC LLThread::staticRun(apr_thread_t *apr_threadp, void *datap { LLThread *threadp = (LLThread *)datap; - sTraceData = new LLTrace::SlaveThreadTrace(gMasterThreadTrace); + sTraceData = new LLTrace::SlaveThreadTrace(); #if !LL_DARWIN sThreadIndex = threadp->mID; @@ -155,7 +153,7 @@ void LLThread::shutdown() //llinfos << "LLThread::~LLThread() Killing thread " << mName << " Status: " << mStatus << llendl; // Now wait a bit for the thread to exit // It's unclear whether I should even bother doing this - this destructor - // should netver get called unless we're already stopped, really... + // should never get called unless we're already stopped, really... S32 counter = 0; const S32 MAX_WAIT = 600; while (counter < MAX_WAIT) -- cgit v1.2.3 From 308ff886c3ab2aa561477921bc0d92e1bd7d399a Mon Sep 17 00:00:00 2001 From: Richard Linden Date: Mon, 24 Sep 2012 19:01:48 -0700 Subject: fixed build moved LLThread::lockData and unlockData back to header --- indra/llcommon/llthread.cpp | 10 ---------- 1 file changed, 10 deletions(-) (limited to 'indra/llcommon/llthread.cpp') diff --git a/indra/llcommon/llthread.cpp b/indra/llcommon/llthread.cpp index 023004eedd..de1f0801a1 100644 --- a/indra/llcommon/llthread.cpp +++ b/indra/llcommon/llthread.cpp @@ -308,13 +308,3 @@ void LLThread::wakeLocked() mRunCondition->signal(); } } - -void LLThread::lockData() -{ - mRunCondition->lock(); -} - -void LLThread::unlockData() -{ - mRunCondition->unlock(); -} -- cgit v1.2.3 From 05a3203d8274a0a0999faad128f629614b8d62c5 Mon Sep 17 00:00:00 2001 From: Richard Linden Date: Wed, 26 Sep 2012 17:04:57 -0700 Subject: SH-3275 WIP Run viewer metrics for object update messages fixed various issues related to unit tests and LLThreadLocalPtr initialization and teardown --- indra/llcommon/llthread.cpp | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) (limited to 'indra/llcommon/llthread.cpp') diff --git a/indra/llcommon/llthread.cpp b/indra/llcommon/llthread.cpp index de1f0801a1..2e6eb085dc 100644 --- a/indra/llcommon/llthread.cpp +++ b/indra/llcommon/llthread.cpp @@ -66,7 +66,7 @@ U32 __thread LLThread::sThreadID = 0; #endif U32 LLThread::sIDIter = 0; -LLThreadLocalPtr LLThread::sTraceData; +LLThreadLocalPtr LLThread::sTraceData; LL_COMMON_API void assert_main_thread() @@ -99,6 +99,8 @@ void *APR_THREAD_FUNC LLThread::staticRun(apr_thread_t *apr_threadp, void *datap // We're done with the run function, this thread is done executing now. threadp->mStatus = STOPPED; + delete sTraceData.get(); + return NULL; } @@ -108,6 +110,7 @@ LLThread::LLThread(const std::string& name, apr_pool_t *poolp) : mAPRThreadp(NULL), mStatus(STOPPED) { + mID = ++sIDIter; // Thread creation probably CAN be paranoid about APR being initialized, if necessary -- cgit v1.2.3 From 07c4be092b276f0d7c14ba12872efb31c1f16764 Mon Sep 17 00:00:00 2001 From: Richard Linden Date: Wed, 26 Sep 2012 19:12:40 -0700 Subject: SH-3275 WIP Run viewer metrics for object update messages slave threads now pushing data to master thread --- indra/llcommon/llthread.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'indra/llcommon/llthread.cpp') diff --git a/indra/llcommon/llthread.cpp b/indra/llcommon/llthread.cpp index 2e6eb085dc..2ff524d9ba 100644 --- a/indra/llcommon/llthread.cpp +++ b/indra/llcommon/llthread.cpp @@ -66,7 +66,7 @@ U32 __thread LLThread::sThreadID = 0; #endif U32 LLThread::sIDIter = 0; -LLThreadLocalPtr LLThread::sTraceData; +LLThreadLocalPtr LLThread::sTraceData; LL_COMMON_API void assert_main_thread() -- cgit v1.2.3 From 38354e19063478c8cda0408547ad05023b457041 Mon Sep 17 00:00:00 2001 From: Richard Linden Date: Fri, 28 Sep 2012 10:45:14 -0700 Subject: SH-3275 WIP Run viewer metrics for object update messages created separate constructor for static allocation of sampler buffer fixed start/stop/resume semantics of samplers and added sampler time interval tracking --- indra/llcommon/llthread.cpp | 14 +++++++++++++- 1 file changed, 13 insertions(+), 1 deletion(-) (limited to 'indra/llcommon/llthread.cpp') diff --git a/indra/llcommon/llthread.cpp b/indra/llcommon/llthread.cpp index 2ff524d9ba..7384842627 100644 --- a/indra/llcommon/llthread.cpp +++ b/indra/llcommon/llthread.cpp @@ -32,6 +32,7 @@ #include "llmutex.h" #include "lltimer.h" +#include "lltrace.h" #if LL_LINUX || LL_SOLARIS #include @@ -85,7 +86,7 @@ void *APR_THREAD_FUNC LLThread::staticRun(apr_thread_t *apr_threadp, void *datap { LLThread *threadp = (LLThread *)datap; - sTraceData = new LLTrace::SlaveThreadTrace(); + setTraceData(new LLTrace::SlaveThreadTrace()); #if !LL_DARWIN sThreadIndex = threadp->mID; @@ -100,6 +101,7 @@ void *APR_THREAD_FUNC LLThread::staticRun(apr_thread_t *apr_threadp, void *datap threadp->mStatus = STOPPED; delete sTraceData.get(); + sTraceData = NULL; return NULL; } @@ -311,3 +313,13 @@ void LLThread::wakeLocked() mRunCondition->signal(); } } + +LLTrace::ThreadTrace* LLThread::getTraceData() +{ + return sTraceData.get(); +} + +void LLThread::setTraceData( LLTrace::ThreadTrace* data ) +{ + sTraceData = data; +} -- cgit v1.2.3 From 14b1b0b2bb6bac5bc688cc4d14c33f1b680dd3b4 Mon Sep 17 00:00:00 2001 From: Richard Linden Date: Mon, 1 Oct 2012 19:39:04 -0700 Subject: SH-3275 WIP Run viewer metrics for object update messages cleaned up API samplers are now value types with copy-on-write buffers under the hood removed coupling with LLThread --- indra/llcommon/llthread.cpp | 15 ++------------- 1 file changed, 2 insertions(+), 13 deletions(-) (limited to 'indra/llcommon/llthread.cpp') diff --git a/indra/llcommon/llthread.cpp b/indra/llcommon/llthread.cpp index 7384842627..c705e5103b 100644 --- a/indra/llcommon/llthread.cpp +++ b/indra/llcommon/llthread.cpp @@ -67,7 +67,6 @@ U32 __thread LLThread::sThreadID = 0; #endif U32 LLThread::sIDIter = 0; -LLThreadLocalPtr LLThread::sTraceData; LL_COMMON_API void assert_main_thread() @@ -86,7 +85,7 @@ void *APR_THREAD_FUNC LLThread::staticRun(apr_thread_t *apr_threadp, void *datap { LLThread *threadp = (LLThread *)datap; - setTraceData(new LLTrace::SlaveThreadTrace()); + LLTrace::ThreadTrace* thread_trace = new LLTrace::SlaveThreadTrace(); #if !LL_DARWIN sThreadIndex = threadp->mID; @@ -100,8 +99,7 @@ void *APR_THREAD_FUNC LLThread::staticRun(apr_thread_t *apr_threadp, void *datap // We're done with the run function, this thread is done executing now. threadp->mStatus = STOPPED; - delete sTraceData.get(); - sTraceData = NULL; + delete thread_trace; return NULL; } @@ -314,12 +312,3 @@ void LLThread::wakeLocked() } } -LLTrace::ThreadTrace* LLThread::getTraceData() -{ - return sTraceData.get(); -} - -void LLThread::setTraceData( LLTrace::ThreadTrace* data ) -{ - sTraceData = data; -} -- cgit v1.2.3 From dbe9742703cf14db85ec3d16c540efc68dce95a6 Mon Sep 17 00:00:00 2001 From: Richard Linden Date: Tue, 2 Oct 2012 15:37:16 -0700 Subject: SH-3404 create sampler class renamed LLTrace::ThreadTrace to LLTrace::ThreadRecorder renamed LLTrace::Sampler to LLTrace::Recording --- indra/llcommon/llthread.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'indra/llcommon/llthread.cpp') diff --git a/indra/llcommon/llthread.cpp b/indra/llcommon/llthread.cpp index c705e5103b..6723e427f5 100644 --- a/indra/llcommon/llthread.cpp +++ b/indra/llcommon/llthread.cpp @@ -85,7 +85,7 @@ void *APR_THREAD_FUNC LLThread::staticRun(apr_thread_t *apr_threadp, void *datap { LLThread *threadp = (LLThread *)datap; - LLTrace::ThreadTrace* thread_trace = new LLTrace::SlaveThreadTrace(); + LLTrace::ThreadRecorder* thread_recorder = new LLTrace::SlaveThreadRecorder(); #if !LL_DARWIN sThreadIndex = threadp->mID; @@ -99,7 +99,7 @@ void *APR_THREAD_FUNC LLThread::staticRun(apr_thread_t *apr_threadp, void *datap // We're done with the run function, this thread is done executing now. threadp->mStatus = STOPPED; - delete thread_trace; + delete thread_recorder; return NULL; } -- cgit v1.2.3 From 74ac0182ec8f7a0f6d0ea89f5814f0998ab90b62 Mon Sep 17 00:00:00 2001 From: Richard Linden Date: Wed, 10 Oct 2012 19:25:56 -0700 Subject: SH-3405 WIP convert existing stats to lltrace system fixed units conversion so that trace getters return convertable units removed circular dependencies from lltrace* converted more stats to lltrace --- indra/llcommon/llthread.cpp | 1 + 1 file changed, 1 insertion(+) (limited to 'indra/llcommon/llthread.cpp') diff --git a/indra/llcommon/llthread.cpp b/indra/llcommon/llthread.cpp index 6723e427f5..cc661bab59 100644 --- a/indra/llcommon/llthread.cpp +++ b/indra/llcommon/llthread.cpp @@ -33,6 +33,7 @@ #include "lltimer.h" #include "lltrace.h" +#include "lltracethreadrecorder.h" #if LL_LINUX || LL_SOLARIS #include -- cgit v1.2.3 From 5d51175cd79b15cf036cd7e6bd646a1a0777eb7f Mon Sep 17 00:00:00 2001 From: Richard Linden Date: Tue, 20 Nov 2012 15:55:04 -0800 Subject: SH-3406 WIP convert fast timers to lltrace system fixes to merge --- indra/llcommon/llthread.cpp | 153 +------------------------------------------- 1 file changed, 2 insertions(+), 151 deletions(-) (limited to 'indra/llcommon/llthread.cpp') diff --git a/indra/llcommon/llthread.cpp b/indra/llcommon/llthread.cpp index 1c86eb4f06..8ce739bf23 100644 --- a/indra/llcommon/llthread.cpp +++ b/indra/llcommon/llthread.cpp @@ -62,7 +62,7 @@ #if LL_DARWIN // statically allocated thread local storage not supported in Darwin executable formats #elif LL_WINDOWS -U32 __declspec(thread) LLThread::sThreadIndex = 0; +U32 __declspec(thread) LLThread::sThreadID = 0; #elif LL_LINUX U32 __thread LLThread::sThreadID = 0; #endif @@ -96,7 +96,7 @@ void *APR_THREAD_FUNC LLThread::staticRun(apr_thread_t *apr_threadp, void *datap LLTrace::ThreadRecorder* thread_recorder = new LLTrace::SlaveThreadRecorder(); #if !LL_DARWIN - sThreadIndex = threadp->mID; + sThreadID = threadp->mID; #endif // Run the user supplied function @@ -327,155 +327,6 @@ void LLThread::wakeLocked() //============================================================================ -LLMutex::LLMutex(apr_pool_t *poolp) : - mAPRMutexp(NULL), mCount(0), mLockingThread(NO_THREAD) -{ - //if (poolp) - //{ - // mIsLocalPool = FALSE; - // mAPRPoolp = poolp; - //} - //else - { - mIsLocalPool = TRUE; - apr_pool_create(&mAPRPoolp, NULL); // Create a subpool for this thread - } - apr_thread_mutex_create(&mAPRMutexp, APR_THREAD_MUTEX_UNNESTED, mAPRPoolp); -} - - -LLMutex::~LLMutex() -{ -#if MUTEX_DEBUG - //bad assertion, the subclass LLSignal might be "locked", and that's OK - //llassert_always(!isLocked()); // better not be locked! -#endif - apr_thread_mutex_destroy(mAPRMutexp); - mAPRMutexp = NULL; - if (mIsLocalPool) - { - apr_pool_destroy(mAPRPoolp); - } -} - - -void LLMutex::lock() -{ - if(isSelfLocked()) - { //redundant lock - mCount++; - return; - } - - apr_thread_mutex_lock(mAPRMutexp); - -#if MUTEX_DEBUG - // Have to have the lock before we can access the debug info - U32 id = LLThread::currentID(); - if (mIsLocked[id] != FALSE) - llerrs << "Already locked in Thread: " << id << llendl; - mIsLocked[id] = TRUE; -#endif - -#if LL_DARWIN - mLockingThread = LLThread::currentID(); -#else - mLockingThread = sThreadID; -#endif -} - -void LLMutex::unlock() -{ - if (mCount > 0) - { //not the root unlock - mCount--; - return; - } - -#if MUTEX_DEBUG - // Access the debug info while we have the lock - U32 id = LLThread::currentID(); - if (mIsLocked[id] != TRUE) - llerrs << "Not locked in Thread: " << id << llendl; - mIsLocked[id] = FALSE; -#endif - - mLockingThread = NO_THREAD; - apr_thread_mutex_unlock(mAPRMutexp); -} - -bool LLMutex::isLocked() -{ - apr_status_t status = apr_thread_mutex_trylock(mAPRMutexp); - if (APR_STATUS_IS_EBUSY(status)) - { - return true; - } - else - { - apr_thread_mutex_unlock(mAPRMutexp); - return false; - } -} - -bool LLMutex::isSelfLocked() -{ -#if LL_DARWIN - return mLockingThread == LLThread::currentID(); -#else - return mLockingThread == sThreadID; -#endif -} - -U32 LLMutex::lockingThread() const -{ - return mLockingThread; -} - -//============================================================================ - -LLCondition::LLCondition(apr_pool_t *poolp) : - LLMutex(poolp) -{ - // base class (LLMutex) has already ensured that mAPRPoolp is set up. - - apr_thread_cond_create(&mAPRCondp, mAPRPoolp); -} - - -LLCondition::~LLCondition() -{ - apr_thread_cond_destroy(mAPRCondp); - mAPRCondp = NULL; -} - - -void LLCondition::wait() -{ - if (!isLocked()) - { //mAPRMutexp MUST be locked before calling apr_thread_cond_wait - apr_thread_mutex_lock(mAPRMutexp); -#if MUTEX_DEBUG - // avoid asserts on destruction in non-release builds - U32 id = LLThread::currentID(); - mIsLocked[id] = TRUE; -#endif - } - apr_thread_cond_wait(mAPRCondp, mAPRMutexp); -} - -void LLCondition::signal() -{ - apr_thread_cond_signal(mAPRCondp); -} - -void LLCondition::broadcast() -{ - apr_thread_cond_broadcast(mAPRCondp); -} - -//============================================================================ - //---------------------------------------------------------------------------- //static -- cgit v1.2.3 From 68967e7b2b9416ff66cb49ae755fb33d7b81d129 Mon Sep 17 00:00:00 2001 From: Richard Linden Date: Wed, 5 Dec 2012 14:22:18 -0800 Subject: SH-3406 WIP convert fast timers to lltrace system changed thread id declaration to be local to llthread.cpp and use currentID() uniformly across platforms --- indra/llcommon/llthread.cpp | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) (limited to 'indra/llcommon/llthread.cpp') diff --git a/indra/llcommon/llthread.cpp b/indra/llcommon/llthread.cpp index 8ce739bf23..6374b5398b 100644 --- a/indra/llcommon/llthread.cpp +++ b/indra/llcommon/llthread.cpp @@ -62,9 +62,9 @@ #if LL_DARWIN // statically allocated thread local storage not supported in Darwin executable formats #elif LL_WINDOWS -U32 __declspec(thread) LLThread::sThreadID = 0; +U32 __declspec(thread) sThreadID = 0; #elif LL_LINUX -U32 __thread LLThread::sThreadID = 0; +U32 __thread sThreadID = 0; #endif U32 LLThread::sIDIter = 0; @@ -294,7 +294,13 @@ void LLThread::setQuitting() // static U32 LLThread::currentID() { +#if LL_DARWIN + // statically allocated thread local storage not supported in Darwin executable formats return (U32)apr_os_thread_current(); +#else + return sThreadID; +#endif + } // static -- cgit v1.2.3