summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
author Ian Rogers <irogers@google.com> 2013-05-16 11:19:53 -0700
committer Ian Rogers <irogers@google.com> 2013-05-16 11:26:24 -0700
commitc4ee12e73fc844f28a9812a9141985cf05143a57 (patch)
tree59ea9f105b39b05beea9ff17cda83f1122461629 /src
parentd8274bcbc565fff1254574b3cbf46dc4e7b52812 (diff)
Avoid recursion if logging lock is corrupt.
If the logging lock is corrupt then using LOG fails and recursive death ensues. Make Mutex a friend of LogMessage so that it can do raw logging in this special situation. Opportunistically also make fields of LogMessage and LogMessageData that can be const, const. Change-Id: I9e0d07c3224096bcf03d6410cd64bb8b5c831fac
Diffstat (limited to 'src')
-rw-r--r--src/base/logging.h11
-rw-r--r--src/base/mutex.cc10
2 files changed, 15 insertions, 6 deletions
diff --git a/src/base/logging.h b/src/base/logging.h
index 310357d11b..f250ce01b3 100644
--- a/src/base/logging.h
+++ b/src/base/logging.h
@@ -170,10 +170,10 @@ struct LogMessageData {
public:
LogMessageData(const char* file, int line, LogSeverity severity, int error);
std::ostringstream buffer;
- const char* file;
- int line_number;
- LogSeverity severity;
- int error;
+ const char* const file;
+ const int line_number;
+ const LogSeverity severity;
+ const int error;
private:
DISALLOW_COPY_AND_ASSIGN(LogMessageData);
@@ -190,9 +190,10 @@ class LogMessage {
private:
static void LogLine(const LogMessageData& data, const char*);
- LogMessageData* data_;
+ LogMessageData* const data_;
friend void HandleUnexpectedSignal(int signal_number, siginfo_t* info, void* raw_context);
+ friend class Mutex;
DISALLOW_COPY_AND_ASSIGN(LogMessage);
};
diff --git a/src/base/mutex.cc b/src/base/mutex.cc
index 86356a9b85..a2851e5b3c 100644
--- a/src/base/mutex.cc
+++ b/src/base/mutex.cc
@@ -394,7 +394,15 @@ void Mutex::ExclusiveUnlock(Thread* self) {
}
}
} else {
- LOG(FATAL) << "Unexpected state_:" << cur_state << " for " << name_;
+ // Logging acquires the logging lock, avoid infinite recursion in that case.
+ if (this != Locks::logging_lock_) {
+ LOG(FATAL) << "Unexpected state_ in unlock " << cur_state << " for " << name_;
+ } else {
+ LogMessageData data(__FILE__, __LINE__, INTERNAL_FATAL, -1);
+ LogMessage::LogLine(data, StringPrintf("Unexpected state_ %d in unlock for %s",
+ cur_state, name_).c_str());
+ _exit(1);
+ }
}
} while(!done);
#else