diff options
author | Elliott Hughes <enh@google.com> | 2012-05-29 09:12:18 -0700 |
---|---|---|
committer | Elliott Hughes <enh@google.com> | 2012-05-29 11:38:43 -0700 |
commit | af8d15a3267343dec135cc6df1db740c0a5c7b52 (patch) | |
tree | 8fb28f60c50ca9c6d0f2bfa14e855a2a0a980ab4 | |
parent | 8029cbe626a467b344ff84d86170d757aa12ecd4 (diff) | |
download | art-af8d15a3267343dec135cc6df1db740c0a5c7b52.zip art-af8d15a3267343dec135cc6df1db740c0a5c7b52.tar.gz art-af8d15a3267343dec135cc6df1db740c0a5c7b52.tar.bz2 |
Move the thread.cc Class*/Field*/Method* caching over to WellKnownClasses.
Just heap.cc left to do, plus maybe some of the less convincing ClassLinker
roots.
Change-Id: Ib8adf3e28e00025e0c016dcd8d7b17e42f96796c
-rw-r--r-- | src/thread.cc | 141 | ||||
-rw-r--r-- | src/well_known_classes.cc | 57 | ||||
-rw-r--r-- | src/well_known_classes.h | 21 |
3 files changed, 109 insertions, 110 deletions
diff --git a/src/thread.cc b/src/thread.cc index 3c3e56e..5c221e8 100644 --- a/src/thread.cc +++ b/src/thread.cc @@ -56,23 +56,6 @@ namespace art { pthread_key_t Thread::pthread_key_self_; -static Class* gThreadGroup = NULL; -static Class* gThreadLock = NULL; -static Field* gThread_daemon = NULL; -static Field* gThread_group = NULL; -static Field* gThread_lock = NULL; -static Field* gThread_name = NULL; -static Field* gThread_priority = NULL; -static Field* gThread_uncaughtHandler = NULL; -static Field* gThread_vmData = NULL; -static Field* gThreadGroup_mMain = NULL; -static Field* gThreadGroup_mSystem = NULL; -static Field* gThreadGroup_name = NULL; -static Field* gThreadLock_thread = NULL; -static Method* gThread_run = NULL; -static Method* gThreadGroup_removeThread = NULL; -static Method* gUncaughtExceptionHandler_uncaughtException = NULL; - static const char* kThreadNameDuringStartup = "<native thread without managed peer>"; void Thread::InitCardTable() { @@ -136,7 +119,8 @@ void* Thread::CreateCallback(void* arg) { // Invoke the 'run' method of our java.lang.Thread. CHECK(self->peer_ != NULL); Object* receiver = self->peer_; - Method* m = receiver->GetClass()->FindVirtualMethodForVirtualOrInterface(gThread_run); + jmethodID mid = WellKnownClasses::java_lang_Thread_run; + Method* m = receiver->GetClass()->FindVirtualMethodForVirtualOrInterface(DecodeMethod(mid)); m->Invoke(self, receiver, NULL, NULL); // Detach. @@ -146,11 +130,13 @@ void* Thread::CreateCallback(void* arg) { } static void SetVmData(Object* managed_thread, Thread* native_thread) { - gThread_vmData->SetInt(managed_thread, reinterpret_cast<uintptr_t>(native_thread)); + Field* f = DecodeField(WellKnownClasses::java_lang_Thread_vmData); + f->SetInt(managed_thread, reinterpret_cast<uintptr_t>(native_thread)); } Thread* Thread::FromManagedThread(Object* thread_peer) { - return reinterpret_cast<Thread*>(static_cast<uintptr_t>(gThread_vmData->GetInt(thread_peer))); + Field* f = DecodeField(WellKnownClasses::java_lang_Thread_vmData); + return reinterpret_cast<Thread*>(static_cast<uintptr_t>(f->GetInt(thread_peer))); } Thread* Thread::FromManagedThread(JNIEnv* env, jobject java_thread) { @@ -299,18 +285,20 @@ Thread* Thread::Attach(const char* thread_name, bool as_daemon, Object* thread_g return self; } -Object* Thread::GetMainThreadGroup() { - if (!Runtime::Current()->GetClassLinker()->EnsureInitialized(gThreadGroup, true, true)) { +static Object* GetWellKnownThreadGroup(jfieldID which) { + Class* c = WellKnownClasses::ToClass(WellKnownClasses::java_lang_ThreadGroup); + if (!Runtime::Current()->GetClassLinker()->EnsureInitialized(c, true, true)) { return NULL; } - return gThreadGroup_mMain->GetObject(NULL); + return DecodeField(which)->GetObject(NULL); +} + +Object* Thread::GetMainThreadGroup() { + return GetWellKnownThreadGroup(WellKnownClasses::java_lang_ThreadGroup_mainThreadGroup); } Object* Thread::GetSystemThreadGroup() { - if (!Runtime::Current()->GetClassLinker()->EnsureInitialized(gThreadGroup, true, true)) { - return NULL; - } - return gThreadGroup_mSystem->GetObject(NULL); + return GetWellKnownThreadGroup(WellKnownClasses::java_lang_ThreadGroup_systemThreadGroup); } void Thread::CreatePeer(const char* name, bool as_daemon, Object* thread_group) { @@ -344,10 +332,10 @@ void Thread::CreatePeer(const char* name, bool as_daemon, Object* thread_group) // non-null value. However, because we can run without code // available (in the compiler, in tests), we manually assign the // fields the constructor should have set. - gThread_daemon->SetBoolean(peer_, thread_is_daemon); - gThread_group->SetObject(peer_, thread_group); - gThread_name->SetObject(peer_, Decode<Object*>(env, thread_name.get())); - gThread_priority->SetInt(peer_, thread_priority); + DecodeField(WellKnownClasses::java_lang_Thread_daemon)->SetBoolean(peer_, thread_is_daemon); + DecodeField(WellKnownClasses::java_lang_Thread_group)->SetObject(peer_, thread_group); + DecodeField(WellKnownClasses::java_lang_Thread_name)->SetObject(peer_, Decode<Object*>(env, thread_name.get())); + DecodeField(WellKnownClasses::java_lang_Thread_priority)->SetInt(peer_, thread_priority); peer_thread_name.reset(GetThreadName()); } // thread_name may have been null, so don't trust this to be non-null @@ -442,7 +430,8 @@ void Thread::Dump(std::ostream& os, bool full) const { } String* Thread::GetThreadName() const { - return (peer_ != NULL) ? reinterpret_cast<String*>(gThread_name->GetObject(peer_)) : NULL; + Field* f = DecodeField(WellKnownClasses::java_lang_Thread_name); + return (peer_ != NULL) ? reinterpret_cast<String*>(f->GetObject(peer_)) : NULL; } void Thread::GetThreadName(std::string& name) const { @@ -455,12 +444,13 @@ void Thread::DumpState(std::ostream& os) const { bool is_daemon = false; if (peer_ != NULL) { - priority = gThread_priority->GetInt(peer_); - is_daemon = gThread_daemon->GetBoolean(peer_); + priority = DecodeField(WellKnownClasses::java_lang_Thread_priority)->GetInt(peer_); + is_daemon = DecodeField(WellKnownClasses::java_lang_Thread_daemon)->GetBoolean(peer_); Object* thread_group = GetThreadGroup(); if (thread_group != NULL) { - String* group_name_string = reinterpret_cast<String*>(gThreadGroup_name->GetObject(thread_group)); + Field* group_name_field = DecodeField(WellKnownClasses::java_lang_ThreadGroup_name); + String* group_name_string = reinterpret_cast<String*>(group_name_field->GetObject(thread_group)); group_name = (group_name_string != NULL) ? group_name_string->ToModifiedUtf8() : "<null>"; } } else { @@ -788,71 +778,16 @@ void Thread::Startup() { } } -// TODO: make more accessible? -static Class* FindClassOrDie(ClassLinker* class_linker, const char* descriptor) { - Class* c = class_linker->FindSystemClass(descriptor); - CHECK(c != NULL) << descriptor; - return c; -} - -// TODO: make more accessible? -static Field* FindFieldOrDie(Class* c, const char* name, const char* descriptor) { - Field* f = c->FindDeclaredInstanceField(name, descriptor); - CHECK(f != NULL) << PrettyClass(c) << " " << name << " " << descriptor; - return f; -} - -// TODO: make more accessible? -static Method* FindMethodOrDie(Class* c, const char* name, const char* signature) { - Method* m = c->FindVirtualMethod(name, signature); - CHECK(m != NULL) << PrettyClass(c) << " " << name << " " << signature; - return m; -} - -// TODO: make more accessible? -static Field* FindStaticFieldOrDie(Class* c, const char* name, const char* descriptor) { - Field* f = c->FindDeclaredStaticField(name, descriptor); - CHECK(f != NULL) << PrettyClass(c) << " " << name << " " << descriptor; - return f; -} - void Thread::FinishStartup() { CHECK(Runtime::Current()->IsStarted()); Thread* self = Thread::Current(); - // Need to be kRunnable for FindClass - ScopedThreadStateChange tsc(self, kRunnable); - - // Now the ClassLinker is ready, we can find the various Class*, Field*, and Method*s we need. - ClassLinker* class_linker = Runtime::Current()->GetClassLinker(); - - Class* Thread_class = FindClassOrDie(class_linker, "Ljava/lang/Thread;"); - Class* UncaughtExceptionHandler_class = FindClassOrDie(class_linker, "Ljava/lang/Thread$UncaughtExceptionHandler;"); - gThreadGroup = FindClassOrDie(class_linker, "Ljava/lang/ThreadGroup;"); - gThreadLock = FindClassOrDie(class_linker, "Ljava/lang/ThreadLock;"); - - gThread_daemon = FindFieldOrDie(Thread_class, "daemon", "Z"); - gThread_group = FindFieldOrDie(Thread_class, "group", "Ljava/lang/ThreadGroup;"); - gThread_lock = FindFieldOrDie(Thread_class, "lock", "Ljava/lang/ThreadLock;"); - gThread_name = FindFieldOrDie(Thread_class, "name", "Ljava/lang/String;"); - gThread_priority = FindFieldOrDie(Thread_class, "priority", "I"); - gThread_uncaughtHandler = FindFieldOrDie(Thread_class, "uncaughtHandler", "Ljava/lang/Thread$UncaughtExceptionHandler;"); - gThread_vmData = FindFieldOrDie(Thread_class, "vmData", "I"); - gThreadGroup_name = FindFieldOrDie(gThreadGroup, "name", "Ljava/lang/String;"); - gThreadGroup_mMain = FindStaticFieldOrDie(gThreadGroup, "mMain", "Ljava/lang/ThreadGroup;"); - gThreadGroup_mSystem = FindStaticFieldOrDie(gThreadGroup, "mSystem", "Ljava/lang/ThreadGroup;"); - gThreadLock_thread = FindFieldOrDie(gThreadLock, "thread", "Ljava/lang/Thread;"); - - gThread_run = FindMethodOrDie(Thread_class, "run", "()V"); - gThreadGroup_removeThread = FindMethodOrDie(gThreadGroup, "removeThread", "(Ljava/lang/Thread;)V"); - gUncaughtExceptionHandler_uncaughtException = FindMethodOrDie(UncaughtExceptionHandler_class, - "uncaughtException", "(Ljava/lang/Thread;Ljava/lang/Throwable;)V"); - // Finish attaching the main thread. + ScopedThreadStateChange tsc(self, kRunnable); Thread::Current()->CreatePeer("main", false, Thread::GetMainThreadGroup()); InitBoxingMethods(); - class_linker->RunRootClinits(); + Runtime::Current()->GetClassLinker()->RunRootClinits(); } void Thread::Shutdown() { @@ -860,14 +795,16 @@ void Thread::Shutdown() { } uint32_t Thread::LockOwnerFromThreadLock(Object* thread_lock) { - if (thread_lock == NULL || thread_lock->GetClass() != gThreadLock) { + if (thread_lock == NULL || thread_lock->GetClass() != WellKnownClasses::ToClass(WellKnownClasses::java_lang_ThreadLock)) { return ThreadList::kInvalidId; } - Object* managed_thread = gThreadLock_thread->GetObject(thread_lock); + Field* thread_field = DecodeField(WellKnownClasses::java_lang_ThreadLock_thread); + Object* managed_thread = thread_field->GetObject(thread_lock); if (managed_thread == NULL) { return ThreadList::kInvalidId; } - uintptr_t vmData = static_cast<uintptr_t>(gThread_vmData->GetInt(managed_thread)); + Field* vmData_field = DecodeField(WellKnownClasses::java_lang_Thread_vmData); + uintptr_t vmData = static_cast<uintptr_t>(vmData_field->GetInt(managed_thread)); Thread* thread = reinterpret_cast<Thread*>(vmData); if (thread == NULL) { return ThreadList::kInvalidId; @@ -949,7 +886,7 @@ void Thread::Destroy() { // Thread.join() is implemented as an Object.wait() on the Thread.lock // object. Signal anyone who is waiting. - Object* lock = gThread_lock->GetObject(peer_); + Object* lock = DecodeField(WellKnownClasses::java_lang_Thread_lock)->GetObject(peer_); // (This conditional is only needed for tests, where Thread.lock won't have been set.) if (lock != NULL) { lock->MonitorEnter(self); @@ -989,14 +926,15 @@ void Thread::HandleUncaughtExceptions() { ClearException(); // If the thread has its own handler, use that. - Object* handler = gThread_uncaughtHandler->GetObject(peer_); + Object* handler = DecodeField(WellKnownClasses::java_lang_Thread_uncaughtHandler)->GetObject(peer_); if (handler == NULL) { // Otherwise use the thread group's default handler. handler = GetThreadGroup(); } // Call the handler. - Method* m = handler->GetClass()->FindVirtualMethodForVirtualOrInterface(gUncaughtExceptionHandler_uncaughtException); + jmethodID mid = WellKnownClasses::java_lang_Thread$UncaughtExceptionHandler_uncaughtException; + Method* m = handler->GetClass()->FindVirtualMethodForVirtualOrInterface(DecodeMethod(mid)); JValue args[2]; args[0].SetL(peer_); args[1].SetL(exception); @@ -1007,7 +945,7 @@ void Thread::HandleUncaughtExceptions() { } Object* Thread::GetThreadGroup() const { - return gThread_group->GetObject(peer_); + return DecodeField(WellKnownClasses::java_lang_Thread_group)->GetObject(peer_); } void Thread::RemoveFromThreadGroup() { @@ -1015,7 +953,8 @@ void Thread::RemoveFromThreadGroup() { // group can be null if we're in the compiler or a test. Object* group = GetThreadGroup(); if (group != NULL) { - Method* m = group->GetClass()->FindVirtualMethodForVirtualOrInterface(gThreadGroup_removeThread); + jmethodID mid = WellKnownClasses::java_lang_ThreadGroup_removeThread; + Method* m = group->GetClass()->FindVirtualMethodForVirtualOrInterface(DecodeMethod(mid)); JValue args[1]; args[0].SetL(peer_); m->Invoke(this, group, args, NULL); @@ -1863,7 +1802,7 @@ bool Thread::HoldsLock(Object* object) { } bool Thread::IsDaemon() { - return gThread_daemon->GetBoolean(peer_); + return DecodeField(WellKnownClasses::java_lang_Thread_daemon)->GetBoolean(peer_); } #if !defined(ART_USE_LLVM_COMPILER) diff --git a/src/well_known_classes.cc b/src/well_known_classes.cc index 7e21a66..c89771a 100644 --- a/src/well_known_classes.cc +++ b/src/well_known_classes.cc @@ -20,6 +20,7 @@ #include "logging.h" #include "ScopedLocalRef.h" +#include "thread.h" namespace art { @@ -34,6 +35,9 @@ jclass WellKnownClasses::java_lang_reflect_Method; jclass WellKnownClasses::java_lang_reflect_Proxy; jclass WellKnownClasses::java_lang_reflect_UndeclaredThrowableException; jclass WellKnownClasses::java_lang_Thread; +jclass WellKnownClasses::java_lang_Thread$UncaughtExceptionHandler; +jclass WellKnownClasses::java_lang_ThreadGroup; +jclass WellKnownClasses::java_lang_ThreadLock; jclass WellKnownClasses::java_nio_ReadWriteDirectByteBuffer; jclass WellKnownClasses::org_apache_harmony_dalvik_ddmc_Chunk; jclass WellKnownClasses::org_apache_harmony_dalvik_ddmc_DdmServer; @@ -44,10 +48,24 @@ jmethodID WellKnownClasses::java_lang_Daemons_requestHeapTrim; jmethodID WellKnownClasses::java_lang_Daemons_start; jmethodID WellKnownClasses::java_lang_reflect_InvocationHandler_invoke; jmethodID WellKnownClasses::java_lang_Thread_init; +jmethodID WellKnownClasses::java_lang_Thread_run; +jmethodID WellKnownClasses::java_lang_Thread$UncaughtExceptionHandler_uncaughtException; +jmethodID WellKnownClasses::java_lang_ThreadGroup_removeThread; jmethodID WellKnownClasses::java_nio_ReadWriteDirectByteBuffer_init; jmethodID WellKnownClasses::org_apache_harmony_dalvik_ddmc_DdmServer_broadcast; jmethodID WellKnownClasses::org_apache_harmony_dalvik_ddmc_DdmServer_dispatch; +jfieldID WellKnownClasses::java_lang_Thread_daemon; +jfieldID WellKnownClasses::java_lang_Thread_group; +jfieldID WellKnownClasses::java_lang_Thread_lock; +jfieldID WellKnownClasses::java_lang_Thread_name; +jfieldID WellKnownClasses::java_lang_Thread_priority; +jfieldID WellKnownClasses::java_lang_Thread_uncaughtHandler; +jfieldID WellKnownClasses::java_lang_Thread_vmData; +jfieldID WellKnownClasses::java_lang_ThreadGroup_mainThreadGroup; +jfieldID WellKnownClasses::java_lang_ThreadGroup_name; +jfieldID WellKnownClasses::java_lang_ThreadGroup_systemThreadGroup; +jfieldID WellKnownClasses::java_lang_ThreadLock_thread; jfieldID WellKnownClasses::java_lang_reflect_Proxy_h; jfieldID WellKnownClasses::java_nio_ReadWriteDirectByteBuffer_capacity; jfieldID WellKnownClasses::java_nio_ReadWriteDirectByteBuffer_effectiveDirectAddress; @@ -64,8 +82,8 @@ static jclass CacheClass(JNIEnv* env, const char* jni_class_name) { return reinterpret_cast<jclass>(env->NewGlobalRef(c.get())); } -static jfieldID CacheField(JNIEnv* env, jclass c, const char* name, const char* signature) { - jfieldID fid = env->GetFieldID(c, name, signature); +static jfieldID CacheField(JNIEnv* env, jclass c, bool is_static, const char* name, const char* signature) { + jfieldID fid = is_static ? env->GetStaticFieldID(c, name, signature) : env->GetFieldID(c, name, signature); if (fid == NULL) { LOG(FATAL) << "Couldn't find field \"" << name << "\" with signature \"" << signature << "\""; } @@ -92,6 +110,9 @@ void WellKnownClasses::Init(JNIEnv* env) { java_lang_reflect_Proxy = CacheClass(env, "java/lang/reflect/Proxy"); java_lang_reflect_UndeclaredThrowableException = CacheClass(env, "java/lang/reflect/UndeclaredThrowableException"); java_lang_Thread = CacheClass(env, "java/lang/Thread"); + java_lang_Thread$UncaughtExceptionHandler = CacheClass(env, "java/lang/Thread$UncaughtExceptionHandler"); + java_lang_ThreadGroup = CacheClass(env, "java/lang/ThreadGroup"); + java_lang_ThreadLock = CacheClass(env, "java/lang/ThreadLock"); java_nio_ReadWriteDirectByteBuffer = CacheClass(env, "java/nio/ReadWriteDirectByteBuffer"); org_apache_harmony_dalvik_ddmc_Chunk = CacheClass(env, "org/apache/harmony/dalvik/ddmc/Chunk"); org_apache_harmony_dalvik_ddmc_DdmServer = CacheClass(env, "org/apache/harmony/dalvik/ddmc/DdmServer"); @@ -102,17 +123,35 @@ void WellKnownClasses::Init(JNIEnv* env) { java_lang_Daemons_start = CacheMethod(env, java_lang_Daemons, true, "start", "()V"); java_lang_reflect_InvocationHandler_invoke = CacheMethod(env, java_lang_reflect_InvocationHandler, false, "invoke", "(Ljava/lang/Object;Ljava/lang/reflect/Method;[Ljava/lang/Object;)Ljava/lang/Object;"); java_lang_Thread_init = CacheMethod(env, java_lang_Thread, false, "<init>", "(Ljava/lang/ThreadGroup;Ljava/lang/String;IZ)V"); + java_lang_Thread_run = CacheMethod(env, java_lang_Thread, false, "run", "()V"); + java_lang_Thread$UncaughtExceptionHandler_uncaughtException = CacheMethod(env, java_lang_Thread$UncaughtExceptionHandler, false, "uncaughtException", "(Ljava/lang/Thread;Ljava/lang/Throwable;)V"); + java_lang_ThreadGroup_removeThread = CacheMethod(env, java_lang_ThreadGroup, false, "removeThread", "(Ljava/lang/Thread;)V"); java_nio_ReadWriteDirectByteBuffer_init = CacheMethod(env, java_nio_ReadWriteDirectByteBuffer, false, "<init>", "(II)V"); 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;"); - java_lang_reflect_Proxy_h = CacheField(env, java_lang_reflect_Proxy, "h", "Ljava/lang/reflect/InvocationHandler;"); - java_nio_ReadWriteDirectByteBuffer_capacity = CacheField(env, java_nio_ReadWriteDirectByteBuffer, "capacity", "I"); - java_nio_ReadWriteDirectByteBuffer_effectiveDirectAddress = CacheField(env, java_nio_ReadWriteDirectByteBuffer, "effectiveDirectAddress", "I"); - org_apache_harmony_dalvik_ddmc_Chunk_data = CacheField(env, org_apache_harmony_dalvik_ddmc_Chunk, "data", "[B"); - org_apache_harmony_dalvik_ddmc_Chunk_length = CacheField(env, org_apache_harmony_dalvik_ddmc_Chunk, "length", "I"); - org_apache_harmony_dalvik_ddmc_Chunk_offset = CacheField(env, org_apache_harmony_dalvik_ddmc_Chunk, "offset", "I"); - org_apache_harmony_dalvik_ddmc_Chunk_type = CacheField(env, org_apache_harmony_dalvik_ddmc_Chunk, "type", "I"); + java_lang_Thread_daemon = CacheField(env, java_lang_Thread, false, "daemon", "Z"); + java_lang_Thread_group = CacheField(env, java_lang_Thread, false, "group", "Ljava/lang/ThreadGroup;"); + java_lang_Thread_lock = CacheField(env, java_lang_Thread, false, "lock", "Ljava/lang/ThreadLock;"); + java_lang_Thread_name = CacheField(env, java_lang_Thread, false, "name", "Ljava/lang/String;"); + java_lang_Thread_priority = CacheField(env, java_lang_Thread, false, "priority", "I"); + java_lang_Thread_uncaughtHandler = CacheField(env, java_lang_Thread, false, "uncaughtHandler", "Ljava/lang/Thread$UncaughtExceptionHandler;"); + java_lang_Thread_vmData = CacheField(env, java_lang_Thread, false, "vmData", "I"); + java_lang_ThreadGroup_mainThreadGroup = CacheField(env, java_lang_ThreadGroup, true, "mainThreadGroup", "Ljava/lang/ThreadGroup;"); + java_lang_ThreadGroup_name = CacheField(env, java_lang_ThreadGroup, false, "name", "Ljava/lang/String;"); + java_lang_ThreadGroup_systemThreadGroup = CacheField(env, java_lang_ThreadGroup, true, "systemThreadGroup", "Ljava/lang/ThreadGroup;"); + java_lang_ThreadLock_thread = CacheField(env, java_lang_ThreadLock, false, "thread", "Ljava/lang/Thread;"); + java_lang_reflect_Proxy_h = CacheField(env, java_lang_reflect_Proxy, false, "h", "Ljava/lang/reflect/InvocationHandler;"); + java_nio_ReadWriteDirectByteBuffer_capacity = CacheField(env, java_nio_ReadWriteDirectByteBuffer, false, "capacity", "I"); + java_nio_ReadWriteDirectByteBuffer_effectiveDirectAddress = CacheField(env, java_nio_ReadWriteDirectByteBuffer, false, "effectiveDirectAddress", "I"); + org_apache_harmony_dalvik_ddmc_Chunk_data = CacheField(env, org_apache_harmony_dalvik_ddmc_Chunk, false, "data", "[B"); + org_apache_harmony_dalvik_ddmc_Chunk_length = CacheField(env, org_apache_harmony_dalvik_ddmc_Chunk, false, "length", "I"); + org_apache_harmony_dalvik_ddmc_Chunk_offset = CacheField(env, org_apache_harmony_dalvik_ddmc_Chunk, false, "offset", "I"); + org_apache_harmony_dalvik_ddmc_Chunk_type = CacheField(env, org_apache_harmony_dalvik_ddmc_Chunk, false, "type", "I"); +} + +Class* WellKnownClasses::ToClass(jclass global_jclass) { + return reinterpret_cast<Class*>(Thread::Current()->DecodeJObject(global_jclass)); } } // namespace art diff --git a/src/well_known_classes.h b/src/well_known_classes.h index 5d45938..613c47e 100644 --- a/src/well_known_classes.h +++ b/src/well_known_classes.h @@ -21,6 +21,8 @@ namespace art { +class Class; + // Various classes used in JNI. We cache them so we don't have to keep looking // them up. Similar to libcore's JniConstants (except there's no overlap, so // we keep them separate). @@ -28,6 +30,8 @@ namespace art { struct WellKnownClasses { static void Init(JNIEnv* env); + static Class* ToClass(jclass global_jclass); + static jclass com_android_dex_Dex; static jclass java_lang_ClassLoader; static jclass java_lang_ClassNotFoundException; @@ -39,6 +43,9 @@ struct WellKnownClasses { static jclass java_lang_reflect_Proxy; static jclass java_lang_reflect_UndeclaredThrowableException; static jclass java_lang_Thread; + static jclass java_lang_ThreadGroup; + static jclass java_lang_ThreadLock; + static jclass java_lang_Thread$UncaughtExceptionHandler; static jclass java_nio_ReadWriteDirectByteBuffer; static jclass org_apache_harmony_dalvik_ddmc_Chunk; static jclass org_apache_harmony_dalvik_ddmc_DdmServer; @@ -49,11 +56,25 @@ struct WellKnownClasses { static jmethodID java_lang_Daemons_start; static jmethodID java_lang_reflect_InvocationHandler_invoke; static jmethodID java_lang_Thread_init; + static jmethodID java_lang_Thread_run; + static jmethodID java_lang_Thread$UncaughtExceptionHandler_uncaughtException; + static jmethodID java_lang_ThreadGroup_removeThread; static jmethodID java_nio_ReadWriteDirectByteBuffer_init; static jmethodID org_apache_harmony_dalvik_ddmc_DdmServer_broadcast; static jmethodID org_apache_harmony_dalvik_ddmc_DdmServer_dispatch; static jfieldID java_lang_reflect_Proxy_h; + static jfieldID java_lang_Thread_daemon; + static jfieldID java_lang_Thread_group; + static jfieldID java_lang_Thread_lock; + static jfieldID java_lang_Thread_name; + static jfieldID java_lang_Thread_priority; + static jfieldID java_lang_Thread_uncaughtHandler; + static jfieldID java_lang_Thread_vmData; + static jfieldID java_lang_ThreadGroup_mainThreadGroup; + static jfieldID java_lang_ThreadGroup_name; + static jfieldID java_lang_ThreadGroup_systemThreadGroup; + static jfieldID java_lang_ThreadLock_thread; static jfieldID java_nio_ReadWriteDirectByteBuffer_capacity; static jfieldID java_nio_ReadWriteDirectByteBuffer_effectiveDirectAddress; static jfieldID org_apache_harmony_dalvik_ddmc_Chunk_data; |