summaryrefslogtreecommitdiff
path: root/compiler/driver/compiler_driver.cc
diff options
context:
space:
mode:
author Jeff Hao <jeffhao@google.com> 2017-07-12 14:51:49 -0700
committer Jeff Hao <jeffhao@google.com> 2017-07-17 14:09:56 -0700
commit0cb172874481f736c6b7c491dd621166cc25561b (patch)
tree2408750b6e08c686b89cee5df0ddae736a775092 /compiler/driver/compiler_driver.cc
parent890045e5a768257d8def42827a09a516ebe3e07e (diff)
Do superclass validation at compile time and log with new class status.
Tries to perform superclass validation for classes that are resolved, but not initialized at runtime. If successful, saves the result in the oat file with a new class status. At runtime, the superclass validation can be skipped during class initialization, saving some time and reducing string accesses. Results show savings of 50kB PSS in maps on startup, with slight decrease in startup time. Maps (average of 100 runs) Before: dex 9941.3 odex 15159.8 total 25101.1 launch 908 After: dex 9897.4 odex 15155.7 total 25053.1 launch 906.6 Bug: 63456114 Test: mm test-art-host Change-Id: If67a4a49d61781b6d561c26118d7e0c6b9cc0d6f
Diffstat (limited to 'compiler/driver/compiler_driver.cc')
-rw-r--r--compiler/driver/compiler_driver.cc15
1 files changed, 12 insertions, 3 deletions
diff --git a/compiler/driver/compiler_driver.cc b/compiler/driver/compiler_driver.cc
index bb64755c9e..e8b915009b 100644
--- a/compiler/driver/compiler_driver.cc
+++ b/compiler/driver/compiler_driver.cc
@@ -2245,7 +2245,7 @@ class InitializeClassVisitor : public CompilationVisitor {
const bool is_boot_image = manager_->GetCompiler()->GetCompilerOptions().IsBootImage();
const bool is_app_image = manager_->GetCompiler()->GetCompilerOptions().IsAppImage();
- mirror::Class::Status old_status = klass->GetStatus();;
+ mirror::Class::Status old_status = klass->GetStatus();
// Only try to initialize classes that were successfully verified.
if (klass->IsVerified()) {
// Don't initialize classes in boot space when compiling app image
@@ -2363,6 +2363,14 @@ class InitializeClassVisitor : public CompilationVisitor {
}
}
}
+ // If the class still isn't initialized, at least try some checks that initialization
+ // would do so they can be skipped at runtime.
+ if (!klass->IsInitialized() &&
+ manager_->GetClassLinker()->ValidateSuperClassDescriptors(klass)) {
+ old_status = mirror::Class::kStatusSuperclassValidated;
+ } else {
+ soa.Self()->ClearException();
+ }
soa.Self()->AssertNoPendingException();
}
}
@@ -2860,13 +2868,14 @@ bool CompilerDriver::GetCompiledClass(ClassReference ref, mirror::Class::Status*
void CompilerDriver::RecordClassStatus(ClassReference ref, mirror::Class::Status status) {
switch (status) {
- case mirror::Class::kStatusNotReady:
case mirror::Class::kStatusErrorResolved:
case mirror::Class::kStatusErrorUnresolved:
+ case mirror::Class::kStatusNotReady:
+ case mirror::Class::kStatusResolved:
case mirror::Class::kStatusRetryVerificationAtRuntime:
case mirror::Class::kStatusVerified:
+ case mirror::Class::kStatusSuperclassValidated:
case mirror::Class::kStatusInitialized:
- case mirror::Class::kStatusResolved:
break; // Expected states.
default:
LOG(FATAL) << "Unexpected class status for class "