diff options
| -rwxr-xr-x | indra/llcommon/llerror.cpp | 5 | ||||
| -rwxr-xr-x | indra/llcommon/llerrorcontrol.h | 5 | ||||
| -rwxr-xr-x | indra/llcommon/llsingleton.cpp | 64 | ||||
| -rwxr-xr-x | indra/llcommon/llsingleton.h | 6 | 
4 files changed, 58 insertions, 22 deletions
diff --git a/indra/llcommon/llerror.cpp b/indra/llcommon/llerror.cpp index 2100989316..54524bbe8e 100755 --- a/indra/llcommon/llerror.cpp +++ b/indra/llcommon/llerror.cpp @@ -402,6 +402,11 @@ namespace  namespace LLError  { +	bool is_available() +	{ +		return Globals::instanceExists(); +	} +  	class SettingsConfig : public LLRefCount  	{  		friend class Settings; diff --git a/indra/llcommon/llerrorcontrol.h b/indra/llcommon/llerrorcontrol.h index 56ac52e5de..56e84f7172 100755 --- a/indra/llcommon/llerrorcontrol.h +++ b/indra/llcommon/llerrorcontrol.h @@ -189,6 +189,11 @@ namespace LLError  	LL_COMMON_API std::string abbreviateFile(const std::string& filePath);  	LL_COMMON_API int shouldLogCallCount(); + +	// Check whether Globals exists. This should only be used by LLSingleton +	// infrastructure to avoid trying to log when our internal LLSingleton is +	// unavailable -- circularity ensues. +	LL_COMMON_API bool is_available();  };  #endif // LL_LLERRORCONTROL_H diff --git a/indra/llcommon/llsingleton.cpp b/indra/llcommon/llsingleton.cpp index 204c0d24d0..a3edf925ad 100755 --- a/indra/llcommon/llsingleton.cpp +++ b/indra/llcommon/llsingleton.cpp @@ -28,9 +28,11 @@  #include "llsingleton.h"  #include "llerror.h" +#include "llerrorcontrol.h"         // LLError::is_available()  #include "lldependencies.h"  #include <boost/foreach.hpp>  #include <algorithm> +#include <iostream>                 // std::cerr in dire emergency  #include <sstream>  #include <stdexcept> @@ -108,14 +110,14 @@ void LLSingletonBase::pop_initializing()      list_t& list(get_initializing());      if (list.empty())      { -        LL_ERRS() << "Underflow in stack of currently-initializing LLSingletons at " -                  << typeid(*this).name() << "::getInstance()" << LL_ENDL; +        logerrs("Underflow in stack of currently-initializing LLSingletons at ", +                typeid(*this).name(), "::getInstance()");      }      if (list.back() != this)      { -        LL_ERRS() << "Push/pop mismatch in stack of currently-initializing LLSingletons: " -                  << typeid(*this).name() << "::getInstance() trying to pop " -                  << typeid(*list.back()).name() << LL_ENDL; +        logerrs("Push/pop mismatch in stack of currently-initializing LLSingletons: ", +                typeid(*this).name(), "::getInstance() trying to pop ", +                typeid(*list.back()).name());      }      // Here we're sure that list.back() == this. Whew, pop it.      list.pop_back(); @@ -151,8 +153,8 @@ void LLSingletonBase::capture_dependency()              // DEBUGGING: Initially, make this crump. We want to know how bad              // the problem is before we add it to the long, sad list of              // ominous warnings that everyone always ignores. -            LL_ERRS() << "LLSingleton circularity: " << out.str() -                      << typeid(*this).name() << LL_ENDL; +            logerrs("LLSingleton circularity: ", out.str().c_str(), +                    typeid(*this).name());          }          else          { @@ -223,13 +225,13 @@ void LLSingletonBase::cleanupAll()              }              catch (const std::exception& e)              { -                LL_WARNS() << "Exception in " << typeid(*sp).name() -                           << "::cleanupSingleton(): " << e.what() << LL_ENDL; +                logwarns("Exception in ", typeid(*sp).name(), +                         "::cleanupSingleton(): ", e.what());              }              catch (...)              { -                LL_WARNS() << "Unknown exception in " << typeid(*sp).name() -                           << "::cleanupSingleton()" << LL_ENDL; +                logwarns("Unknown exception in ", typeid(*sp).name(), +                         "::cleanupSingleton()");              }          }      } @@ -250,7 +252,7 @@ void LLSingletonBase::deleteAll()              if (! sp->mDeleteSingleton)              {                  // This Should Not Happen... but carry on. -                LL_WARNS() << name << "::mDeleteSingleton not initialized!" << LL_ENDL; +                logwarns(name, "::mDeleteSingleton not initialized!");              }              else              { @@ -261,13 +263,11 @@ void LLSingletonBase::deleteAll()          }          catch (const std::exception& e)          { -            LL_WARNS() << "Exception in " << name -                       << "::deleteSingleton(): " << e.what() << LL_ENDL; +            logwarns("Exception in ", name, "::deleteSingleton(): ", e.what());          }          catch (...)          { -            LL_WARNS() << "Unknown exception in " << name -                       << "::deleteSingleton()" << LL_ENDL; +            logwarns("Unknown exception in ", name, "::deleteSingleton()");          }      }  } @@ -307,13 +307,37 @@ void intrusive_ptr_release(LLSingletonBase::MasterRefcount* mrc)  /*---------------------------- Logging helpers -----------------------------*/  //static -void LLSingletonBase::logerrs(const char* p1, const char* p2, const char* p3) +void LLSingletonBase::logerrs(const char* p1, const char* p2, const char* p3, const char* p4)  { -    LL_ERRS() << p1 << p2 << p3 << LL_ENDL; +    // Check LLError::is_available() because some of LLError's infrastructure +    // is itself an LLSingleton. If that LLSingleton has not yet been +    // initialized, trying to log will engage LLSingleton machinery... and +    // around and around we go. +    if (LLError::is_available()) +    { +        LL_ERRS() << p1 << p2 << p3 << p4 << LL_ENDL; +    } +    else +    { +        // Caller may be a test program, or something else whose stderr is +        // visible to the user. +        std::cerr << p1 << p2 << p3 << p4 << std::endl; +        // The other important side effect of LL_ERRS() is +        // https://www.youtube.com/watch?v=OMG7paGJqhQ (emphasis on OMG) +        LLError::crashAndLoop(std::string()); +    }  }  //static -void LLSingletonBase::logwarns(const char* p1, const char* p2, const char* p3) +void LLSingletonBase::logwarns(const char* p1, const char* p2, const char* p3, const char* p4)  { -    LL_WARNS() << p1 << p2 << p3 << LL_ENDL; +    // See logerrs() remarks about is_available(). +    if (LLError::is_available()) +    { +        LL_WARNS() << p1 << p2 << p3 << p4 << LL_ENDL; +    } +    else +    { +        std::cerr << p1 << p2 << p3 << p4 << std::endl; +    }  } diff --git a/indra/llcommon/llsingleton.h b/indra/llcommon/llsingleton.h index 7706ed53f2..d66ea33c0c 100755 --- a/indra/llcommon/llsingleton.h +++ b/indra/llcommon/llsingleton.h @@ -90,9 +90,11 @@ protected:      void capture_dependency();      // delegate LL_ERRS() logging to llsingleton.cpp -    static void logerrs(const char* p1, const char* p2="", const char* p3=""); +    static void logerrs(const char* p1, const char* p2="", +                        const char* p3="", const char* p4="");      // delegate LL_WARNS() logging to llsingleton.cpp -    static void logwarns(const char* p1, const char* p2="", const char* p3=""); +    static void logwarns(const char* p1, const char* p2="", +                         const char* p3="", const char* p4="");      // obtain canonical ref_ptr_t      static ref_ptr_t get_master_refcount();  | 
