Handlerize methods across some GC points.
Bug: 12687968
Change-Id: I0d5b0a78488ba76db4d25991d8db95b24bb624e9
diff --git a/runtime/entrypoints/quick/quick_trampoline_entrypoints.cc b/runtime/entrypoints/quick/quick_trampoline_entrypoints.cc
index 1dbbb70..f970ef8 100644
--- a/runtime/entrypoints/quick/quick_trampoline_entrypoints.cc
+++ b/runtime/entrypoints/quick/quick_trampoline_entrypoints.cc
@@ -492,19 +492,18 @@
self->PushShadowFrame(shadow_frame);
self->EndAssertNoThreadSuspension(old_cause);
- if (method->IsStatic() && !method->GetDeclaringClass()->IsInitialized()) {
+ StackHandleScope<1> hs(self);
+ MethodHelper mh(hs.NewHandle(method));
+ if (mh.Get()->IsStatic() && !mh.Get()->GetDeclaringClass()->IsInitialized()) {
// Ensure static method's class is initialized.
StackHandleScope<1> hs(self);
- Handle<mirror::Class> h_class(hs.NewHandle(method->GetDeclaringClass()));
+ Handle<mirror::Class> h_class(hs.NewHandle(mh.Get()->GetDeclaringClass()));
if (!Runtime::Current()->GetClassLinker()->EnsureInitialized(self, h_class, true, true)) {
- DCHECK(Thread::Current()->IsExceptionPending()) << PrettyMethod(method);
+ DCHECK(Thread::Current()->IsExceptionPending()) << PrettyMethod(mh.Get());
self->PopManagedStackFragment(fragment);
return 0;
}
}
-
- StackHandleScope<1> hs(self);
- MethodHelper mh(hs.NewHandle(method));
JValue result = interpreter::EnterInterpreterFromStub(self, mh, code_item, *shadow_frame);
// Pop transition.
self->PopManagedStackFragment(fragment);
diff --git a/runtime/interpreter/interpreter.cc b/runtime/interpreter/interpreter.cc
index 07224ef..8fb1712 100644
--- a/runtime/interpreter/interpreter.cc
+++ b/runtime/interpreter/interpreter.cc
@@ -529,10 +529,10 @@
}
self->PushShadowFrame(shadow_frame);
- ArtMethod* method = shadow_frame->GetMethod();
+ DCHECK_EQ(shadow_frame->GetMethod(), mh.Get());
// Ensure static methods are initialized.
- if (method->IsStatic()) {
- mirror::Class* declaring_class = method->GetDeclaringClass();
+ if (mh.Get()->IsStatic()) {
+ mirror::Class* declaring_class = mh.Get()->GetDeclaringClass();
if (UNLIKELY(!declaring_class->IsInitialized())) {
StackHandleScope<1> hs(self);
HandleWrapper<Class> h_declaring_class(hs.NewHandleWrapper(&declaring_class));
@@ -546,15 +546,15 @@
}
}
- if (LIKELY(!method->IsNative())) {
+ if (LIKELY(!mh.Get()->IsNative())) {
result->SetJ(Execute(self, mh, code_item, *shadow_frame, JValue()).GetJ());
} else {
// We don't expect to be asked to interpret native code (which is entered via a JNI compiler
// generated stub) except during testing and image writing.
CHECK(!Runtime::Current()->IsStarted());
- Object* receiver = method->IsStatic() ? nullptr : shadow_frame->GetVRegReference(0);
- uint32_t* args = shadow_frame->GetVRegArgs(method->IsStatic() ? 0 : 1);
- UnstartedRuntimeJni(self, method, receiver, args, result);
+ Object* receiver = mh.Get()->IsStatic() ? nullptr : shadow_frame->GetVRegReference(0);
+ uint32_t* args = shadow_frame->GetVRegArgs(mh.Get()->IsStatic() ? 0 : 1);
+ UnstartedRuntimeJni(self, mh.Get(), receiver, args, result);
}
self->PopShadowFrame();
diff --git a/runtime/interpreter/interpreter_common.cc b/runtime/interpreter/interpreter_common.cc
index 733f1d1..52583ae 100644
--- a/runtime/interpreter/interpreter_common.cc
+++ b/runtime/interpreter/interpreter_common.cc
@@ -569,9 +569,9 @@
// We need to do runtime check on reference assignment. We need to load the shorty
// to get the exact type of each reference argument.
- const DexFile::TypeList* params = method->GetParameterTypeList();
+ const DexFile::TypeList* params = mh.Get()->GetParameterTypeList();
uint32_t shorty_len = 0;
- const char* shorty = method->GetShorty(&shorty_len);
+ const char* shorty = mh.Get()->GetShorty(&shorty_len);
// TODO: find a cleaner way to separate non-range and range information without duplicating code.
uint32_t arg[5]; // only used in invoke-XXX.
@@ -585,7 +585,7 @@
// Handle receiver apart since it's not part of the shorty.
size_t dest_reg = first_dest_reg;
size_t arg_offset = 0;
- if (!method->IsStatic()) {
+ if (!mh.Get()->IsStatic()) {
size_t receiver_reg = is_range ? vregC : arg[0];
new_shadow_frame->SetVRegReference(dest_reg, shadow_frame.GetVRegReference(receiver_reg));
++dest_reg;
@@ -609,7 +609,7 @@
self->ThrowNewExceptionF(self->GetCurrentLocationForThrow(),
"Ljava/lang/VirtualMachineError;",
"Invoking %s with bad arg %d, type '%s' not instance of '%s'",
- method->GetName(), shorty_pos,
+ mh.Get()->GetName(), shorty_pos,
o->GetClass()->GetDescriptor(&temp1),
arg_type->GetDescriptor(&temp2));
return false;
@@ -658,15 +658,15 @@
// Do the call now.
if (LIKELY(Runtime::Current()->IsStarted())) {
- if (kIsDebugBuild && method->GetEntryPointFromInterpreter() == nullptr) {
- LOG(FATAL) << "Attempt to invoke non-executable method: " << PrettyMethod(method);
+ if (kIsDebugBuild && mh.Get()->GetEntryPointFromInterpreter() == nullptr) {
+ LOG(FATAL) << "Attempt to invoke non-executable method: " << PrettyMethod(mh.Get());
}
if (kIsDebugBuild && Runtime::Current()->GetInstrumentation()->IsForcedInterpretOnly() &&
- !method->IsNative() && !method->IsProxyMethod() &&
- method->GetEntryPointFromInterpreter() == artInterpreterToCompiledCodeBridge) {
- LOG(FATAL) << "Attempt to call compiled code when -Xint: " << PrettyMethod(method);
+ !mh.Get()->IsNative() && !mh.Get()->IsProxyMethod() &&
+ mh.Get()->GetEntryPointFromInterpreter() == artInterpreterToCompiledCodeBridge) {
+ LOG(FATAL) << "Attempt to call compiled code when -Xint: " << PrettyMethod(mh.Get());
}
- (method->GetEntryPointFromInterpreter())(self, mh, code_item, new_shadow_frame, result);
+ (mh.Get()->GetEntryPointFromInterpreter())(self, mh, code_item, new_shadow_frame, result);
} else {
UnstartedRuntimeInvoke(self, mh, code_item, new_shadow_frame, result, first_dest_reg);
}