summaryrefslogtreecommitdiff
path: root/indra
diff options
context:
space:
mode:
authorNat Goodspeed <nat@lindenlab.com>2019-12-10 10:56:24 -0500
committerNat Goodspeed <nat@lindenlab.com>2020-03-25 19:24:25 -0400
commit39e7b48317e3f0fe37d7398099ab1e38b97963bf (patch)
tree7734474fcadf89bfeeea1dbc099ccc33b3716ef6 /indra
parent3cd2beb97ef0d368d47b0b7efd242b3c709d01af (diff)
DRTVWR-476: Make llcoro::logname() distinguish different threads.
Actually, introduce static LLCoros::logname() and make the namespaced free function an alias for that. Because CoroData is a subclass of LLInstanceTracker with a key, every instance requires a distinct key. That conflicts with our "getName() returns empty string for default coroutine on thread" convention. Introduce a new CoroData constructor, specifically for the default coroutine on each thread, that initializes the getName() name to empty string while providing a distinct "mainN" key. Make get_CoroData() use that new constructor for its thread_local instance, passing an atomic<int> incremented each time we initialize one for a new thread. Then LLCoros::logname() returns either the getName() name or the key.
Diffstat (limited to 'indra')
-rw-r--r--indra/llcommon/llcoros.cpp28
-rw-r--r--indra/llcommon/llcoros.h15
2 files changed, 33 insertions, 10 deletions
diff --git a/indra/llcommon/llcoros.cpp b/indra/llcommon/llcoros.cpp
index 9e0cceda2b..adb86c4e0b 100644
--- a/indra/llcommon/llcoros.cpp
+++ b/indra/llcommon/llcoros.cpp
@@ -34,6 +34,7 @@
#include "llcoros.h"
// STL headers
// std headers
+#include <atomic>
// external library headers
#include <boost/bind.hpp>
#include <boost/fiber/fiber.hpp>
@@ -73,10 +74,9 @@ LLCoros::CoroData& LLCoros::get_CoroData(const std::string& caller)
// canonical values.
if (! current)
{
- // It's tempting to provide a distinct name for each thread's "main
- // coroutine." But as getName() has always returned the empty string
- // to mean "not in a coroutine," empty string should suffice here.
- static thread_local CoroData sMain("");
+ static std::atomic<int> which_thread(0);
+ // Use alternate CoroData constructor.
+ static thread_local CoroData sMain(which_thread++);
// We need not reset() the local_ptr to this instance; we'll simply
// find it again every time we discover that current is null.
current = &sMain;
@@ -198,6 +198,13 @@ std::string LLCoros::getName()
return get_CoroData("getName()").mName;
}
+//static
+std::string LLCoros::logname()
+{
+ LLCoros::CoroData& data(get_CoroData("logname()"));
+ return data.mName.empty()? data.getKey() : data.mName;
+}
+
void LLCoros::setStackSize(S32 stacksize)
{
LL_DEBUGS("LLCoros") << "Setting coroutine stack size to " << stacksize << LL_ENDL;
@@ -353,3 +360,16 @@ LLCoros::CoroData::CoroData(const std::string& name):
mCreationTime(LLTimer::getTotalSeconds())
{
}
+
+LLCoros::CoroData::CoroData(int n):
+ // This constructor is used for the thread_local instance belonging to the
+ // default coroutine on each thread. We must give each one a different
+ // LLInstanceTracker key because LLInstanceTracker's map spans all
+ // threads, but we want the default coroutine on each thread to have the
+ // empty string as its visible name because some consumers test for that.
+ LLInstanceTracker<CoroData, std::string>("main" + stringize(n)),
+ mName(),
+ mConsuming(false),
+ mCreationTime(LLTimer::getTotalSeconds())
+{
+}
diff --git a/indra/llcommon/llcoros.h b/indra/llcommon/llcoros.h
index 2e4cd8ccad..95859198d4 100644
--- a/indra/llcommon/llcoros.h
+++ b/indra/llcommon/llcoros.h
@@ -143,6 +143,13 @@ public:
static std::string getName();
/**
+ * This variation returns a name suitable for log messages: the explicit
+ * name for an explicitly-launched coroutine, or "mainN" for the default
+ * coroutine on a thread.
+ */
+ static std::string logname();
+
+ /**
* For delayed initialization. To be clear, this will only affect
* coroutines launched @em after this point. The underlying facility
* provides no way to alter the stack size of any running coroutine.
@@ -272,6 +279,7 @@ private:
struct CoroData: public LLInstanceTracker<CoroData, std::string>
{
CoroData(const std::string& name);
+ CoroData(int n);
// tweaked name of the current coroutine
const std::string mName;
@@ -292,12 +300,7 @@ namespace llcoro
{
inline
-std::string logname()
-{
- static std::string main("main");
- std::string name(LLCoros::getName());
- return name.empty()? main : name;
-}
+std::string logname() { return LLCoros::logname(); }
} // llcoro