diff --git a/whale/src/android/art/art_hook_param.h b/whale/src/android/art/art_hook_param.h index dc11eb8..ecaef27 100644 --- a/whale/src/android/art/art_hook_param.h +++ b/whale/src/android/art/art_hook_param.h @@ -18,7 +18,7 @@ struct ArtHookParam final { u4 origin_code_item_off; jobject origin_method_; jobject hooked_method_; - ptr_t decl_class_; + volatile ptr_t decl_class_; jobject class_Loader_; jmethodID hooked_native_method_; jmethodID origin_native_method_; diff --git a/whale/src/android/art/art_jni_trampoline.cc b/whale/src/android/art/art_jni_trampoline.cc index a2384c6..f0f1a82 100644 --- a/whale/src/android/art/art_jni_trampoline.cc +++ b/whale/src/android/art/art_jni_trampoline.cc @@ -12,6 +12,10 @@ namespace whale { namespace art { static void UnBoxValue(JNIEnv *env, jvalue *jv, jobject obj, char type) { + if (obj == nullptr) { + jv->l = obj; + return; + } switch (type) { case 'I': jv->i = Types::FromInteger(env, obj); diff --git a/whale/src/android/art/art_runtime.cc b/whale/src/android/art/art_runtime.cc index 66ccdaa..f763fa4 100644 --- a/whale/src/android/art/art_runtime.cc +++ b/whale/src/android/art/art_runtime.cc @@ -175,6 +175,7 @@ bool ArtRuntime::OnLoad(JavaVM *vm, JNIEnv *env, jclass java_class) { CHECK_FIELD(quick_generic_jni_trampoline, nullptr) class_linker_objects_.quick_generic_jni_trampoline_ = quick_generic_jni_trampoline; + pthread_mutex_init(&mutex, nullptr); EnforceDisableHiddenAPIPolicy(); return true; @@ -267,19 +268,23 @@ ArtRuntime::InvokeOriginalMethod(jlong slot, jobject this_object, jobjectArray a ArtMethod hooked_method(param->hooked_native_method_); ptr_t decl_class = hooked_method.GetDeclaringClass(); if (param->decl_class_ != decl_class) { - ScopedSuspendAll suspend_all; - LOG(INFO) - << "Notice: MovingGC cause the GcRoot References changed."; - jobject origin_java_method = hooked_method.Clone(env, param->origin_access_flags); - jmethodID origin_jni_method = env->FromReflectedMethod(origin_java_method); - ArtMethod origin_method(origin_jni_method); - origin_method.SetEntryPointFromQuickCompiledCode(param->origin_compiled_code_); - origin_method.SetEntryPointFromJni(param->origin_jni_code_); - origin_method.SetDexCodeItemOffset(param->origin_code_item_off); - param->origin_native_method_ = origin_jni_method; - env->DeleteGlobalRef(param->origin_method_); - param->origin_method_ = env->NewGlobalRef(origin_java_method); - param->decl_class_ = decl_class; + pthread_mutex_lock(&mutex); + if (param->decl_class_ != decl_class) { + ScopedSuspendAll suspend_all; + LOG(INFO) + << "Notice: MovingGC cause the GcRoot References changed."; + jobject origin_java_method = hooked_method.Clone(env, param->origin_access_flags); + jmethodID origin_jni_method = env->FromReflectedMethod(origin_java_method); + ArtMethod origin_method(origin_jni_method); + origin_method.SetEntryPointFromQuickCompiledCode(param->origin_compiled_code_); + origin_method.SetEntryPointFromJni(param->origin_jni_code_); + origin_method.SetDexCodeItemOffset(param->origin_code_item_off); + param->origin_native_method_ = origin_jni_method; + env->DeleteGlobalRef(param->origin_method_); + param->origin_method_ = env->NewGlobalRef(origin_java_method); + param->decl_class_ = decl_class; + } + pthread_mutex_unlock(&mutex); } jobject ret = env->CallNonvirtualObjectMethod( diff --git a/whale/src/android/art/art_runtime.h b/whale/src/android/art/art_runtime.h index a0da8e5..fe88cde 100644 --- a/whale/src/android/art/art_runtime.h +++ b/whale/src/android/art/art_runtime.h @@ -137,6 +137,7 @@ class ArtRuntime final { ClassLinkerObjects class_linker_objects_; ArtMethodOffsets method_offset_; std::map hooked_method_map_; + pthread_mutex_t mutex; bool EnforceDisableHiddenAPIPolicyImpl();