diff options
author | 2024-05-14 16:46:15 +0200 | |
---|---|---|
committer | 2024-05-17 05:52:24 +0000 | |
commit | 382f0db56cb95d0f1062ce46c73bc21705c87cef (patch) | |
tree | af1ed12f59c3a8a90946560001a53a98ffdbce0a /runtime/class_linker.cc | |
parent | e6374e9c089c98729068fc25fc981e78b27d6a70 (diff) |
Move transaction records from `Runtime` to `AotClassLinker`.
Keep a simple flag for active transaction in `Runtime` but
move all other transaction data to `AotClassLinker`.
Make `IsActiveTransaction()` a pre-requisite for calling
`IsTransactionAborted()`.
Eliminate `AbortTransactionAndThrowAbortError()` by inlining
into `AbortTransactionV()` and rewriting other callers to
use `AbortTransactionF()` instead.
Separate transaction-related test code to its own files.
Test: m test-art-host-gtest
Test: testrunner.py --host --optimizing
Change-Id: Ie6ee421fcfed1599049ab50ca692f19c71f395ce
Diffstat (limited to 'runtime/class_linker.cc')
-rw-r--r-- | runtime/class_linker.cc | 144 |
1 files changed, 142 insertions, 2 deletions
diff --git a/runtime/class_linker.cc b/runtime/class_linker.cc index 03611ebc20..823d79e7d0 100644 --- a/runtime/class_linker.cc +++ b/runtime/class_linker.cc @@ -5857,13 +5857,13 @@ bool ClassLinker::InitializeClass(Thread* self, WrapExceptionInInitializer(klass); mirror::Class::SetStatus(klass, ClassStatus::kErrorResolved, self); success = false; - } else if (Runtime::Current()->IsTransactionAborted()) { + } else if (Runtime::Current()->IsActiveTransaction() && IsTransactionAborted()) { // The exception thrown when the transaction aborted has been caught and cleared // so we need to throw it again now. VLOG(compiler) << "Return from class initializer of " << mirror::Class::PrettyDescriptor(klass.Get()) << " without exception while transaction was aborted: re-throw it now."; - runtime->ThrowTransactionAbortError(self); + ThrowTransactionAbortError(self); mirror::Class::SetStatus(klass, ClassStatus::kErrorResolved, self); success = false; } else { @@ -11188,6 +11188,146 @@ bool ClassLinker::TransactionAllocationConstraint( UNREACHABLE(); } +void ClassLinker::RecordWriteFieldBoolean([[maybe_unused]] mirror::Object* obj, + [[maybe_unused]] MemberOffset field_offset, + [[maybe_unused]] uint8_t value, + [[maybe_unused]] bool is_volatile) { + // Should not be called on ClassLinker, only on AotClassLinker that overrides this. + LOG(FATAL) << "UNREACHABLE"; + UNREACHABLE(); +} + +void ClassLinker::RecordWriteFieldByte([[maybe_unused]] mirror::Object* obj, + [[maybe_unused]] MemberOffset field_offset, + [[maybe_unused]] int8_t value, + [[maybe_unused]] bool is_volatile) { + // Should not be called on ClassLinker, only on AotClassLinker that overrides this. + LOG(FATAL) << "UNREACHABLE"; + UNREACHABLE(); +} + +void ClassLinker::RecordWriteFieldChar([[maybe_unused]] mirror::Object* obj, + [[maybe_unused]] MemberOffset field_offset, + [[maybe_unused]] uint16_t value, + [[maybe_unused]] bool is_volatile) { + // Should not be called on ClassLinker, only on AotClassLinker that overrides this. + LOG(FATAL) << "UNREACHABLE"; + UNREACHABLE(); +} + +void ClassLinker::RecordWriteFieldShort([[maybe_unused]] mirror::Object* obj, + [[maybe_unused]] MemberOffset field_offset, + [[maybe_unused]] int16_t value, + [[maybe_unused]] bool is_volatile) { + // Should not be called on ClassLinker, only on AotClassLinker that overrides this. + LOG(FATAL) << "UNREACHABLE"; + UNREACHABLE(); +} + +void ClassLinker::RecordWriteField32([[maybe_unused]] mirror::Object* obj, + [[maybe_unused]] MemberOffset field_offset, + [[maybe_unused]] uint32_t value, + [[maybe_unused]] bool is_volatile) { + // Should not be called on ClassLinker, only on AotClassLinker that overrides this. + LOG(FATAL) << "UNREACHABLE"; + UNREACHABLE(); +} + +void ClassLinker::RecordWriteField64([[maybe_unused]] mirror::Object* obj, + [[maybe_unused]] MemberOffset field_offset, + [[maybe_unused]] uint64_t value, + [[maybe_unused]] bool is_volatile) { + // Should not be called on ClassLinker, only on AotClassLinker that overrides this. + LOG(FATAL) << "UNREACHABLE"; + UNREACHABLE(); +} + +void ClassLinker::RecordWriteFieldReference([[maybe_unused]] mirror::Object* obj, + [[maybe_unused]] MemberOffset field_offset, + [[maybe_unused]] ObjPtr<mirror::Object> value, + [[maybe_unused]] bool is_volatile) { + // Should not be called on ClassLinker, only on AotClassLinker that overrides this. + LOG(FATAL) << "UNREACHABLE"; + UNREACHABLE(); +} + +void ClassLinker::RecordWriteArray([[maybe_unused]] mirror::Array* array, + [[maybe_unused]] size_t index, + [[maybe_unused]] uint64_t value) { + // Should not be called on ClassLinker, only on AotClassLinker that overrides this. + LOG(FATAL) << "UNREACHABLE"; + UNREACHABLE(); +} + +void ClassLinker::RecordStrongStringInsertion([[maybe_unused]] ObjPtr<mirror::String> s) { + // Should not be called on ClassLinker, only on AotClassLinker that overrides this. + LOG(FATAL) << "UNREACHABLE"; + UNREACHABLE(); +} + +void ClassLinker::RecordWeakStringInsertion([[maybe_unused]] ObjPtr<mirror::String> s) { + // Should not be called on ClassLinker, only on AotClassLinker that overrides this. + LOG(FATAL) << "UNREACHABLE"; + UNREACHABLE(); +} + +void ClassLinker::RecordStrongStringRemoval([[maybe_unused]] ObjPtr<mirror::String> s) { + // Should not be called on ClassLinker, only on AotClassLinker that overrides this. + LOG(FATAL) << "UNREACHABLE"; + UNREACHABLE(); +} + +void ClassLinker::RecordWeakStringRemoval([[maybe_unused]] ObjPtr<mirror::String> s) { + // Should not be called on ClassLinker, only on AotClassLinker that overrides this. + LOG(FATAL) << "UNREACHABLE"; + UNREACHABLE(); +} + +void ClassLinker::RecordResolveString([[maybe_unused]] ObjPtr<mirror::DexCache> dex_cache, + [[maybe_unused]] dex::StringIndex string_idx) { + // Should not be called on ClassLinker, only on AotClassLinker that overrides this. + LOG(FATAL) << "UNREACHABLE"; + UNREACHABLE(); +} + +void ClassLinker::RecordResolveMethodType([[maybe_unused]] ObjPtr<mirror::DexCache> dex_cache, + [[maybe_unused]] dex::ProtoIndex proto_idx) { + // Should not be called on ClassLinker, only on AotClassLinker that overrides this. + LOG(FATAL) << "UNREACHABLE"; + UNREACHABLE(); +} + +void ClassLinker::ThrowTransactionAbortError([[maybe_unused]] Thread* self) { + // Should not be called on ClassLinker, only on AotClassLinker that overrides this. + LOG(FATAL) << "UNREACHABLE"; + UNREACHABLE(); +} + +void ClassLinker::AbortTransactionF( + [[maybe_unused]] Thread* self, [[maybe_unused]] const char* fmt, ...) { + // Should not be called on ClassLinker, only on AotClassLinker that overrides this. + LOG(FATAL) << "UNREACHABLE"; + UNREACHABLE(); +} + +void ClassLinker::AbortTransactionV([[maybe_unused]] Thread* self, + [[maybe_unused]] const char* fmt, + [[maybe_unused]] va_list args) { + // Should not be called on ClassLinker, only on AotClassLinker that overrides this. + LOG(FATAL) << "UNREACHABLE"; + UNREACHABLE(); +} + +bool ClassLinker::IsTransactionAborted() const { + // Should not be called on ClassLinker, only on AotClassLinker that overrides this. + LOG(FATAL) << "UNREACHABLE"; + UNREACHABLE(); +} + +void ClassLinker::VisitTransactionRoots([[maybe_unused]] RootVisitor* visitor) { + // Nothing to do for normal `ClassLinker`, only `AotClassLinker` handles transactions. +} + void ClassLinker::RemoveDexFromCaches(const DexFile& dex_file) { ReaderMutexLock mu(Thread::Current(), *Locks::dex_lock_); |