From b23eab1c507f5d133a2dbcdd00c45aa86d156eef Mon Sep 17 00:00:00 2001 From: Brian Carlstrom Date: Wed, 8 Oct 2014 17:55:21 -0700 Subject: [PATCH] Add VLOG(class_linker) for clinit errors Bug: 17915141 Change-Id: I3002cf4348ec3fa241f63ff1515f813f6051c267 --- runtime/class_linker.cc | 23 +++++++++++++++++++---- 1 file changed, 19 insertions(+), 4 deletions(-) diff --git a/runtime/class_linker.cc b/runtime/class_linker.cc index cf3a58166..5718e44f9 100644 --- a/runtime/class_linker.cc +++ b/runtime/class_linker.cc @@ -115,7 +115,17 @@ static void ThrowEarlierClassFailure(mirror::Class* c) } } -static void WrapExceptionInInitializer() SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) { +static void VlogClassInitializationFailure(Handle klass) + SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) { + if (VLOG_IS_ON(class_linker)) { + std::string temp; + LOG(INFO) << "Failed to initialize class " << klass->GetDescriptor(&temp) << " from " + << klass->GetLocation() << "\n" << Thread::Current()->GetException(nullptr)->Dump(); + } +} + +static void WrapExceptionInInitializer(Handle klass) + SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) { Thread* self = Thread::Current(); JNIEnv* env = self->GetJniEnv(); @@ -132,6 +142,7 @@ static void WrapExceptionInInitializer() SHARED_LOCKS_REQUIRED(Locks::mutator_lo self->ThrowNewWrappedException(throw_location, "Ljava/lang/ExceptionInInitializerError;", nullptr); } + VlogClassInitializationFailure(klass); } static size_t Hash(const char* s) { @@ -4151,6 +4162,7 @@ bool ClassLinker::InitializeClass(Thread* self, Handle klass, // Was the class already found to be erroneous? Done under the lock to match the JLS. if (klass->IsErroneous()) { ThrowEarlierClassFailure(klass.Get()); + VlogClassInitializationFailure(klass); return false; } @@ -4163,6 +4175,7 @@ bool ClassLinker::InitializeClass(Thread* self, Handle klass, // compile time. if (klass->IsErroneous()) { CHECK(self->IsExceptionPending()); + VlogClassInitializationFailure(klass); } else { CHECK(Runtime::Current()->IsCompiler()); CHECK_EQ(klass->GetStatus(), mirror::Class::kStatusRetryVerificationAtRuntime); @@ -4181,6 +4194,7 @@ bool ClassLinker::InitializeClass(Thread* self, Handle klass, if (klass->GetStatus() == mirror::Class::kStatusInitializing) { // Could have got an exception during verification. if (self->IsExceptionPending()) { + VlogClassInitializationFailure(klass); return false; } // We caught somebody else in the act; was it us? @@ -4277,7 +4291,7 @@ bool ClassLinker::InitializeClass(Thread* self, Handle klass, ObjectLock lock(self, klass); if (self->IsExceptionPending()) { - WrapExceptionInInitializer(); + WrapExceptionInInitializer(klass); klass->SetStatus(mirror::Class::kStatusError, self); success = false; } else { @@ -4311,9 +4325,9 @@ bool ClassLinker::WaitForInitializeClass(Handle klass, Thread* se // When we wake up, repeat the test for init-in-progress. If // there's an exception pending (only possible if - // "interruptShouldThrow" was set), bail out. + // we were not using WaitIgnoringInterrupts), bail out. if (self->IsExceptionPending()) { - WrapExceptionInInitializer(); + WrapExceptionInInitializer(klass); klass->SetStatus(mirror::Class::kStatusError, self); return false; } @@ -4330,6 +4344,7 @@ bool ClassLinker::WaitForInitializeClass(Handle klass, Thread* se // different thread. Synthesize one here. ThrowNoClassDefFoundError(" failed for class %s; see exception in other thread", PrettyDescriptor(klass.Get()).c_str()); + VlogClassInitializationFailure(klass); return false; } if (klass->IsInitialized()) { -- 2.11.0