DRTVWR-476: Merge backout of e913c05d43b6

master
Nat Goodspeed 2019-11-12 16:59:23 -05:00
commit dbfd51b787
1 changed files with 39 additions and 79 deletions

View File

@ -53,46 +53,6 @@
#include "llstl.h"
#include "lltimer.h"
#if LL_WINDOWS
#define fhclose _close
#define fhdup _dup
#define fhdup2 _dup2
#define fhfdopen _fdopen
#define fhfileno _fileno
#else
#define fhclose ::close
#define fhdup ::dup
#define fhdup2 ::dup2
#define fhfdopen ::fdopen
#define fhfileno ::fileno
#endif
namespace LLError
{
class SettingsConfig;
typedef LLPointer<SettingsConfig> SettingsConfigPtr;
class Settings : public LLSingleton<Settings>
{
LLSINGLETON(Settings);
public:
SettingsConfigPtr getSettingsConfig();
~Settings();
void reset();
SettingsStoragePtr saveAndReset();
void restore(SettingsStoragePtr pSettingsStorage);
int getDupStderr() const;
private:
SettingsConfigPtr mSettingsConfig;
int mDupStderr;
};
} // namespace LLError
namespace {
#if LL_WINDOWS
void debugger_print(const std::string& s)
@ -160,8 +120,7 @@ namespace {
public:
RecordToFile(const std::string& filename):
mName(filename),
mFile(LLFile::fopen(filename, "a")),
mSavedStderr(LLError::Settings::instance().getDupStderr())
mFile(LLFile::fopen(filename, "a"))
{
if (!mFile)
{
@ -169,19 +128,25 @@ namespace {
}
else
{
#if LL_DARWIN || LL_LINUX
// We use a number of classic-C libraries, some of which write
// log output to stderr. The trouble with that is that unless
// you launch the viewer from a console, stderr output is
// lost. Redirect STDERR_FILENO to write into this log file.
fhdup2(fhfileno(mFile), fhfileno(stderr));
// But first, save the original stream in case we want it later.
mSavedStderr = ::dup(STDERR_FILENO);
::dup2(::fileno(mFile), STDERR_FILENO);
#endif
}
}
~RecordToFile()
{
#if LL_DARWIN || LL_LINUX
// restore stderr to its original fileno so any subsequent output
// to stderr goes to original stream
fhdup2(mSavedStderr, fhfileno(stderr));
::dup2(mSavedStderr, STDERR_FILENO);
#endif
mFile.close();
}
@ -201,8 +166,7 @@ namespace {
virtual void recordMessage(LLError::ELevel level,
const std::string& message) override
{
::fwrite(message.c_str(), sizeof(char), message.length(), mFile);
::fputc('\n', mFile);
fwrite(message.c_str(), sizeof(char), message.length(), mFile);
if (LLError::getAlwaysFlush())
{
::fflush(mFile);
@ -212,26 +176,22 @@ namespace {
private:
const std::string mName;
LLUniqueFile mFile;
int mSavedStderr;
int mSavedStderr{0};
};
class RecordToStderr : public LLError::Recorder
{
public:
RecordToStderr(bool timestamp) :
mUseANSI(checkANSI()),
// use duplicate stderr file handle so THIS output isn't affected
// by our internal redirection of all (other) stderr output
mStderr(fhfdopen(LLError::Settings::instance().getDupStderr(), "a"))
RecordToStderr(bool timestamp) : mUseANSI(checkANSI())
{
this->showMultiline(true);
}
virtual bool enabled() override
{
return LLError::getEnabledLogTypesMask() & 0x04;
this->showMultiline(true);
}
virtual bool enabled() override
{
return LLError::getEnabledLogTypesMask() & 0x04;
}
virtual void recordMessage(LLError::ELevel level,
const std::string& message) override
@ -254,18 +214,17 @@ namespace {
break;
}
}
fprintf(mStderr, "%s\n", message.c_str());
fprintf(stderr, "%s\n", message.c_str());
if (mUseANSI) colorANSI("0"); // reset
}
private:
bool mUseANSI;
LLFILE* mStderr;
void colorANSI(const std::string color)
{
// ANSI color code escape sequence
fprintf(mStderr, "\033[%sm", color.c_str() );
fprintf(stderr, "\033[%sm", color.c_str() );
};
static bool checkANSI(void)
@ -274,7 +233,7 @@ namespace {
// Check whether it's okay to use ANSI; if stderr is
// a tty then we assume yes. Can be turned off with
// the LL_NO_ANSI_COLOR env var.
return (0 != isatty(fhfileno(stderr))) &&
return (0 != isatty(2)) &&
(NULL == getenv("LL_NO_ANSI_COLOR"));
#endif // LL_LINUX
return false;
@ -538,6 +497,22 @@ namespace LLError
SettingsConfig();
};
typedef LLPointer<SettingsConfig> SettingsConfigPtr;
class Settings : public LLSingleton<Settings>
{
LLSINGLETON(Settings);
public:
SettingsConfigPtr getSettingsConfig();
void reset();
SettingsStoragePtr saveAndReset();
void restore(SettingsStoragePtr pSettingsStorage);
private:
SettingsConfigPtr mSettingsConfig;
};
SettingsConfig::SettingsConfig()
: LLRefCount(),
mDefaultLevel(LLError::LEVEL_DEBUG),
@ -561,20 +536,10 @@ namespace LLError
}
Settings::Settings():
mSettingsConfig(new SettingsConfig()),
// duplicate stderr file handle right away
mDupStderr(fhdup(fhfileno(stderr)))
mSettingsConfig(new SettingsConfig())
{
}
Settings::~Settings()
{
// restore original stderr
fhdup2(mDupStderr, fhfileno(stderr));
// and close the duplicate
fhclose(mDupStderr);
}
SettingsConfigPtr Settings::getSettingsConfig()
{
return mSettingsConfig;
@ -600,11 +565,6 @@ namespace LLError
mSettingsConfig = newSettingsConfig;
}
int Settings::getDupStderr() const
{
return mDupStderr;
}
bool is_available()
{
return Settings::instanceExists() && Globals::instanceExists();