ART: Fix VerifyObject runtime verification
Update some bit-rotted code to work again. Most tests now work, for
some the verification overhead results in a timeout.
Change-Id: Ieab4f2de474a05e915e24abc93da3c2eeed996eb
diff --git a/runtime/entrypoints/quick/callee_save_frame.h b/runtime/entrypoints/quick/callee_save_frame.h
index 8cd6ca6..3bcaf93 100644
--- a/runtime/entrypoints/quick/callee_save_frame.h
+++ b/runtime/entrypoints/quick/callee_save_frame.h
@@ -38,22 +38,24 @@
class ScopedQuickEntrypointChecks {
public:
- explicit ScopedQuickEntrypointChecks(Thread *self) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_)
- : self_(self) {
- if (kIsDebugBuild) {
+ explicit ScopedQuickEntrypointChecks(Thread *self,
+ bool entry_check = kIsDebugBuild,
+ bool exit_check = kIsDebugBuild)
+ SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) : self_(self), exit_check_(exit_check) {
+ if (entry_check) {
TestsOnEntry();
}
}
- explicit ScopedQuickEntrypointChecks() SHARED_LOCKS_REQUIRED(Locks::mutator_lock_)
- : self_(kIsDebugBuild ? Thread::Current() : nullptr) {
+ ScopedQuickEntrypointChecks() SHARED_LOCKS_REQUIRED(Locks::mutator_lock_)
+ : self_(kIsDebugBuild ? Thread::Current() : nullptr), exit_check_(kIsDebugBuild) {
if (kIsDebugBuild) {
TestsOnEntry();
}
}
~ScopedQuickEntrypointChecks() SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) {
- if (kIsDebugBuild) {
+ if (exit_check_) {
TestsOnExit();
}
}
@@ -70,6 +72,7 @@
}
Thread* const self_;
+ bool exit_check_;
};
static constexpr size_t GetCalleeSaveFrameSize(InstructionSet isa, Runtime::CalleeSaveType type) {
diff --git a/runtime/entrypoints/quick/quick_instrumentation_entrypoints.cc b/runtime/entrypoints/quick/quick_instrumentation_entrypoints.cc
index eb1b105..2bb73ef 100644
--- a/runtime/entrypoints/quick/quick_instrumentation_entrypoints.cc
+++ b/runtime/entrypoints/quick/quick_instrumentation_entrypoints.cc
@@ -29,7 +29,9 @@
Thread* self,
uintptr_t lr)
SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) {
- ScopedQuickEntrypointChecks sqec(self);
+ // Instrumentation changes the stack. Thus, when exiting, the stack cannot be verified, so skip
+ // that part.
+ ScopedQuickEntrypointChecks sqec(self, kIsDebugBuild, false);
instrumentation::Instrumentation* instrumentation = Runtime::Current()->GetInstrumentation();
const void* result;
if (instrumentation->IsDeoptimized(method)) {
diff --git a/runtime/entrypoints/quick/quick_trampoline_entrypoints.cc b/runtime/entrypoints/quick/quick_trampoline_entrypoints.cc
index 838427f..227c5b0 100644
--- a/runtime/entrypoints/quick/quick_trampoline_entrypoints.cc
+++ b/runtime/entrypoints/quick/quick_trampoline_entrypoints.cc
@@ -823,7 +823,10 @@
Thread* self,
StackReference<mirror::ArtMethod>* sp)
SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) {
- ScopedQuickEntrypointChecks sqec(self);
+ // The resolution trampoline stashes the resolved method into the callee-save frame to transport
+ // it. Thus, when exiting, the stack cannot be verified (as the resolved method most likely
+ // does not have the same stack layout as the callee-save method).
+ ScopedQuickEntrypointChecks sqec(self, kIsDebugBuild, false);
// Start new JNI local reference state
JNIEnvExt* env = self->GetJniEnv();
ScopedObjectAccessUnchecked soa(env);