ART: Add GetFrameCount and GetFrameLocation
Add support for GetFrameCount and GetFrameLocation. Add tests.
Bug: 31684812
Test: m test-art-host-run-test-911-get-stack-trace
Change-Id: I7656e243f614eb0ceb5fcd6841128119fad89968
diff --git a/test/911-get-stack-trace/stack_trace.cc b/test/911-get-stack-trace/stack_trace.cc
index f853387..d162e8a 100644
--- a/test/911-get-stack-trace/stack_trace.cc
+++ b/test/911-get-stack-trace/stack_trace.cc
@@ -20,6 +20,7 @@
#include "android-base/stringprintf.h"
+#include "android-base/stringprintf.h"
#include "base/logging.h"
#include "base/macros.h"
#include "jni.h"
@@ -202,5 +203,55 @@
return ret;
}
+extern "C" JNIEXPORT jint JNICALL Java_Frames_getFrameCount(
+ JNIEnv* env, jclass klass ATTRIBUTE_UNUSED, jthread thread) {
+ jint count;
+ jvmtiError result = jvmti_env->GetFrameCount(thread, &count);
+ if (JvmtiErrorToException(env, result)) {
+ return -1;
+ }
+ return count;
+}
+
+extern "C" JNIEXPORT jobjectArray JNICALL Java_Frames_getFrameLocation(
+ JNIEnv* env, jclass klass ATTRIBUTE_UNUSED, jthread thread, jint depth) {
+ jmethodID method;
+ jlocation location;
+
+ jvmtiError result = jvmti_env->GetFrameLocation(thread, depth, &method, &location);
+ if (JvmtiErrorToException(env, result)) {
+ return nullptr;
+ }
+
+ auto callback = [&](jint index) -> jobject {
+ switch (index) {
+ case 0:
+ {
+ jclass decl_class;
+ jvmtiError class_result = jvmti_env->GetMethodDeclaringClass(method, &decl_class);
+ if (JvmtiErrorToException(env, class_result)) {
+ return nullptr;
+ }
+ jint modifiers;
+ jvmtiError mod_result = jvmti_env->GetMethodModifiers(method, &modifiers);
+ if (JvmtiErrorToException(env, mod_result)) {
+ return nullptr;
+ }
+ constexpr jint kStatic = 0x8;
+ return env->ToReflectedMethod(decl_class,
+ method,
+ (modifiers & kStatic) != 0 ? JNI_TRUE : JNI_FALSE);
+ }
+ case 1:
+ return env->NewStringUTF(
+ android::base::StringPrintf("%x", static_cast<uint32_t>(location)).c_str());
+ }
+ LOG(FATAL) << "Unreachable";
+ UNREACHABLE();
+ };
+ jobjectArray ret = CreateObjectArray(env, 2, "java/lang/Object", callback);
+ return ret;
+}
+
} // namespace Test911GetStackTrace
} // namespace art