Refactor ArtField::GetType<>() as {Lookup,Resolve}Type().
And add no thread suspension assertion to LookupType()
as well as ArtMethod::LookupResolvedClassFromTypeIndex().
Test: m test-art-host-gtest
Test: testrunner.py --host --optimizing
Change-Id: If1541ccb0aafeabb6d1dd5566f10afcac98a2ef1
diff --git a/runtime/art_field-inl.h b/runtime/art_field-inl.h
index fced995..4a328e8 100644
--- a/runtime/art_field-inl.h
+++ b/runtime/art_field-inl.h
@@ -299,10 +299,26 @@
return GetTypeAsPrimitiveType() != Primitive::kPrimNot;
}
-template <bool kResolve>
-inline ObjPtr<mirror::Class> ArtField::GetType() {
- // TODO: Refactor this function into two functions, ResolveType() and LookupType()
- // so that we can properly annotate it with no-suspension possible / suspension possible.
+inline ObjPtr<mirror::Class> ArtField::LookupType() {
+ ScopedAssertNoThreadSuspension ants(__FUNCTION__);
+ const uint32_t field_index = GetDexFieldIndex();
+ ObjPtr<mirror::Class> declaring_class = GetDeclaringClass();
+ if (UNLIKELY(declaring_class->IsProxyClass())) {
+ return ProxyFindSystemClass(GetTypeDescriptor());
+ }
+ ObjPtr<mirror::DexCache> dex_cache = declaring_class->GetDexCache();
+ const DexFile* const dex_file = dex_cache->GetDexFile();
+ dex::TypeIndex type_idx = dex_file->GetFieldId(field_index).type_idx_;
+ ObjPtr<mirror::Class> type = dex_cache->GetResolvedType(type_idx);
+ if (UNLIKELY(type == nullptr)) {
+ type = Runtime::Current()->GetClassLinker()->LookupResolvedType(
+ *dex_file, type_idx, dex_cache, declaring_class->GetClassLoader());
+ DCHECK(!Thread::Current()->IsExceptionPending());
+ }
+ return type.Ptr();
+}
+
+inline ObjPtr<mirror::Class> ArtField::ResolveType() {
const uint32_t field_index = GetDexFieldIndex();
ObjPtr<mirror::Class> declaring_class = GetDeclaringClass();
if (UNLIKELY(declaring_class->IsProxyClass())) {
@@ -310,18 +326,12 @@
}
auto* dex_cache = declaring_class->GetDexCache();
const DexFile* const dex_file = dex_cache->GetDexFile();
- const DexFile::FieldId& field_id = dex_file->GetFieldId(field_index);
- ObjPtr<mirror::Class> type = dex_cache->GetResolvedType(field_id.type_idx_);
+ dex::TypeIndex type_idx = dex_file->GetFieldId(field_index).type_idx_;
+ ObjPtr<mirror::Class> type = dex_cache->GetResolvedType(type_idx);
if (UNLIKELY(type == nullptr)) {
ClassLinker* class_linker = Runtime::Current()->GetClassLinker();
- if (kResolve) {
- type = class_linker->ResolveType(*dex_file, field_id.type_idx_, declaring_class);
- CHECK(type != nullptr || Thread::Current()->IsExceptionPending());
- } else {
- type = class_linker->LookupResolvedType(
- *dex_file, field_id.type_idx_, dex_cache, declaring_class->GetClassLoader());
- DCHECK(!Thread::Current()->IsExceptionPending());
- }
+ type = class_linker->ResolveType(*dex_file, type_idx, declaring_class);
+ DCHECK_EQ(type == nullptr, Thread::Current()->IsExceptionPending());
}
return type;
}
diff --git a/runtime/art_field.h b/runtime/art_field.h
index 5114578..866bf0b 100644
--- a/runtime/art_field.h
+++ b/runtime/art_field.h
@@ -205,8 +205,8 @@
bool IsPrimitiveType() REQUIRES_SHARED(Locks::mutator_lock_);
- template <bool kResolve>
- ObjPtr<mirror::Class> GetType() REQUIRES_SHARED(Locks::mutator_lock_);
+ ObjPtr<mirror::Class> LookupType() REQUIRES_SHARED(Locks::mutator_lock_);
+ ObjPtr<mirror::Class> ResolveType() REQUIRES_SHARED(Locks::mutator_lock_);
size_t FieldSize() REQUIRES_SHARED(Locks::mutator_lock_);
diff --git a/runtime/art_method-inl.h b/runtime/art_method-inl.h
index 4181169..12b4d16 100644
--- a/runtime/art_method-inl.h
+++ b/runtime/art_method-inl.h
@@ -103,6 +103,7 @@
}
inline ObjPtr<mirror::Class> ArtMethod::LookupResolvedClassFromTypeIndex(dex::TypeIndex type_idx) {
+ ScopedAssertNoThreadSuspension ants(__FUNCTION__);
ObjPtr<mirror::DexCache> dex_cache = GetDexCache();
ObjPtr<mirror::Class> type = dex_cache->GetResolvedType(type_idx);
if (UNLIKELY(type == nullptr)) {
diff --git a/runtime/class_linker.cc b/runtime/class_linker.cc
index 5435c11..35da434 100644
--- a/runtime/class_linker.cc
+++ b/runtime/class_linker.cc
@@ -8159,23 +8159,23 @@
Handle<mirror::Class> return_type;
switch (handle_type) {
case DexFile::MethodHandleType::kStaticPut: {
- method_params->Set(0, target_field->GetType<true>());
+ method_params->Set(0, target_field->ResolveType());
return_type = hs.NewHandle(FindPrimitiveClass('V'));
break;
}
case DexFile::MethodHandleType::kStaticGet: {
- return_type = hs.NewHandle(target_field->GetType<true>());
+ return_type = hs.NewHandle(target_field->ResolveType());
break;
}
case DexFile::MethodHandleType::kInstancePut: {
method_params->Set(0, target_field->GetDeclaringClass());
- method_params->Set(1, target_field->GetType<true>());
+ method_params->Set(1, target_field->ResolveType());
return_type = hs.NewHandle(FindPrimitiveClass('V'));
break;
}
case DexFile::MethodHandleType::kInstanceGet: {
method_params->Set(0, target_field->GetDeclaringClass());
- return_type = hs.NewHandle(target_field->GetType<true>());
+ return_type = hs.NewHandle(target_field->ResolveType());
break;
}
case DexFile::MethodHandleType::kInvokeStatic:
@@ -8582,7 +8582,7 @@
ArtField* dex_elements_field =
jni::DecodeArtField(WellKnownClasses::dalvik_system_DexPathList_dexElements);
- Handle<mirror::Class> dex_elements_class(hs.NewHandle(dex_elements_field->GetType<true>()));
+ Handle<mirror::Class> dex_elements_class(hs.NewHandle(dex_elements_field->ResolveType()));
DCHECK(dex_elements_class != nullptr);
DCHECK(dex_elements_class->IsArrayClass());
Handle<mirror::ObjectArray<mirror::Object>> h_dex_elements(hs.NewHandle(
@@ -8597,10 +8597,10 @@
DCHECK_EQ(h_dex_element_class.Get(), element_file_field->GetDeclaringClass());
ArtField* cookie_field = jni::DecodeArtField(WellKnownClasses::dalvik_system_DexFile_cookie);
- DCHECK_EQ(cookie_field->GetDeclaringClass(), element_file_field->GetType<false>());
+ DCHECK_EQ(cookie_field->GetDeclaringClass(), element_file_field->LookupType());
ArtField* file_name_field = jni::DecodeArtField(WellKnownClasses::dalvik_system_DexFile_fileName);
- DCHECK_EQ(file_name_field->GetDeclaringClass(), element_file_field->GetType<false>());
+ DCHECK_EQ(file_name_field->GetDeclaringClass(), element_file_field->LookupType());
// Fill the elements array.
int32_t index = 0;
diff --git a/runtime/class_linker_test.cc b/runtime/class_linker_test.cc
index 4d92826..1b867c0 100644
--- a/runtime/class_linker_test.cc
+++ b/runtime/class_linker_test.cc
@@ -253,7 +253,7 @@
EXPECT_TRUE(field != nullptr);
EXPECT_OBJ_PTR_EQ(klass, field->GetDeclaringClass());
EXPECT_TRUE(field->GetName() != nullptr);
- EXPECT_TRUE(field->GetType<true>() != nullptr);
+ EXPECT_TRUE(field->ResolveType() != nullptr);
}
void AssertClass(const std::string& descriptor, Handle<mirror::Class> klass)
@@ -362,7 +362,7 @@
MemberOffset current_ref_offset = start_ref_offset;
for (size_t i = 0; i < klass->NumInstanceFields(); i++) {
ArtField* field = klass->GetInstanceField(i);
- ObjPtr<mirror::Class> field_type = field->GetType<true>();
+ ObjPtr<mirror::Class> field_type = field->ResolveType();
ASSERT_TRUE(field_type != nullptr);
if (!field->IsPrimitiveType()) {
ASSERT_TRUE(!field_type->IsPrimitive());
diff --git a/runtime/common_dex_operations.h b/runtime/common_dex_operations.h
index 6a78637..267735f 100644
--- a/runtime/common_dex_operations.h
+++ b/runtime/common_dex_operations.h
@@ -201,7 +201,7 @@
StackHandleScope<2> hs(self);
HandleWrapperObjPtr<mirror::Object> h_reg(hs.NewHandleWrapper(®));
HandleWrapperObjPtr<mirror::Object> h_obj(hs.NewHandleWrapper(&obj));
- field_class = field->GetType<true>();
+ field_class = field->ResolveType();
}
if (!reg->VerifierInstanceOf(field_class.Ptr())) {
// This should never happen.
diff --git a/runtime/debugger.cc b/runtime/debugger.cc
index 8898afe..c7f2453 100644
--- a/runtime/debugger.cc
+++ b/runtime/debugger.cc
@@ -1931,7 +1931,7 @@
StackHandleScope<2> hs(Thread::Current());
HandleWrapper<mirror::Object> h_v(hs.NewHandleWrapper(&v));
HandleWrapper<mirror::Object> h_o(hs.NewHandleWrapper(&o));
- field_type = f->GetType<true>();
+ field_type = f->ResolveType();
}
if (!field_type->IsAssignableFrom(v->GetClass())) {
return JDWP::ERR_INVALID_OBJECT;
diff --git a/runtime/mirror/field-inl.h b/runtime/mirror/field-inl.h
index ad48202..bcd2db4 100644
--- a/runtime/mirror/field-inl.h
+++ b/runtime/mirror/field-inl.h
@@ -31,7 +31,7 @@
inline mirror::Field* Field::CreateFromArtField(Thread* self, ArtField* field, bool force_resolve) {
StackHandleScope<2> hs(self);
// Try to resolve type before allocating since this is a thread suspension point.
- Handle<mirror::Class> type = hs.NewHandle(field->GetType<true>());
+ Handle<mirror::Class> type = hs.NewHandle(field->ResolveType());
if (type == nullptr) {
if (force_resolve) {
diff --git a/runtime/mirror/object.cc b/runtime/mirror/object.cc
index 78ef339..87cc620 100644
--- a/runtime/mirror/object.cc
+++ b/runtime/mirror/object.cc
@@ -239,7 +239,8 @@
if (field.GetOffset().Int32Value() == field_offset.Int32Value()) {
CHECK_NE(field.GetTypeAsPrimitiveType(), Primitive::kPrimNot);
// TODO: resolve the field type for moving GC.
- ObjPtr<mirror::Class> field_type = field.GetType<!kMovingCollector>();
+ ObjPtr<mirror::Class> field_type =
+ kMovingCollector ? field.LookupType() : field.ResolveType();
if (field_type != nullptr) {
CHECK(field_type->IsAssignableFrom(new_value->GetClass()));
}
@@ -256,7 +257,8 @@
if (field.GetOffset().Int32Value() == field_offset.Int32Value()) {
CHECK_NE(field.GetTypeAsPrimitiveType(), Primitive::kPrimNot);
// TODO: resolve the field type for moving GC.
- ObjPtr<mirror::Class> field_type = field.GetType<!kMovingCollector>();
+ ObjPtr<mirror::Class> field_type =
+ kMovingCollector ? field.LookupType() : field.ResolveType();
if (field_type != nullptr) {
CHECK(field_type->IsAssignableFrom(new_value->GetClass()));
}
diff --git a/runtime/mirror/var_handle_test.cc b/runtime/mirror/var_handle_test.cc
index 0e1c994..159f80c 100644
--- a/runtime/mirror/var_handle_test.cc
+++ b/runtime/mirror/var_handle_test.cc
@@ -44,7 +44,7 @@
StackHandleScope<4> hs(self);
Handle<FieldVarHandle> fvh = hs.NewHandle(
ObjPtr<FieldVarHandle>::DownCast(FieldVarHandle::StaticClass()->AllocObject(self)));
- Handle<Class> var_type = hs.NewHandle(art_field->GetType<true>().Ptr());
+ Handle<Class> var_type = hs.NewHandle(art_field->ResolveType());
if (art_field->IsStatic()) {
InitializeVarHandle(fvh.Get(), var_type, access_modes_bit_mask);
diff --git a/runtime/proxy_test.cc b/runtime/proxy_test.cc
index b055bf9..3ad3a4b 100644
--- a/runtime/proxy_test.cc
+++ b/runtime/proxy_test.cc
@@ -188,7 +188,7 @@
ArtField* field = &static_fields->At(0);
EXPECT_STREQ("interfaces", field->GetName());
EXPECT_STREQ("[Ljava/lang/Class;", field->GetTypeDescriptor());
- EXPECT_OBJ_PTR_EQ(interfacesFieldClass.Get(), field->GetType<true>());
+ EXPECT_OBJ_PTR_EQ(interfacesFieldClass.Get(), field->ResolveType());
std::string temp;
EXPECT_STREQ("L$Proxy1234;", field->GetDeclaringClass()->GetDescriptor(&temp));
EXPECT_FALSE(field->IsPrimitiveType());
@@ -197,7 +197,7 @@
field = &static_fields->At(1);
EXPECT_STREQ("throws", field->GetName());
EXPECT_STREQ("[[Ljava/lang/Class;", field->GetTypeDescriptor());
- EXPECT_OBJ_PTR_EQ(throwsFieldClass.Get(), field->GetType<true>());
+ EXPECT_OBJ_PTR_EQ(throwsFieldClass.Get(), field->ResolveType());
EXPECT_STREQ("L$Proxy1234;", field->GetDeclaringClass()->GetDescriptor(&temp));
EXPECT_FALSE(field->IsPrimitiveType());
}
diff --git a/runtime/verifier/method_verifier.cc b/runtime/verifier/method_verifier.cc
index a84d0ba..0f6244e 100644
--- a/runtime/verifier/method_verifier.cc
+++ b/runtime/verifier/method_verifier.cc
@@ -5035,7 +5035,7 @@
}
ObjPtr<mirror::Class> field_type_class =
- can_load_classes_ ? field->GetType<true>() : field->GetType<false>();
+ can_load_classes_ ? field->ResolveType() : field->LookupType();
if (field_type_class != nullptr) {
field_type = &FromClass(field->GetTypeDescriptor(),
field_type_class.Ptr(),
@@ -5183,8 +5183,8 @@
// Get the field type.
const RegType* field_type;
{
- ObjPtr<mirror::Class> field_type_class = can_load_classes_ ? field->GetType<true>() :
- field->GetType<false>();
+ ObjPtr<mirror::Class> field_type_class =
+ can_load_classes_ ? field->ResolveType() : field->LookupType();
if (field_type_class != nullptr) {
field_type = &FromClass(field->GetTypeDescriptor(),