Revert^2 "Support clinit for app image during compilation"
Add some spot fixes for app image class initialization and re-enable
test 660 features.
Bug: 70735003
Test: test-art-host
This reverts commit abadf024efdc632f663d7fb503cd277b3f65fca2.
Change-Id: Id16fd3ada3eb1bd57ea60c3cdc4a0cf9835950d7
diff --git a/runtime/aot_class_linker.cc b/runtime/aot_class_linker.cc
index c9ca4c9..c151306 100644
--- a/runtime/aot_class_linker.cc
+++ b/runtime/aot_class_linker.cc
@@ -31,6 +31,16 @@
AotClassLinker::~AotClassLinker() {}
+bool AotClassLinker::CanAllocClass() {
+ // AllocClass doesn't work under transaction, so we abort.
+ if (Runtime::Current()->IsActiveTransaction()) {
+ Runtime::Current()->AbortTransactionAndThrowAbortError(
+ Thread::Current(), "Can't resolve type within transaction.");
+ return false;
+ }
+ return ClassLinker::CanAllocClass();
+}
+
// Wrap the original InitializeClass with creation of transaction when in strict mode.
bool AotClassLinker::InitializeClass(Thread* self,
Handle<mirror::Class> klass,
@@ -44,6 +54,13 @@
return ClassLinker::InitializeClass(self, klass, can_init_statics, can_init_parents);
}
+ // When in strict_mode, don't initialize a class if it belongs to boot but not initialized.
+ if (strict_mode_ && klass->IsBootStrapClassLoaded()) {
+ runtime->AbortTransactionAndThrowAbortError(self, "Can't resolve "
+ + klass->PrettyTypeOf() + " because it is an uninitialized boot class.");
+ return false;
+ }
+
// Don't initialize klass if it's superclass is not initialized, because superclass might abort
// the transaction and rolled back after klass's change is commited.
if (strict_mode_ && !klass->IsInterface() && klass->HasSuperClass()) {
@@ -64,9 +81,8 @@
// Exit Transaction if success.
runtime->ExitTransactionMode();
} else {
- // If not successfully initialized, the last transaction must abort. Don't rollback
- // immediately, leave the cleanup to compiler driver which needs abort message and exception.
- DCHECK(runtime->IsTransactionAborted());
+ // If not successfully initialized, don't rollback immediately, leave the cleanup to compiler
+ // driver which needs abort message and exception.
DCHECK(self->IsExceptionPending());
}
}
diff --git a/runtime/aot_class_linker.h b/runtime/aot_class_linker.h
index 6a8133e..74da33d 100644
--- a/runtime/aot_class_linker.h
+++ b/runtime/aot_class_linker.h
@@ -37,6 +37,13 @@
override
REQUIRES_SHARED(Locks::mutator_lock_);
+ // Override AllocClass because aot compiler will need to perform a transaction check to determine
+ // can we allocate class from heap.
+ bool CanAllocClass()
+ override
+ REQUIRES_SHARED(Locks::mutator_lock_)
+ REQUIRES(!Roles::uninterruptible_);
+
bool InitializeClass(Thread *self,
Handle<mirror::Class> klass,
bool can_run_clinit,
diff --git a/runtime/class_linker.cc b/runtime/class_linker.cc
index c06e5e8..2bbcbb7 100644
--- a/runtime/class_linker.cc
+++ b/runtime/class_linker.cc
@@ -3152,7 +3152,11 @@
// Interface object should get the right size here. Regular class will
// figure out the right size later and be replaced with one of the right
// size when the class becomes resolved.
- klass.Assign(AllocClass(self, SizeOfClassWithoutEmbeddedTables(dex_file, dex_class_def)));
+ if (CanAllocClass()) {
+ klass.Assign(AllocClass(self, SizeOfClassWithoutEmbeddedTables(dex_file, dex_class_def)));
+ } else {
+ return nullptr;
+ }
}
if (UNLIKELY(klass == nullptr)) {
self->AssertPendingOOMException();
diff --git a/runtime/class_linker.h b/runtime/class_linker.h
index 3605ffb..8269aaa 100644
--- a/runtime/class_linker.h
+++ b/runtime/class_linker.h
@@ -758,6 +758,10 @@
std::string* error_msg)
REQUIRES_SHARED(Locks::mutator_lock_);
+ virtual bool CanAllocClass() REQUIRES_SHARED(Locks::mutator_lock_) REQUIRES(!Locks::dex_lock_) {
+ return true;
+ }
+
private:
class LinkInterfaceMethodsHelper;