summaryrefslogtreecommitdiff
path: root/runtime/class_linker-inl.h
diff options
context:
space:
mode:
author Vladimir Marko <vmarko@google.com> 2017-07-06 14:55:02 +0100
committer Vladimir Marko <vmarko@google.com> 2017-07-20 16:33:00 +0100
commit07bfbace6f835e6c748fd68ec7624992478b16c1 (patch)
tree5d094a00fbc90455bd9b53e042cf8b4fe8433462 /runtime/class_linker-inl.h
parentba118827465d12177f3996e50133960087b1c916 (diff)
Hash-based DexCache methods array.
Total boot*.art size for aosp_angler-userdebug: - arm64: - before: 11603968 - after: 10129408 (-1.4MiB, -12.7%) - arm: - before: 8626176 - after: 7888896 (-0.7MiB, -8.5%) Test: m test-art-host-gtest Test: testrunner.py --host Test: Nexus 6P boots. Test: testrunner.py --target Test: Build aosp_mips64-eng Bug: 30627598 Change-Id: I7f858605de5f074cbd7f0d9c4c072fbd44aee28f
Diffstat (limited to 'runtime/class_linker-inl.h')
-rw-r--r--runtime/class_linker-inl.h58
1 files changed, 27 insertions, 31 deletions
diff --git a/runtime/class_linker-inl.h b/runtime/class_linker-inl.h
index d29db15f0a..9a736973bc 100644
--- a/runtime/class_linker-inl.h
+++ b/runtime/class_linker-inl.h
@@ -156,6 +156,29 @@ inline bool ClassLinker::CheckInvokeClassMismatch(ObjPtr<mirror::DexCache> dex_c
});
}
+inline ArtMethod* ClassLinker::LookupResolvedMethod(uint32_t method_idx,
+ ObjPtr<mirror::DexCache> dex_cache,
+ ObjPtr<mirror::ClassLoader> class_loader) {
+ PointerSize pointer_size = image_pointer_size_;
+ ArtMethod* resolved = dex_cache->GetResolvedMethod(method_idx, pointer_size);
+ if (resolved == nullptr) {
+ const DexFile& dex_file = *dex_cache->GetDexFile();
+ const DexFile::MethodId& method_id = dex_file.GetMethodId(method_idx);
+ ObjPtr<mirror::Class> klass = LookupResolvedType(method_id.class_idx_, dex_cache, class_loader);
+ if (klass != nullptr) {
+ if (klass->IsInterface()) {
+ resolved = klass->FindInterfaceMethod(dex_cache, method_idx, pointer_size);
+ } else {
+ resolved = klass->FindClassMethod(dex_cache, method_idx, pointer_size);
+ }
+ if (resolved != nullptr) {
+ dex_cache->SetResolvedMethod(method_idx, resolved, pointer_size);
+ }
+ }
+ }
+ return resolved;
+}
+
template <InvokeType type, ClassLinker::ResolveMode kResolveMode>
inline ArtMethod* ClassLinker::GetResolvedMethod(uint32_t method_idx, ArtMethod* referrer) {
DCHECK(referrer != nullptr);
@@ -164,9 +187,10 @@ inline ArtMethod* ClassLinker::GetResolvedMethod(uint32_t method_idx, ArtMethod*
// However, we delay the GetInterfaceMethodIfProxy() until needed.
DCHECK(!referrer->IsProxyMethod() || referrer->IsConstructor());
ArtMethod* resolved_method = referrer->GetDexCacheResolvedMethod(method_idx, image_pointer_size_);
- if (resolved_method == nullptr || resolved_method->IsRuntimeMethod()) {
+ if (resolved_method == nullptr) {
return nullptr;
}
+ DCHECK(!resolved_method->IsRuntimeMethod());
if (kResolveMode == ResolveMode::kCheckICCEAndIAE) {
referrer = referrer->GetInterfaceMethodIfProxy(image_pointer_size_);
// Check if the invoke type matches the class type.
@@ -203,7 +227,8 @@ inline ArtMethod* ClassLinker::ResolveMethod(Thread* self,
DCHECK(!referrer->IsProxyMethod() || referrer->IsConstructor());
Thread::PoisonObjectPointersIfDebug();
ArtMethod* resolved_method = referrer->GetDexCacheResolvedMethod(method_idx, image_pointer_size_);
- if (UNLIKELY(resolved_method == nullptr || resolved_method->IsRuntimeMethod())) {
+ DCHECK(resolved_method == nullptr || !resolved_method->IsRuntimeMethod());
+ if (UNLIKELY(resolved_method == nullptr)) {
referrer = referrer->GetInterfaceMethodIfProxy(image_pointer_size_);
ObjPtr<mirror::Class> declaring_class = referrer->GetDeclaringClass();
StackHandleScope<2> hs(self);
@@ -287,35 +312,6 @@ inline mirror::Class* ClassLinker::GetClassRoot(ClassRoot class_root) {
return klass.Ptr();
}
-template<ReadBarrierOption kReadBarrierOption>
-ArtMethod* ClassLinker::FindMethodForProxy(ObjPtr<mirror::Class> proxy_class,
- ArtMethod* proxy_method) {
- DCHECK(proxy_class->IsProxyClass());
- DCHECK(proxy_method->IsProxyMethod());
- {
- Thread* const self = Thread::Current();
- ReaderMutexLock mu(self, *Locks::dex_lock_);
- // Locate the dex cache of the original interface/Object
- for (const DexCacheData& data : dex_caches_) {
- if (!self->IsJWeakCleared(data.weak_root) &&
- proxy_method->HasSameDexCacheResolvedMethods(data.resolved_methods,
- image_pointer_size_)) {
- ObjPtr<mirror::DexCache> dex_cache =
- ObjPtr<mirror::DexCache>::DownCast(self->DecodeJObject(data.weak_root));
- if (dex_cache != nullptr) {
- ArtMethod* resolved_method = dex_cache->GetResolvedMethod(
- proxy_method->GetDexMethodIndex(), image_pointer_size_);
- CHECK(resolved_method != nullptr);
- return resolved_method;
- }
- }
- }
- }
- LOG(FATAL) << "Didn't find dex cache for " << proxy_class->PrettyClass() << " "
- << proxy_method->PrettyMethod();
- UNREACHABLE();
-}
-
} // namespace art
#endif // ART_RUNTIME_CLASS_LINKER_INL_H_