Reland "Change well known `ClassLoader` fields to `ArtField*`."
This reverts commit 839193ee2031d28aac2ce16c4b76ad40531b07cc.
Reason for revert: Reland with a fix - make CompilerDriver
reponsible for initializing required `ClassLoader` classes
for boot image.
Test: m test-art-host-gtest
Test: testrunner.py --host --optimizing
Test: Manually run Golem benchmark ArrayListStress.
Bug: 253570082
Change-Id: I2ddb70566352f8728f089b3a6c58473270240e25
diff --git a/dex2oat/driver/compiler_driver.cc b/dex2oat/driver/compiler_driver.cc
index 1cf7e2f..fc94957 100644
--- a/dex2oat/driver/compiler_driver.cc
+++ b/dex2oat/driver/compiler_driver.cc
@@ -87,6 +87,7 @@
#include "verifier/class_verifier.h"
#include "verifier/verifier_deps.h"
#include "verifier/verifier_enums.h"
+#include "well_known_classes.h"
namespace art {
@@ -1010,13 +1011,67 @@
HashSet<std::string>* const image_classes_;
};
-// Add classes which contain intrinsics methods to the list of image classes.
-static void AddClassesContainingIntrinsics(/* out */ HashSet<std::string>* image_classes) {
-#define ADD_INTRINSIC_OWNER_CLASS(_, __, ___, ____, _____, ClassName, ______, _______) \
- image_classes->insert(ClassName);
+// Verify that classes which contain intrinsics methods are in the list of image classes.
+static void VerifyClassesContainingIntrinsicsAreImageClasses(HashSet<std::string>* image_classes) {
+#define CHECK_INTRINSIC_OWNER_CLASS(_, __, ___, ____, _____, ClassName, ______, _______) \
+ CHECK(image_classes->find(std::string_view(ClassName)) != image_classes->end());
- INTRINSICS_LIST(ADD_INTRINSIC_OWNER_CLASS)
-#undef ADD_INTRINSIC_OWNER_CLASS
+ INTRINSICS_LIST(CHECK_INTRINSIC_OWNER_CLASS)
+#undef CHECK_INTRINSIC_OWNER_CLASS
+}
+
+// We need to put classes required by app class loaders to the boot image,
+// otherwise we would not be able to store app class loaders in app images.
+static void AddClassLoaderClasses(/* out */ HashSet<std::string>* image_classes) {
+ ScopedObjectAccess soa(Thread::Current());
+ // Well known classes have been loaded and shall be added to image classes
+ // by the `RecordImageClassesVisitor`. However, there are fields with array
+ // types which we need to add to the image classes explicitly.
+ ArtField* class_loader_array_fields[] = {
+ WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoaders,
+ // BaseDexClassLoader.sharedLibraryLoadersAfter has the same array type as above.
+ WellKnownClasses::dalvik_system_DexPathList_dexElements,
+ };
+ for (ArtField* field : class_loader_array_fields) {
+ const char* field_type_descriptor = field->GetTypeDescriptor();
+ DCHECK_EQ(field_type_descriptor[0], '[');
+ image_classes->insert(field_type_descriptor);
+ }
+}
+
+static void VerifyClassLoaderClassesAreImageClasses(/* out */ HashSet<std::string>* image_classes) {
+ ScopedObjectAccess soa(Thread::Current());
+ jclass class_loader_classes[] = {
+ WellKnownClasses::dalvik_system_BaseDexClassLoader,
+ WellKnownClasses::dalvik_system_DelegateLastClassLoader,
+ WellKnownClasses::dalvik_system_DexClassLoader,
+ WellKnownClasses::dalvik_system_DexFile,
+ WellKnownClasses::dalvik_system_DexPathList,
+ WellKnownClasses::dalvik_system_DexPathList__Element,
+ WellKnownClasses::dalvik_system_InMemoryDexClassLoader,
+ WellKnownClasses::dalvik_system_PathClassLoader,
+ WellKnownClasses::java_lang_BootClassLoader,
+ WellKnownClasses::java_lang_ClassLoader,
+ };
+ for (jclass klass : class_loader_classes) {
+ std::string temp;
+ std::string_view descriptor = soa.Decode<mirror::Class>(klass)->GetDescriptor(&temp);
+ CHECK(image_classes->find(descriptor) != image_classes->end());
+ }
+ ArtField* class_loader_fields[] = {
+ WellKnownClasses::dalvik_system_BaseDexClassLoader_pathList,
+ WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoaders,
+ WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoadersAfter,
+ WellKnownClasses::dalvik_system_DexFile_cookie,
+ WellKnownClasses::dalvik_system_DexFile_fileName,
+ WellKnownClasses::dalvik_system_DexPathList_dexElements,
+ WellKnownClasses::dalvik_system_DexPathList__Element_dexFile,
+ WellKnownClasses::java_lang_ClassLoader_parent,
+ };
+ for (ArtField* field : class_loader_fields) {
+ std::string_view field_type_descriptor = field->GetTypeDescriptor();
+ CHECK(image_classes->find(field_type_descriptor) != image_classes->end());
+ }
}
// Make a list of descriptors for classes to include in the image
@@ -1030,7 +1085,10 @@
TimingLogger::ScopedTiming t("LoadImageClasses", timings);
if (GetCompilerOptions().IsBootImage()) {
- AddClassesContainingIntrinsics(image_classes);
+ // Image classes of intrinsics are loaded and shall be added
+ // to image classes by the `RecordImageClassesVisitor`.
+ // Add classes needed for storing class loaders in app images.
+ AddClassLoaderClasses(image_classes);
}
// Make a first pass to load all classes explicitly listed in the file
@@ -1101,6 +1159,11 @@
RecordImageClassesVisitor visitor(image_classes);
class_linker->VisitClasses(&visitor);
+ if (kIsDebugBuild && GetCompilerOptions().IsBootImage()) {
+ VerifyClassesContainingIntrinsicsAreImageClasses(image_classes);
+ VerifyClassLoaderClassesAreImageClasses(image_classes);
+ }
+
if (GetCompilerOptions().IsBootImage()) {
CHECK(!image_classes->empty());
}
diff --git a/dex2oat/linker/image_writer.cc b/dex2oat/linker/image_writer.cc
index 483165a..a8bd965 100644
--- a/dex2oat/linker/image_writer.cc
+++ b/dex2oat/linker/image_writer.cc
@@ -273,7 +273,7 @@
DCHECK(obj != nullptr);
Class* klass = obj->GetClass();
if (klass == WellKnownClasses::ToClass(WellKnownClasses::dalvik_system_DexFile)) {
- ArtField* field = jni::DecodeArtField(WellKnownClasses::dalvik_system_DexFile_cookie);
+ ArtField* field = WellKnownClasses::dalvik_system_DexFile_cookie;
// Null out the cookie to enable determinism. b/34090128
field->SetObject</*kTransactionActive*/false>(obj, nullptr);
}
@@ -2229,7 +2229,7 @@
// Note: The app class loader is used only for checking against the runtime
// class loader, the dex file cookie is cleared and therefore we do not need
// to run the finalizer even if we implement app image objects collection.
- ArtField* field = jni::DecodeArtField(WellKnownClasses::dalvik_system_DexFile_cookie);
+ ArtField* field = WellKnownClasses::dalvik_system_DexFile_cookie;
CHECK(field->GetObject<kWithoutReadBarrier>(ref) == nullptr);
return;
}
diff --git a/openjdkjvmti/ti_class_loader-inl.h b/openjdkjvmti/ti_class_loader-inl.h
index 29ea684..f6b0126 100644
--- a/openjdkjvmti/ti_class_loader-inl.h
+++ b/openjdkjvmti/ti_class_loader-inl.h
@@ -48,8 +48,8 @@
art::Handle<art::mirror::ClassLoader> loader,
const Visitor& visitor) {
art::StackHandleScope<1> hs(self);
- art::ArtField* element_dex_file_field = art::jni::DecodeArtField(
- art::WellKnownClasses::dalvik_system_DexPathList__Element_dexFile);
+ art::ArtField* element_dex_file_field =
+ art::WellKnownClasses::dalvik_system_DexPathList__Element_dexFile;
art::Handle<art::mirror::ObjectArray<art::mirror::Object>> dex_elements_list(
hs.NewHandle(GetDexElementList(self, loader)));
diff --git a/openjdkjvmti/ti_class_loader.cc b/openjdkjvmti/ti_class_loader.cc
index cf82534..41b8771 100644
--- a/openjdkjvmti/ti_class_loader.cc
+++ b/openjdkjvmti/ti_class_loader.cc
@@ -145,10 +145,10 @@
art::WellKnownClasses::dalvik_system_BaseDexClassLoader)->AsClass()));
// Get all the ArtFields so we can look in the BaseDexClassLoader
- art::ArtField* path_list_field = art::jni::DecodeArtField(
- art::WellKnownClasses::dalvik_system_BaseDexClassLoader_pathList);
+ art::ArtField* path_list_field =
+ art::WellKnownClasses::dalvik_system_BaseDexClassLoader_pathList;
art::ArtField* dex_path_list_element_field =
- art::jni::DecodeArtField(art::WellKnownClasses::dalvik_system_DexPathList_dexElements);
+ art::WellKnownClasses::dalvik_system_DexPathList_dexElements;
// Check if loader is a BaseDexClassLoader
art::Handle<art::mirror::Class> loader_class(hs.NewHandle(loader->GetClass()));
diff --git a/runtime/class_linker.cc b/runtime/class_linker.cc
index 663b2b9..47f3325 100644
--- a/runtime/class_linker.cc
+++ b/runtime/class_linker.cc
@@ -2681,8 +2681,7 @@
size_t hash,
Handle<mirror::ClassLoader> class_loader,
/*out*/ ObjPtr<mirror::Class>* result) {
- ArtField* field =
- jni::DecodeArtField(WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoaders);
+ ArtField* field = WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoaders;
return FindClassInSharedLibrariesHelper(soa, self, descriptor, hash, class_loader, field, result);
}
@@ -2718,8 +2717,7 @@
size_t hash,
Handle<mirror::ClassLoader> class_loader,
/*out*/ ObjPtr<mirror::Class>* result) {
- ArtField* field = jni::DecodeArtField(
- WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoadersAfter);
+ ArtField* field = WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoadersAfter;
return FindClassInSharedLibrariesHelper(soa, self, descriptor, hash, class_loader, field, result);
}
@@ -10039,8 +10037,7 @@
StackHandleScope<5> hs(self);
- ArtField* dex_elements_field =
- jni::DecodeArtField(WellKnownClasses::dalvik_system_DexPathList_dexElements);
+ ArtField* dex_elements_field = WellKnownClasses::dalvik_system_DexPathList_dexElements;
Handle<mirror::Class> dex_elements_class(hs.NewHandle(dex_elements_field->ResolveType()));
DCHECK(dex_elements_class != nullptr);
@@ -10052,14 +10049,13 @@
Handle<mirror::Class> h_dex_element_class =
hs.NewHandle(dex_elements_class->GetComponentType());
- ArtField* element_file_field =
- jni::DecodeArtField(WellKnownClasses::dalvik_system_DexPathList__Element_dexFile);
+ ArtField* element_file_field = WellKnownClasses::dalvik_system_DexPathList__Element_dexFile;
DCHECK_EQ(h_dex_element_class.Get(), element_file_field->GetDeclaringClass());
- ArtField* cookie_field = jni::DecodeArtField(WellKnownClasses::dalvik_system_DexFile_cookie);
+ ArtField* cookie_field = WellKnownClasses::dalvik_system_DexFile_cookie;
DCHECK_EQ(cookie_field->GetDeclaringClass(), element_file_field->LookupResolvedType());
- ArtField* file_name_field = jni::DecodeArtField(WellKnownClasses::dalvik_system_DexFile_fileName);
+ ArtField* file_name_field = WellKnownClasses::dalvik_system_DexFile_fileName;
DCHECK_EQ(file_name_field->GetDeclaringClass(), element_file_field->LookupResolvedType());
// Fill the elements array.
@@ -10131,15 +10127,13 @@
ObjPtr<mirror::ClassLoader>::DownCast(loader_class->AllocObject(self)));
DCHECK(h_class_loader != nullptr);
// Set DexPathList.
- ArtField* path_list_field =
- jni::DecodeArtField(WellKnownClasses::dalvik_system_BaseDexClassLoader_pathList);
+ ArtField* path_list_field = WellKnownClasses::dalvik_system_BaseDexClassLoader_pathList;
DCHECK(path_list_field != nullptr);
path_list_field->SetObject<false>(h_class_loader.Get(), h_dex_path_list.Get());
// Make a pretend boot-classpath.
// TODO: Should we scan the image?
- ArtField* const parent_field =
- jni::DecodeArtField(WellKnownClasses::java_lang_ClassLoader_parent);
+ ArtField* const parent_field = WellKnownClasses::java_lang_ClassLoader_parent;
DCHECK(parent_field != nullptr);
if (parent_loader.Get() == nullptr) {
ScopedObjectAccessUnchecked soa(self);
@@ -10151,13 +10145,12 @@
}
ArtField* shared_libraries_field =
- jni::DecodeArtField(WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoaders);
+ WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoaders;
DCHECK(shared_libraries_field != nullptr);
shared_libraries_field->SetObject<false>(h_class_loader.Get(), shared_libraries.Get());
ArtField* shared_libraries_after_field =
- jni::DecodeArtField(
- WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoadersAfter);
+ WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoadersAfter;
DCHECK(shared_libraries_after_field != nullptr);
shared_libraries_after_field->SetObject<false>(h_class_loader.Get(),
shared_libraries_after.Get());
diff --git a/runtime/class_loader_context.cc b/runtime/class_loader_context.cc
index 2ab905b..2efa2d6 100644
--- a/runtime/class_loader_context.cc
+++ b/runtime/class_loader_context.cc
@@ -1028,13 +1028,10 @@
// All supported class loaders inherit from BaseDexClassLoader.
// We need to get the DexPathList and loop through it.
- ArtField* const cookie_field =
- jni::DecodeArtField(WellKnownClasses::dalvik_system_DexFile_cookie);
- ArtField* const dex_file_field =
- jni::DecodeArtField(WellKnownClasses::dalvik_system_DexPathList__Element_dexFile);
+ ArtField* const cookie_field = WellKnownClasses::dalvik_system_DexFile_cookie;
+ ArtField* const dex_file_field = WellKnownClasses::dalvik_system_DexPathList__Element_dexFile;
ObjPtr<mirror::Object> dex_path_list =
- jni::DecodeArtField(WellKnownClasses::dalvik_system_BaseDexClassLoader_pathList)->
- GetObject(class_loader.Get());
+ WellKnownClasses::dalvik_system_BaseDexClassLoader_pathList->GetObject(class_loader.Get());
CHECK(cookie_field != nullptr);
CHECK(dex_file_field != nullptr);
if (dex_path_list == nullptr) {
@@ -1044,8 +1041,7 @@
}
// DexPathList has an array dexElements of Elements[] which each contain a dex file.
ObjPtr<mirror::Object> dex_elements_obj =
- jni::DecodeArtField(WellKnownClasses::dalvik_system_DexPathList_dexElements)->
- GetObject(dex_path_list);
+ WellKnownClasses::dalvik_system_DexPathList_dexElements->GetObject(dex_path_list);
// Loop through each dalvik.system.DexPathList$Element's dalvik.system.DexFile and look
// at the mCookie which is a DexFile vector.
if (dex_elements_obj == nullptr) {
@@ -1081,10 +1077,8 @@
std::vector<const DexFile*>* out_dex_files) REQUIRES_SHARED(Locks::mutator_lock_) {
DCHECK(dex_elements != nullptr);
- ArtField* const cookie_field =
- jni::DecodeArtField(WellKnownClasses::dalvik_system_DexFile_cookie);
- ArtField* const dex_file_field =
- jni::DecodeArtField(WellKnownClasses::dalvik_system_DexPathList__Element_dexFile);
+ ArtField* const cookie_field = WellKnownClasses::dalvik_system_DexFile_cookie;
+ ArtField* const dex_file_field = WellKnownClasses::dalvik_system_DexPathList__Element_dexFile;
const ObjPtr<mirror::Class> element_class = soa.Decode<mirror::Class>(
WellKnownClasses::dalvik_system_DexPathList__Element);
const ObjPtr<mirror::Class> dexfile_class = soa.Decode<mirror::Class>(
@@ -1198,8 +1192,7 @@
// Add the shared libraries.
StackHandleScope<5> hs(Thread::Current());
- ArtField* field =
- jni::DecodeArtField(WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoaders);
+ ArtField* field = WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoaders;
ObjPtr<mirror::Object> raw_shared_libraries = field->GetObject(class_loader.Get());
if (raw_shared_libraries != nullptr) {
Handle<mirror::ObjectArray<mirror::ClassLoader>> shared_libraries =
@@ -1217,8 +1210,7 @@
}
}
}
- ArtField* field2 = jni::DecodeArtField(
- WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoadersAfter);
+ ArtField* field2 = WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoadersAfter;
ObjPtr<mirror::Object> raw_shared_libraries_after = field2->GetObject(class_loader.Get());
if (raw_shared_libraries_after != nullptr) {
Handle<mirror::ObjectArray<mirror::ClassLoader>> shared_libraries_after =
diff --git a/runtime/class_loader_context_test.cc b/runtime/class_loader_context_test.cc
index 598670b..9d3ceb2 100644
--- a/runtime/class_loader_context_test.cc
+++ b/runtime/class_loader_context_test.cc
@@ -839,8 +839,7 @@
class_loader_1_dex_files);
// Verify the shared libraries.
- ArtField* field =
- jni::DecodeArtField(WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoaders);
+ ArtField* field = WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoaders;
ObjPtr<mirror::Object> raw_shared_libraries = field->GetObject(class_loader_1.Get());
ASSERT_TRUE(raw_shared_libraries != nullptr);
@@ -924,8 +923,7 @@
class_loader_1_dex_files);
// Verify its shared library.
- ArtField* field =
- jni::DecodeArtField(WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoaders);
+ ArtField* field = WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoaders;
ObjPtr<mirror::Object> raw_shared_libraries = field->GetObject(class_loader_1.Get());
ASSERT_TRUE(raw_shared_libraries != nullptr);
@@ -1024,8 +1022,7 @@
class_loader_1_dex_files);
// Verify its shared library.
- ArtField* field =
- jni::DecodeArtField(WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoaders);
+ ArtField* field = WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoaders;
ObjPtr<mirror::Object> raw_shared_libraries = field->GetObject(class_loader_1.Get());
ASSERT_TRUE(raw_shared_libraries != nullptr);
@@ -1139,8 +1136,7 @@
class_loader_1_dex_files);
// Verify its shared library.
- ArtField* field =
- jni::DecodeArtField(WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoaders);
+ ArtField* field = WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoaders;
ObjPtr<mirror::Object> raw_shared_libraries = field->GetObject(class_loader_1.Get());
ASSERT_TRUE(raw_shared_libraries != nullptr);
diff --git a/runtime/class_loader_utils.h b/runtime/class_loader_utils.h
index c777370..aabc4ca 100644
--- a/runtime/class_loader_utils.h
+++ b/runtime/class_loader_utils.h
@@ -82,13 +82,11 @@
REQUIRES_SHARED(Locks::mutator_lock_) {
Thread* self = soa.Self();
ObjPtr<mirror::Object> dex_path_list =
- jni::DecodeArtField(WellKnownClasses::dalvik_system_BaseDexClassLoader_pathList)->
- GetObject(class_loader.Get());
+ WellKnownClasses::dalvik_system_BaseDexClassLoader_pathList->GetObject(class_loader.Get());
if (dex_path_list != nullptr) {
// DexPathList has an array dexElements of Elements[] which each contain a dex file.
ObjPtr<mirror::Object> dex_elements_obj =
- jni::DecodeArtField(WellKnownClasses::dalvik_system_DexPathList_dexElements)->
- GetObject(dex_path_list);
+ WellKnownClasses::dalvik_system_DexPathList_dexElements->GetObject(dex_path_list);
// Loop through each dalvik.system.DexPathList$Element's dalvik.system.DexFile and look
// at the mCookie which is a DexFile vector.
if (dex_elements_obj != nullptr) {
@@ -122,10 +120,8 @@
Visitor fn,
RetType defaultReturn)
REQUIRES_SHARED(Locks::mutator_lock_) {
- ArtField* const cookie_field =
- jni::DecodeArtField(WellKnownClasses::dalvik_system_DexFile_cookie);
- ArtField* const dex_file_field =
- jni::DecodeArtField(WellKnownClasses::dalvik_system_DexPathList__Element_dexFile);
+ ArtField* const cookie_field = WellKnownClasses::dalvik_system_DexFile_cookie;
+ ArtField* const dex_file_field = WellKnownClasses::dalvik_system_DexPathList__Element_dexFile;
if (dex_file_field == nullptr || cookie_field == nullptr) {
return defaultReturn;
}
diff --git a/runtime/runtime_callbacks_test.cc b/runtime/runtime_callbacks_test.cc
index 7f64721..40194cb 100644
--- a/runtime/runtime_callbacks_test.cc
+++ b/runtime/runtime_callbacks_test.cc
@@ -303,6 +303,7 @@
TEST_F(ClassLoadCallbackRuntimeCallbacksTest, ClassLoadCallback) {
ScopedObjectAccess soa(Thread::Current());
jobject jclass_loader = LoadDex("XandY");
+ cb_.data.clear(); // Clear class loading records from `LoadDex()`, if any.
VariableSizedHandleScope hs(soa.Self());
Handle<mirror::ClassLoader> class_loader(hs.NewHandle(
soa.Decode<mirror::ClassLoader>(jclass_loader)));
diff --git a/runtime/well_known_classes.cc b/runtime/well_known_classes.cc
index 888a2ed..615028a 100644
--- a/runtime/well_known_classes.cc
+++ b/runtime/well_known_classes.cc
@@ -132,16 +132,16 @@
jmethodID WellKnownClasses::org_apache_harmony_dalvik_ddmc_DdmServer_broadcast;
jmethodID WellKnownClasses::org_apache_harmony_dalvik_ddmc_DdmServer_dispatch;
-jfieldID WellKnownClasses::dalvik_system_DexFile_cookie;
-jfieldID WellKnownClasses::dalvik_system_DexFile_fileName;
-jfieldID WellKnownClasses::dalvik_system_BaseDexClassLoader_pathList;
-jfieldID WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoaders;
-jfieldID WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoadersAfter;
-jfieldID WellKnownClasses::dalvik_system_DexPathList_dexElements;
-jfieldID WellKnownClasses::dalvik_system_DexPathList__Element_dexFile;
+ArtField* WellKnownClasses::dalvik_system_BaseDexClassLoader_pathList;
+ArtField* WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoaders;
+ArtField* WellKnownClasses::dalvik_system_BaseDexClassLoader_sharedLibraryLoadersAfter;
+ArtField* WellKnownClasses::dalvik_system_DexFile_cookie;
+ArtField* WellKnownClasses::dalvik_system_DexFile_fileName;
+ArtField* WellKnownClasses::dalvik_system_DexPathList_dexElements;
+ArtField* WellKnownClasses::dalvik_system_DexPathList__Element_dexFile;
jfieldID WellKnownClasses::dalvik_system_VMRuntime_nonSdkApiUsageConsumer;
jfieldID WellKnownClasses::java_io_FileDescriptor_descriptor;
-jfieldID WellKnownClasses::java_lang_ClassLoader_parent;
+ArtField* WellKnownClasses::java_lang_ClassLoader_parent;
jfieldID WellKnownClasses::java_lang_Thread_parkBlocker;
jfieldID WellKnownClasses::java_lang_Thread_daemon;
jfieldID WellKnownClasses::java_lang_Thread_group;
@@ -213,6 +213,23 @@
return fid;
}
+static ArtField* CacheField(ObjPtr<mirror::Class> klass,
+ bool is_static,
+ const char* name,
+ const char* signature) REQUIRES_SHARED(Locks::mutator_lock_) {
+ ArtField* field = is_static
+ ? klass->FindDeclaredStaticField(name, signature)
+ : klass->FindDeclaredInstanceField(name, signature);
+ if (UNLIKELY(field == nullptr)) {
+ std::ostringstream os;
+ klass->DumpClass(os, mirror::Class::kDumpClassFullDetail);
+ LOG(FATAL) << "Couldn't find " << (is_static ? "static" : "instance") << " field \""
+ << name << "\" with signature \"" << signature << "\": " << os.str();
+ UNREACHABLE();
+ }
+ return field;
+}
+
static jmethodID CacheMethod(JNIEnv* env, jclass c, bool is_static,
const char* name, const char* signature) {
jmethodID mid;
@@ -401,6 +418,9 @@
hiddenapi::ScopedHiddenApiEnforcementPolicySetting hiddenapi_exemption(
hiddenapi::EnforcementPolicy::kDisabled);
+ Thread* self = Thread::Current();
+ ScopedObjectAccess soa(self);
+
dalvik_system_BaseDexClassLoader_getLdLibraryPath = CacheMethod(env, dalvik_system_BaseDexClassLoader, false, "getLdLibraryPath", "()Ljava/lang/String;");
dalvik_system_VMRuntime_runFinalization = CacheMethod(env, dalvik_system_VMRuntime, true, "runFinalization", "(J)V");
dalvik_system_VMRuntime_hiddenApiUsed = CacheMethod(env, dalvik_system_VMRuntime, true, "hiddenApiUsed", "(ILjava/lang/String;Ljava/lang/String;IZ)V");
@@ -435,20 +455,38 @@
org_apache_harmony_dalvik_ddmc_DdmServer_broadcast = CacheMethod(env, org_apache_harmony_dalvik_ddmc_DdmServer, true, "broadcast", "(I)V");
org_apache_harmony_dalvik_ddmc_DdmServer_dispatch = CacheMethod(env, org_apache_harmony_dalvik_ddmc_DdmServer, true, "dispatch", "(I[BII)Lorg/apache/harmony/dalvik/ddmc/Chunk;");
- dalvik_system_BaseDexClassLoader_pathList = CacheField(env, dalvik_system_BaseDexClassLoader, false, "pathList", "Ldalvik/system/DexPathList;");
- dalvik_system_BaseDexClassLoader_sharedLibraryLoaders = CacheField(env, dalvik_system_BaseDexClassLoader, false, "sharedLibraryLoaders", "[Ljava/lang/ClassLoader;");
- dalvik_system_BaseDexClassLoader_sharedLibraryLoadersAfter = CacheField(env, dalvik_system_BaseDexClassLoader, false, "sharedLibraryLoadersAfter", "[Ljava/lang/ClassLoader;");
- dalvik_system_DexFile_cookie = CacheField(env, dalvik_system_DexFile, false, "mCookie", "Ljava/lang/Object;");
- dalvik_system_DexFile_fileName = CacheField(env, dalvik_system_DexFile, false, "mFileName", "Ljava/lang/String;");
- dalvik_system_DexPathList_dexElements = CacheField(env, dalvik_system_DexPathList, false, "dexElements", "[Ldalvik/system/DexPathList$Element;");
- dalvik_system_DexPathList__Element_dexFile = CacheField(env, dalvik_system_DexPathList__Element, false, "dexFile", "Ldalvik/system/DexFile;");
+ // TODO: There should be no thread suspension when searching for fields and methods. Enable this
+ // assertion when all well known fields and methods are converted to `ArtField*` and `ArtMethod*`.
+ // ScopedAssertNoThreadSuspension sants(__FUNCTION__);
+
+ ObjPtr<mirror::Class> d_s_bdcl = soa.Decode<mirror::Class>(dalvik_system_BaseDexClassLoader);
+ dalvik_system_BaseDexClassLoader_pathList = CacheField(
+ d_s_bdcl, /*is_static=*/ false, "pathList", "Ldalvik/system/DexPathList;");
+ dalvik_system_BaseDexClassLoader_sharedLibraryLoaders = CacheField(
+ d_s_bdcl, /*is_static=*/ false, "sharedLibraryLoaders", "[Ljava/lang/ClassLoader;");
+ dalvik_system_BaseDexClassLoader_sharedLibraryLoadersAfter = CacheField(
+ d_s_bdcl, /*is_static=*/ false, "sharedLibraryLoadersAfter", "[Ljava/lang/ClassLoader;");
+ ObjPtr<mirror::Class> d_s_df = soa.Decode<mirror::Class>(dalvik_system_DexFile);
+ dalvik_system_DexFile_cookie = CacheField(
+ d_s_df, /*is_static=*/ false, "mCookie", "Ljava/lang/Object;");
+ dalvik_system_DexFile_fileName = CacheField(
+ d_s_df, /*is_static=*/ false, "mFileName", "Ljava/lang/String;");
+ ObjPtr<mirror::Class> d_s_dpl = soa.Decode<mirror::Class>(dalvik_system_DexPathList);
+ dalvik_system_DexPathList_dexElements = CacheField(
+ d_s_dpl, /*is_static=*/ false, "dexElements", "[Ldalvik/system/DexPathList$Element;");
+ ObjPtr<mirror::Class> d_s_dpl_e = soa.Decode<mirror::Class>(dalvik_system_DexPathList__Element);
+ dalvik_system_DexPathList__Element_dexFile = CacheField(
+ d_s_dpl_e, /*is_static=*/ false, "dexFile", "Ldalvik/system/DexFile;");
+
dalvik_system_VMRuntime_nonSdkApiUsageConsumer = CacheField(env, dalvik_system_VMRuntime, true, "nonSdkApiUsageConsumer", "Ljava/util/function/Consumer;");
ScopedLocalRef<jclass> java_io_FileDescriptor(env, env->FindClass("java/io/FileDescriptor"));
java_io_FileDescriptor_descriptor = CacheField(env, java_io_FileDescriptor.get(), false, "descriptor", "I");
- java_lang_ClassLoader_parent =
- CacheField(env, java_lang_ClassLoader, false, "parent", "Ljava/lang/ClassLoader;");
+ ObjPtr<mirror::Class> j_l_cl = soa.Decode<mirror::Class>(java_lang_ClassLoader);
+ java_lang_ClassLoader_parent = CacheField(
+ j_l_cl, /*is_static=*/ false, "parent", "Ljava/lang/ClassLoader;");
+
java_lang_Thread_parkBlocker =
CacheField(env, java_lang_Thread, false, "parkBlocker", "Ljava/lang/Object;");
java_lang_Thread_daemon = CacheField(env, java_lang_Thread, false, "daemon", "Z");
diff --git a/runtime/well_known_classes.h b/runtime/well_known_classes.h
index f575317..893a50e 100644
--- a/runtime/well_known_classes.h
+++ b/runtime/well_known_classes.h
@@ -23,6 +23,7 @@
namespace art {
+class ArtField;
class ArtMethod;
namespace mirror {
@@ -145,16 +146,16 @@
static jmethodID org_apache_harmony_dalvik_ddmc_DdmServer_broadcast;
static jmethodID org_apache_harmony_dalvik_ddmc_DdmServer_dispatch;
- static jfieldID dalvik_system_BaseDexClassLoader_pathList;
- static jfieldID dalvik_system_BaseDexClassLoader_sharedLibraryLoaders;
- static jfieldID dalvik_system_BaseDexClassLoader_sharedLibraryLoadersAfter;
- static jfieldID dalvik_system_DexFile_cookie;
- static jfieldID dalvik_system_DexFile_fileName;
- static jfieldID dalvik_system_DexPathList_dexElements;
- static jfieldID dalvik_system_DexPathList__Element_dexFile;
+ static ArtField* dalvik_system_BaseDexClassLoader_pathList;
+ static ArtField* dalvik_system_BaseDexClassLoader_sharedLibraryLoaders;
+ static ArtField* dalvik_system_BaseDexClassLoader_sharedLibraryLoadersAfter;
+ static ArtField* dalvik_system_DexFile_cookie;
+ static ArtField* dalvik_system_DexFile_fileName;
+ static ArtField* dalvik_system_DexPathList_dexElements;
+ static ArtField* dalvik_system_DexPathList__Element_dexFile;
static jfieldID dalvik_system_VMRuntime_nonSdkApiUsageConsumer;
static jfieldID java_io_FileDescriptor_descriptor;
- static jfieldID java_lang_ClassLoader_parent;
+ static ArtField* java_lang_ClassLoader_parent;
static jfieldID java_lang_Thread_parkBlocker;
static jfieldID java_lang_Thread_daemon;
static jfieldID java_lang_Thread_group;