Path: blob/aarch64-shenandoah-jdk8u272-b10/hotspot/src/share/vm/prims/jvmtiEnvBase.cpp
32285 views
/*1* Copyright (c) 2003, 2016, Oracle and/or its affiliates. All rights reserved.2* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.3*4* This code is free software; you can redistribute it and/or modify it5* under the terms of the GNU General Public License version 2 only, as6* published by the Free Software Foundation.7*8* This code is distributed in the hope that it will be useful, but WITHOUT9* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or10* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License11* version 2 for more details (a copy is included in the LICENSE file that12* accompanied this code).13*14* You should have received a copy of the GNU General Public License version15* 2 along with this work; if not, write to the Free Software Foundation,16* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.17*18* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA19* or visit www.oracle.com if you need additional information or have any20* questions.21*22*/2324#include "precompiled.hpp"25#include "classfile/systemDictionary.hpp"26#include "jvmtifiles/jvmtiEnv.hpp"27#include "oops/objArrayKlass.hpp"28#include "oops/objArrayOop.hpp"29#include "prims/jvmtiEnvBase.hpp"30#include "prims/jvmtiEventController.inline.hpp"31#include "prims/jvmtiExtensions.hpp"32#include "prims/jvmtiImpl.hpp"33#include "prims/jvmtiManageCapabilities.hpp"34#include "prims/jvmtiTagMap.hpp"35#include "prims/jvmtiThreadState.inline.hpp"36#include "runtime/biasedLocking.hpp"37#include "runtime/deoptimization.hpp"38#include "runtime/interfaceSupport.hpp"39#include "runtime/jfieldIDWorkaround.hpp"40#include "runtime/objectMonitor.hpp"41#include "runtime/objectMonitor.inline.hpp"42#include "runtime/signature.hpp"43#include "runtime/thread.inline.hpp"44#include "runtime/vframe.hpp"45#include "runtime/vframe_hp.hpp"46#include "runtime/vmThread.hpp"47#include "runtime/vm_operations.hpp"4849///////////////////////////////////////////////////////////////50//51// JvmtiEnvBase52//5354JvmtiEnvBase* JvmtiEnvBase::_head_environment = NULL;5556bool JvmtiEnvBase::_globally_initialized = false;57volatile bool JvmtiEnvBase::_needs_clean_up = false;5859jvmtiPhase JvmtiEnvBase::_phase = JVMTI_PHASE_PRIMORDIAL;6061volatile int JvmtiEnvBase::_dying_thread_env_iteration_count = 0;6263extern jvmtiInterface_1_ jvmti_Interface;64extern jvmtiInterface_1_ jvmtiTrace_Interface;656667// perform initializations that must occur before any JVMTI environments68// are released but which should only be initialized once (no matter69// how many environments are created).70void71JvmtiEnvBase::globally_initialize() {72assert(Threads::number_of_threads() == 0 || JvmtiThreadState_lock->is_locked(), "sanity check");73assert(_globally_initialized == false, "bad call");7475JvmtiManageCapabilities::initialize();7677// register extension functions and events78JvmtiExtensions::register_extensions();7980#ifdef JVMTI_TRACE81JvmtiTrace::initialize();82#endif8384_globally_initialized = true;85}868788void89JvmtiEnvBase::initialize() {90assert(Threads::number_of_threads() == 0 || JvmtiThreadState_lock->is_locked(), "sanity check");9192// Add this environment to the end of the environment list (order is important)93{94// This block of code must not contain any safepoints, as list deallocation95// (which occurs at a safepoint) cannot occur simultaneously with this list96// addition. Note: No_Safepoint_Verifier cannot, currently, be used before97// threads exist.98JvmtiEnvIterator it;99JvmtiEnvBase *previous_env = NULL;100for (JvmtiEnvBase* env = it.first(); env != NULL; env = it.next(env)) {101previous_env = env;102}103if (previous_env == NULL) {104_head_environment = this;105} else {106previous_env->set_next_environment(this);107}108}109110if (_globally_initialized == false) {111globally_initialize();112}113}114115116bool117JvmtiEnvBase::is_valid() {118jint value = 0;119120// This object might not be a JvmtiEnvBase so we can't assume121// the _magic field is properly aligned. Get the value in a safe122// way and then check against JVMTI_MAGIC.123124switch (sizeof(_magic)) {125case 2:126value = Bytes::get_native_u2((address)&_magic);127break;128129case 4:130value = Bytes::get_native_u4((address)&_magic);131break;132133case 8:134value = Bytes::get_native_u8((address)&_magic);135break;136137default:138guarantee(false, "_magic field is an unexpected size");139}140141return value == JVMTI_MAGIC;142}143144145bool146JvmtiEnvBase::use_version_1_0_semantics() {147int major, minor, micro;148149JvmtiExport::decode_version_values(_version, &major, &minor, µ);150return major == 1 && minor == 0; // micro version doesn't matter here151}152153154bool155JvmtiEnvBase::use_version_1_1_semantics() {156int major, minor, micro;157158JvmtiExport::decode_version_values(_version, &major, &minor, µ);159return major == 1 && minor == 1; // micro version doesn't matter here160}161162bool163JvmtiEnvBase::use_version_1_2_semantics() {164int major, minor, micro;165166JvmtiExport::decode_version_values(_version, &major, &minor, µ);167return major == 1 && minor == 2; // micro version doesn't matter here168}169170171JvmtiEnvBase::JvmtiEnvBase(jint version) : _env_event_enable() {172_version = version;173_env_local_storage = NULL;174_tag_map = NULL;175_native_method_prefix_count = 0;176_native_method_prefixes = NULL;177_next = NULL;178_class_file_load_hook_ever_enabled = false;179180// Moot since ClassFileLoadHook not yet enabled.181// But "true" will give a more predictable ClassFileLoadHook behavior182// for environment creation during ClassFileLoadHook.183_is_retransformable = true;184185// all callbacks initially NULL186memset(&_event_callbacks,0,sizeof(jvmtiEventCallbacks));187188// all capabilities initially off189memset(&_current_capabilities, 0, sizeof(_current_capabilities));190191// all prohibited capabilities initially off192memset(&_prohibited_capabilities, 0, sizeof(_prohibited_capabilities));193194_magic = JVMTI_MAGIC;195196JvmtiEventController::env_initialize((JvmtiEnv*)this);197198#ifdef JVMTI_TRACE199_jvmti_external.functions = TraceJVMTI != NULL ? &jvmtiTrace_Interface : &jvmti_Interface;200#else201_jvmti_external.functions = &jvmti_Interface;202#endif203}204205206void207JvmtiEnvBase::dispose() {208209#ifdef JVMTI_TRACE210JvmtiTrace::shutdown();211#endif212213// Dispose of event info and let the event controller call us back214// in a locked state (env_dispose, below)215JvmtiEventController::env_dispose(this);216}217218void219JvmtiEnvBase::env_dispose() {220assert(Threads::number_of_threads() == 0 || JvmtiThreadState_lock->is_locked(), "sanity check");221222// We have been entered with all events disabled on this environment.223// A race to re-enable events (by setting callbacks) is prevented by224// checking for a valid environment when setting callbacks (while225// holding the JvmtiThreadState_lock).226227// Mark as invalid.228_magic = DISPOSED_MAGIC;229230// Relinquish all capabilities.231jvmtiCapabilities *caps = get_capabilities();232JvmtiManageCapabilities::relinquish_capabilities(caps, caps, caps);233234// Same situation as with events (see above)235set_native_method_prefixes(0, NULL);236237JvmtiTagMap* tag_map_to_deallocate = _tag_map;238set_tag_map(NULL);239// A tag map can be big, deallocate it now240if (tag_map_to_deallocate != NULL) {241delete tag_map_to_deallocate;242}243244_needs_clean_up = true;245}246247248JvmtiEnvBase::~JvmtiEnvBase() {249assert(SafepointSynchronize::is_at_safepoint(), "sanity check");250251// There is a small window of time during which the tag map of a252// disposed environment could have been reallocated.253// Make sure it is gone.254JvmtiTagMap* tag_map_to_deallocate = _tag_map;255set_tag_map(NULL);256// A tag map can be big, deallocate it now257if (tag_map_to_deallocate != NULL) {258delete tag_map_to_deallocate;259}260261_magic = BAD_MAGIC;262}263264265void266JvmtiEnvBase::periodic_clean_up() {267assert(SafepointSynchronize::is_at_safepoint(), "sanity check");268269// JvmtiEnvBase reference is saved in JvmtiEnvThreadState. So270// clean up JvmtiThreadState before deleting JvmtiEnv pointer.271JvmtiThreadState::periodic_clean_up();272273// Unlink all invalid environments from the list of environments274// and deallocate them275JvmtiEnvIterator it;276JvmtiEnvBase* previous_env = NULL;277JvmtiEnvBase* env = it.first();278while (env != NULL) {279if (env->is_valid()) {280previous_env = env;281env = it.next(env);282} else {283// This one isn't valid, remove it from the list and deallocate it284JvmtiEnvBase* defunct_env = env;285env = it.next(env);286if (previous_env == NULL) {287_head_environment = env;288} else {289previous_env->set_next_environment(env);290}291delete defunct_env;292}293}294295}296297298void299JvmtiEnvBase::check_for_periodic_clean_up() {300assert(SafepointSynchronize::is_at_safepoint(), "sanity check");301302class ThreadInsideIterationClosure: public ThreadClosure {303private:304bool _inside;305public:306ThreadInsideIterationClosure() : _inside(false) {};307308void do_thread(Thread* thread) {309_inside |= thread->is_inside_jvmti_env_iteration();310}311312bool is_inside_jvmti_env_iteration() {313return _inside;314}315};316317if (_needs_clean_up) {318// Check if we are currently iterating environment,319// deallocation should not occur if we are320ThreadInsideIterationClosure tiic;321Threads::threads_do(&tiic);322if (!tiic.is_inside_jvmti_env_iteration() &&323!is_inside_dying_thread_env_iteration()) {324_needs_clean_up = false;325JvmtiEnvBase::periodic_clean_up();326}327}328}329330331void332JvmtiEnvBase::record_first_time_class_file_load_hook_enabled() {333assert(Threads::number_of_threads() == 0 || JvmtiThreadState_lock->is_locked(),334"sanity check");335336if (!_class_file_load_hook_ever_enabled) {337_class_file_load_hook_ever_enabled = true;338339if (get_capabilities()->can_retransform_classes) {340_is_retransformable = true;341} else {342_is_retransformable = false;343344// cannot add retransform capability after ClassFileLoadHook has been enabled345get_prohibited_capabilities()->can_retransform_classes = 1;346}347}348}349350351void352JvmtiEnvBase::record_class_file_load_hook_enabled() {353if (!_class_file_load_hook_ever_enabled) {354if (Threads::number_of_threads() == 0) {355record_first_time_class_file_load_hook_enabled();356} else {357MutexLocker mu(JvmtiThreadState_lock);358record_first_time_class_file_load_hook_enabled();359}360}361}362363364jvmtiError365JvmtiEnvBase::set_native_method_prefixes(jint prefix_count, char** prefixes) {366assert(Threads::number_of_threads() == 0 || JvmtiThreadState_lock->is_locked(),367"sanity check");368369int old_prefix_count = get_native_method_prefix_count();370char **old_prefixes = get_native_method_prefixes();371372// allocate and install the new prefixex373if (prefix_count == 0 || !is_valid()) {374_native_method_prefix_count = 0;375_native_method_prefixes = NULL;376} else {377// there are prefixes, allocate an array to hold them, and fill it378char** new_prefixes = (char**)os::malloc((prefix_count) * sizeof(char*), mtInternal);379if (new_prefixes == NULL) {380return JVMTI_ERROR_OUT_OF_MEMORY;381}382for (int i = 0; i < prefix_count; i++) {383char* prefix = prefixes[i];384if (prefix == NULL) {385for (int j = 0; j < (i-1); j++) {386os::free(new_prefixes[j]);387}388os::free(new_prefixes);389return JVMTI_ERROR_NULL_POINTER;390}391prefix = os::strdup(prefixes[i]);392if (prefix == NULL) {393for (int j = 0; j < (i-1); j++) {394os::free(new_prefixes[j]);395}396os::free(new_prefixes);397return JVMTI_ERROR_OUT_OF_MEMORY;398}399new_prefixes[i] = prefix;400}401_native_method_prefix_count = prefix_count;402_native_method_prefixes = new_prefixes;403}404405// now that we know the new prefixes have been successfully installed we can406// safely remove the old ones407if (old_prefix_count != 0) {408for (int i = 0; i < old_prefix_count; i++) {409os::free(old_prefixes[i]);410}411os::free(old_prefixes);412}413414return JVMTI_ERROR_NONE;415}416417418// Collect all the prefixes which have been set in any JVM TI environments419// by the SetNativeMethodPrefix(es) functions. Be sure to maintain the420// order of environments and the order of prefixes within each environment.421// Return in a resource allocated array.422char**423JvmtiEnvBase::get_all_native_method_prefixes(int* count_ptr) {424assert(Threads::number_of_threads() == 0 ||425SafepointSynchronize::is_at_safepoint() ||426JvmtiThreadState_lock->is_locked(),427"sanity check");428429int total_count = 0;430GrowableArray<char*>* prefix_array =new GrowableArray<char*>(5);431432JvmtiEnvIterator it;433for (JvmtiEnvBase* env = it.first(); env != NULL; env = it.next(env)) {434int prefix_count = env->get_native_method_prefix_count();435char** prefixes = env->get_native_method_prefixes();436for (int j = 0; j < prefix_count; j++) {437// retrieve a prefix and so that it is safe against asynchronous changes438// copy it into the resource area439char* prefix = prefixes[j];440char* prefix_copy = NEW_RESOURCE_ARRAY(char, strlen(prefix)+1);441strcpy(prefix_copy, prefix);442prefix_array->at_put_grow(total_count++, prefix_copy);443}444}445446char** all_prefixes = NEW_RESOURCE_ARRAY(char*, total_count);447char** p = all_prefixes;448for (int i = 0; i < total_count; ++i) {449*p++ = prefix_array->at(i);450}451*count_ptr = total_count;452return all_prefixes;453}454455void456JvmtiEnvBase::set_event_callbacks(const jvmtiEventCallbacks* callbacks,457jint size_of_callbacks) {458assert(Threads::number_of_threads() == 0 || JvmtiThreadState_lock->is_locked(), "sanity check");459460size_t byte_cnt = sizeof(jvmtiEventCallbacks);461462// clear in either case to be sure we got any gap between sizes463memset(&_event_callbacks, 0, byte_cnt);464465// Now that JvmtiThreadState_lock is held, prevent a possible race condition where events466// are re-enabled by a call to set event callbacks where the DisposeEnvironment467// occurs after the boiler-plate environment check and before the lock is acquired.468if (callbacks != NULL && is_valid()) {469if (size_of_callbacks < (jint)byte_cnt) {470byte_cnt = size_of_callbacks;471}472memcpy(&_event_callbacks, callbacks, byte_cnt);473}474}475476// Called from JVMTI entry points which perform stack walking. If the477// associated JavaThread is the current thread, then wait_for_suspend478// is not used. Otherwise, it determines if we should wait for the479// "other" thread to complete external suspension. (NOTE: in future480// releases the suspension mechanism should be reimplemented so this481// is not necessary.)482//483bool484JvmtiEnvBase::is_thread_fully_suspended(JavaThread* thr, bool wait_for_suspend, uint32_t *bits) {485// "other" threads require special handling486if (thr != JavaThread::current()) {487if (wait_for_suspend) {488// We are allowed to wait for the external suspend to complete489// so give the other thread a chance to get suspended.490if (!thr->wait_for_ext_suspend_completion(SuspendRetryCount,491SuspendRetryDelay, bits)) {492// didn't make it so let the caller know493return false;494}495}496// We aren't allowed to wait for the external suspend to complete497// so if the other thread isn't externally suspended we need to498// let the caller know.499else if (!thr->is_ext_suspend_completed_with_lock(bits)) {500return false;501}502}503504return true;505}506507508// In the fullness of time, all users of the method should instead509// directly use allocate, besides being cleaner and faster, this will510// mean much better out of memory handling511unsigned char *512JvmtiEnvBase::jvmtiMalloc(jlong size) {513unsigned char* mem = NULL;514jvmtiError result = allocate(size, &mem);515assert(result == JVMTI_ERROR_NONE, "Allocate failed");516return mem;517}518519520//521// Threads522//523524jobject *525JvmtiEnvBase::new_jobjectArray(int length, Handle *handles) {526if (length == 0) {527return NULL;528}529530jobject *objArray = (jobject *) jvmtiMalloc(sizeof(jobject) * length);531NULL_CHECK(objArray, NULL);532533for (int i=0; i<length; i++) {534objArray[i] = jni_reference(handles[i]);535}536return objArray;537}538539jthread *540JvmtiEnvBase::new_jthreadArray(int length, Handle *handles) {541return (jthread *) new_jobjectArray(length,handles);542}543544jthreadGroup *545JvmtiEnvBase::new_jthreadGroupArray(int length, Handle *handles) {546return (jthreadGroup *) new_jobjectArray(length,handles);547}548549550JavaThread *551JvmtiEnvBase::get_JavaThread(jthread jni_thread) {552oop t = JNIHandles::resolve_external_guard(jni_thread);553if (t == NULL || !t->is_a(SystemDictionary::Thread_klass())) {554return NULL;555}556// The following returns NULL if the thread has not yet run or is in557// process of exiting558return java_lang_Thread::thread(t);559}560561562// return the vframe on the specified thread and depth, NULL if no such frame563vframe*564JvmtiEnvBase::vframeFor(JavaThread* java_thread, jint depth) {565if (!java_thread->has_last_Java_frame()) {566return NULL;567}568RegisterMap reg_map(java_thread);569vframe *vf = java_thread->last_java_vframe(®_map);570int d = 0;571while ((vf != NULL) && (d < depth)) {572vf = vf->java_sender();573d++;574}575return vf;576}577578579//580// utilities: JNI objects581//582583584jclass585JvmtiEnvBase::get_jni_class_non_null(Klass* k) {586assert(k != NULL, "k != NULL");587return (jclass)jni_reference(k->java_mirror());588}589590//591// Field Information592//593594bool595JvmtiEnvBase::get_field_descriptor(Klass* k, jfieldID field, fieldDescriptor* fd) {596if (!jfieldIDWorkaround::is_valid_jfieldID(k, field)) {597return false;598}599bool found = false;600if (jfieldIDWorkaround::is_static_jfieldID(field)) {601JNIid* id = jfieldIDWorkaround::from_static_jfieldID(field);602found = id->find_local_field(fd);603} else {604// Non-static field. The fieldID is really the offset of the field within the object.605int offset = jfieldIDWorkaround::from_instance_jfieldID(k, field);606found = InstanceKlass::cast(k)->find_field_from_offset(offset, false, fd);607}608return found;609}610611//612// Object Monitor Information613//614615//616// Count the number of objects for a lightweight monitor. The hobj617// parameter is object that owns the monitor so this routine will618// count the number of times the same object was locked by frames619// in java_thread.620//621jint622JvmtiEnvBase::count_locked_objects(JavaThread *java_thread, Handle hobj) {623jint ret = 0;624if (!java_thread->has_last_Java_frame()) {625return ret; // no Java frames so no monitors626}627628ResourceMark rm;629HandleMark hm;630RegisterMap reg_map(java_thread);631632for(javaVFrame *jvf=java_thread->last_java_vframe(®_map); jvf != NULL;633jvf = jvf->java_sender()) {634GrowableArray<MonitorInfo*>* mons = jvf->monitors();635if (!mons->is_empty()) {636for (int i = 0; i < mons->length(); i++) {637MonitorInfo *mi = mons->at(i);638if (mi->owner_is_scalar_replaced()) continue;639640// see if owner of the monitor is our object641if (mi->owner() != NULL && mi->owner() == hobj()) {642ret++;643}644}645}646}647return ret;648}649650651652jvmtiError653JvmtiEnvBase::get_current_contended_monitor(JavaThread *calling_thread, JavaThread *java_thread, jobject *monitor_ptr) {654#ifdef ASSERT655uint32_t debug_bits = 0;656#endif657assert((SafepointSynchronize::is_at_safepoint() ||658is_thread_fully_suspended(java_thread, false, &debug_bits)),659"at safepoint or target thread is suspended");660oop obj = NULL;661ObjectMonitor *mon = java_thread->current_waiting_monitor();662if (mon == NULL) {663// thread is not doing an Object.wait() call664mon = java_thread->current_pending_monitor();665if (mon != NULL) {666// The thread is trying to enter() or raw_enter() an ObjectMonitor.667obj = (oop)mon->object();668// If obj == NULL, then ObjectMonitor is raw which doesn't count669// as contended for this API670}671// implied else: no contended ObjectMonitor672} else {673// thread is doing an Object.wait() call674obj = (oop)mon->object();675assert(obj != NULL, "Object.wait() should have an object");676}677678if (obj == NULL) {679*monitor_ptr = NULL;680} else {681HandleMark hm;682Handle hobj(obj);683*monitor_ptr = jni_reference(calling_thread, hobj);684}685return JVMTI_ERROR_NONE;686}687688689jvmtiError690JvmtiEnvBase::get_owned_monitors(JavaThread *calling_thread, JavaThread* java_thread,691GrowableArray<jvmtiMonitorStackDepthInfo*> *owned_monitors_list) {692jvmtiError err = JVMTI_ERROR_NONE;693#ifdef ASSERT694uint32_t debug_bits = 0;695#endif696assert((SafepointSynchronize::is_at_safepoint() ||697is_thread_fully_suspended(java_thread, false, &debug_bits)),698"at safepoint or target thread is suspended");699700if (java_thread->has_last_Java_frame()) {701ResourceMark rm;702HandleMark hm;703RegisterMap reg_map(java_thread);704705int depth = 0;706for (javaVFrame *jvf = java_thread->last_java_vframe(®_map); jvf != NULL;707jvf = jvf->java_sender()) {708if (depth++ < MaxJavaStackTraceDepth) { // check for stack too deep709// add locked objects for this frame into list710err = get_locked_objects_in_frame(calling_thread, java_thread, jvf, owned_monitors_list, depth-1);711if (err != JVMTI_ERROR_NONE) {712return err;713}714}715}716}717718// Get off stack monitors. (e.g. acquired via jni MonitorEnter).719JvmtiMonitorClosure jmc(java_thread, calling_thread, owned_monitors_list, this);720ObjectSynchronizer::monitors_iterate(&jmc);721err = jmc.error();722723return err;724}725726// Save JNI local handles for any objects that this frame owns.727jvmtiError728JvmtiEnvBase::get_locked_objects_in_frame(JavaThread* calling_thread, JavaThread* java_thread,729javaVFrame *jvf, GrowableArray<jvmtiMonitorStackDepthInfo*>* owned_monitors_list, int stack_depth) {730jvmtiError err = JVMTI_ERROR_NONE;731ResourceMark rm;732733GrowableArray<MonitorInfo*>* mons = jvf->monitors();734if (mons->is_empty()) {735return err; // this javaVFrame holds no monitors736}737738HandleMark hm;739oop wait_obj = NULL;740{741// save object of current wait() call (if any) for later comparison742ObjectMonitor *mon = java_thread->current_waiting_monitor();743if (mon != NULL) {744wait_obj = (oop)mon->object();745}746}747oop pending_obj = NULL;748{749// save object of current enter() call (if any) for later comparison750ObjectMonitor *mon = java_thread->current_pending_monitor();751if (mon != NULL) {752pending_obj = (oop)mon->object();753}754}755756for (int i = 0; i < mons->length(); i++) {757MonitorInfo *mi = mons->at(i);758759if (mi->owner_is_scalar_replaced()) continue;760761oop obj = mi->owner();762if (obj == NULL) {763// this monitor doesn't have an owning object so skip it764continue;765}766767if (wait_obj == obj) {768// the thread is waiting on this monitor so it isn't really owned769continue;770}771772if (pending_obj == obj) {773// the thread is pending on this monitor so it isn't really owned774continue;775}776777if (owned_monitors_list->length() > 0) {778// Our list has at least one object on it so we have to check779// for recursive object locking780bool found = false;781for (int j = 0; j < owned_monitors_list->length(); j++) {782jobject jobj = ((jvmtiMonitorStackDepthInfo*)owned_monitors_list->at(j))->monitor;783oop check = JNIHandles::resolve(jobj);784if (check == obj) {785found = true; // we found the object786break;787}788}789790if (found) {791// already have this object so don't include it792continue;793}794}795796// add the owning object to our list797jvmtiMonitorStackDepthInfo *jmsdi;798err = allocate(sizeof(jvmtiMonitorStackDepthInfo), (unsigned char **)&jmsdi);799if (err != JVMTI_ERROR_NONE) {800return err;801}802Handle hobj(obj);803jmsdi->monitor = jni_reference(calling_thread, hobj);804jmsdi->stack_depth = stack_depth;805owned_monitors_list->append(jmsdi);806}807808return err;809}810811jvmtiError812JvmtiEnvBase::get_stack_trace(JavaThread *java_thread,813jint start_depth, jint max_count,814jvmtiFrameInfo* frame_buffer, jint* count_ptr) {815#ifdef ASSERT816uint32_t debug_bits = 0;817#endif818assert((SafepointSynchronize::is_at_safepoint() ||819is_thread_fully_suspended(java_thread, false, &debug_bits)),820"at safepoint or target thread is suspended");821int count = 0;822if (java_thread->has_last_Java_frame()) {823RegisterMap reg_map(java_thread);824Thread* current_thread = Thread::current();825ResourceMark rm(current_thread);826javaVFrame *jvf = java_thread->last_java_vframe(®_map);827HandleMark hm(current_thread);828if (start_depth != 0) {829if (start_depth > 0) {830for (int j = 0; j < start_depth && jvf != NULL; j++) {831jvf = jvf->java_sender();832}833if (jvf == NULL) {834// start_depth is deeper than the stack depth835return JVMTI_ERROR_ILLEGAL_ARGUMENT;836}837} else { // start_depth < 0838// we are referencing the starting depth based on the oldest839// part of the stack.840// optimize to limit the number of times that java_sender() is called841javaVFrame *jvf_cursor = jvf;842javaVFrame *jvf_prev = NULL;843javaVFrame *jvf_prev_prev;844int j = 0;845while (jvf_cursor != NULL) {846jvf_prev_prev = jvf_prev;847jvf_prev = jvf_cursor;848for (j = 0; j > start_depth && jvf_cursor != NULL; j--) {849jvf_cursor = jvf_cursor->java_sender();850}851}852if (j == start_depth) {853// previous pointer is exactly where we want to start854jvf = jvf_prev;855} else {856// we need to back up further to get to the right place857if (jvf_prev_prev == NULL) {858// the -start_depth is greater than the stack depth859return JVMTI_ERROR_ILLEGAL_ARGUMENT;860}861// j now is the number of frames on the stack starting with862// jvf_prev, we start from jvf_prev_prev and move older on863// the stack that many, the result is -start_depth frames864// remaining.865jvf = jvf_prev_prev;866for (; j < 0; j++) {867jvf = jvf->java_sender();868}869}870}871}872for (; count < max_count && jvf != NULL; count++) {873frame_buffer[count].method = jvf->method()->jmethod_id();874frame_buffer[count].location = (jvf->method()->is_native() ? -1 : jvf->bci());875jvf = jvf->java_sender();876}877} else {878if (start_depth != 0) {879// no frames and there is a starting depth880return JVMTI_ERROR_ILLEGAL_ARGUMENT;881}882}883*count_ptr = count;884return JVMTI_ERROR_NONE;885}886887jvmtiError888JvmtiEnvBase::get_frame_count(JvmtiThreadState *state, jint *count_ptr) {889assert((state != NULL),890"JavaThread should create JvmtiThreadState before calling this method");891*count_ptr = state->count_frames();892return JVMTI_ERROR_NONE;893}894895jvmtiError896JvmtiEnvBase::get_frame_location(JavaThread *java_thread, jint depth,897jmethodID* method_ptr, jlocation* location_ptr) {898#ifdef ASSERT899uint32_t debug_bits = 0;900#endif901assert((SafepointSynchronize::is_at_safepoint() ||902is_thread_fully_suspended(java_thread, false, &debug_bits)),903"at safepoint or target thread is suspended");904Thread* current_thread = Thread::current();905ResourceMark rm(current_thread);906907vframe *vf = vframeFor(java_thread, depth);908if (vf == NULL) {909return JVMTI_ERROR_NO_MORE_FRAMES;910}911912// vframeFor should return a java frame. If it doesn't913// it means we've got an internal error and we return the914// error in product mode. In debug mode we will instead915// attempt to cast the vframe to a javaVFrame and will916// cause an assertion/crash to allow further diagnosis.917#ifdef PRODUCT918if (!vf->is_java_frame()) {919return JVMTI_ERROR_INTERNAL;920}921#endif922923HandleMark hm(current_thread);924javaVFrame *jvf = javaVFrame::cast(vf);925Method* method = jvf->method();926if (method->is_native()) {927*location_ptr = -1;928} else {929*location_ptr = jvf->bci();930}931*method_ptr = method->jmethod_id();932933return JVMTI_ERROR_NONE;934}935936937jvmtiError938JvmtiEnvBase::get_object_monitor_usage(JavaThread* calling_thread, jobject object, jvmtiMonitorUsage* info_ptr) {939HandleMark hm;940Handle hobj;941942bool at_safepoint = SafepointSynchronize::is_at_safepoint();943944// Check arguments945{946oop mirror = JNIHandles::resolve_external_guard(object);947NULL_CHECK(mirror, JVMTI_ERROR_INVALID_OBJECT);948NULL_CHECK(info_ptr, JVMTI_ERROR_NULL_POINTER);949950hobj = Handle(mirror);951}952953JavaThread *owning_thread = NULL;954ObjectMonitor *mon = NULL;955jvmtiMonitorUsage ret = {956NULL, 0, 0, NULL, 0, NULL957};958959uint32_t debug_bits = 0;960// first derive the object's owner and entry_count (if any)961{962// Revoke any biases before querying the mark word963if (SafepointSynchronize::is_at_safepoint()) {964BiasedLocking::revoke_at_safepoint(hobj);965} else {966BiasedLocking::revoke_and_rebias(hobj, false, calling_thread);967}968969address owner = NULL;970{971markOop mark = hobj()->mark();972973if (!mark->has_monitor()) {974// this object has a lightweight monitor975976if (mark->has_locker()) {977owner = (address)mark->locker(); // save the address of the Lock word978}979// implied else: no owner980} else {981// this object has a heavyweight monitor982mon = mark->monitor();983984// The owner field of a heavyweight monitor may be NULL for no985// owner, a JavaThread * or it may still be the address of the986// Lock word in a JavaThread's stack. A monitor can be inflated987// by a non-owning JavaThread, but only the owning JavaThread988// can change the owner field from the Lock word to the989// JavaThread * and it may not have done that yet.990owner = (address)mon->owner();991}992}993994if (owner != NULL) {995// This monitor is owned so we have to find the owning JavaThread.996// Since owning_thread_from_monitor_owner() grabs a lock, GC can997// move our object at this point. However, our owner value is safe998// since it is either the Lock word on a stack or a JavaThread *.999owning_thread = Threads::owning_thread_from_monitor_owner(owner, !at_safepoint);1000// Cannot assume (owning_thread != NULL) here because this function1001// may not have been called at a safepoint and the owning_thread1002// might not be suspended.1003if (owning_thread != NULL) {1004// The monitor's owner either has to be the current thread, at safepoint1005// or it has to be suspended. Any of these conditions will prevent both1006// contending and waiting threads from modifying the state of1007// the monitor.1008if (!at_safepoint && !JvmtiEnv::is_thread_fully_suspended(owning_thread, true, &debug_bits)) {1009// Don't worry! This return of JVMTI_ERROR_THREAD_NOT_SUSPENDED1010// will not make it back to the JVM/TI agent. The error code will1011// get intercepted in JvmtiEnv::GetObjectMonitorUsage() which1012// will retry the call via a VM_GetObjectMonitorUsage VM op.1013return JVMTI_ERROR_THREAD_NOT_SUSPENDED;1014}1015HandleMark hm;1016Handle th(owning_thread->threadObj());1017ret.owner = (jthread)jni_reference(calling_thread, th);1018}1019// implied else: no owner1020}10211022if (owning_thread != NULL) { // monitor is owned1023if ((address)owning_thread == owner) {1024// the owner field is the JavaThread *1025assert(mon != NULL,1026"must have heavyweight monitor with JavaThread * owner");1027ret.entry_count = mon->recursions() + 1;1028} else {1029// The owner field is the Lock word on the JavaThread's stack1030// so the recursions field is not valid. We have to count the1031// number of recursive monitor entries the hard way. We pass1032// a handle to survive any GCs along the way.1033ResourceMark rm;1034ret.entry_count = count_locked_objects(owning_thread, hobj);1035}1036}1037// implied else: entry_count == 01038}10391040int nWant = 0, nWait = 0;1041if (mon != NULL) {1042// this object has a heavyweight monitor1043nWant = mon->contentions(); // # of threads contending for monitor1044nWait = mon->waiters(); // # of threads in Object.wait()1045ret.waiter_count = nWant + nWait;1046ret.notify_waiter_count = nWait;1047} else {1048// this object has a lightweight monitor1049ret.waiter_count = 0;1050ret.notify_waiter_count = 0;1051}10521053// Allocate memory for heavyweight and lightweight monitor.1054jvmtiError err;1055err = allocate(ret.waiter_count * sizeof(jthread *), (unsigned char**)&ret.waiters);1056if (err != JVMTI_ERROR_NONE) {1057return err;1058}1059err = allocate(ret.notify_waiter_count * sizeof(jthread *),1060(unsigned char**)&ret.notify_waiters);1061if (err != JVMTI_ERROR_NONE) {1062deallocate((unsigned char*)ret.waiters);1063return err;1064}10651066// now derive the rest of the fields1067if (mon != NULL) {1068// this object has a heavyweight monitor10691070// Number of waiters may actually be less than the waiter count.1071// So NULL out memory so that unused memory will be NULL.1072memset(ret.waiters, 0, ret.waiter_count * sizeof(jthread *));1073memset(ret.notify_waiters, 0, ret.notify_waiter_count * sizeof(jthread *));10741075if (ret.waiter_count > 0) {1076// we have contending and/or waiting threads1077HandleMark hm;1078if (nWant > 0) {1079// we have contending threads1080ResourceMark rm;1081// get_pending_threads returns only java thread so we do not need to1082// check for non java threads.1083GrowableArray<JavaThread*>* wantList = Threads::get_pending_threads(1084nWant, (address)mon, !at_safepoint);1085if (wantList->length() < nWant) {1086// robustness: the pending list has gotten smaller1087nWant = wantList->length();1088}1089for (int i = 0; i < nWant; i++) {1090JavaThread *pending_thread = wantList->at(i);1091// If the monitor has no owner, then a non-suspended contending1092// thread could potentially change the state of the monitor by1093// entering it. The JVM/TI spec doesn't allow this.1094if (owning_thread == NULL && !at_safepoint &&1095!JvmtiEnv::is_thread_fully_suspended(pending_thread, true, &debug_bits)) {1096if (ret.owner != NULL) {1097destroy_jni_reference(calling_thread, ret.owner);1098}1099for (int j = 0; j < i; j++) {1100destroy_jni_reference(calling_thread, ret.waiters[j]);1101}1102deallocate((unsigned char*)ret.waiters);1103deallocate((unsigned char*)ret.notify_waiters);1104return JVMTI_ERROR_THREAD_NOT_SUSPENDED;1105}1106Handle th(pending_thread->threadObj());1107ret.waiters[i] = (jthread)jni_reference(calling_thread, th);1108}1109}1110if (nWait > 0) {1111// we have threads in Object.wait()1112int offset = nWant; // add after any contending threads1113ObjectWaiter *waiter = mon->first_waiter();1114for (int i = 0, j = 0; i < nWait; i++) {1115if (waiter == NULL) {1116// robustness: the waiting list has gotten smaller1117nWait = j;1118break;1119}1120Thread *t = mon->thread_of_waiter(waiter);1121if (t != NULL && t->is_Java_thread()) {1122JavaThread *wjava_thread = (JavaThread *)t;1123// If the thread was found on the ObjectWaiter list, then1124// it has not been notified. This thread can't change the1125// state of the monitor so it doesn't need to be suspended.1126Handle th(wjava_thread->threadObj());1127ret.waiters[offset + j] = (jthread)jni_reference(calling_thread, th);1128ret.notify_waiters[j++] = (jthread)jni_reference(calling_thread, th);1129}1130waiter = mon->next_waiter(waiter);1131}1132}1133}11341135// Adjust count. nWant and nWait count values may be less than original.1136ret.waiter_count = nWant + nWait;1137ret.notify_waiter_count = nWait;1138} else {1139// this object has a lightweight monitor and we have nothing more1140// to do here because the defaults are just fine.1141}11421143// we don't update return parameter unless everything worked1144*info_ptr = ret;11451146return JVMTI_ERROR_NONE;1147}11481149ResourceTracker::ResourceTracker(JvmtiEnv* env) {1150_env = env;1151_allocations = new (ResourceObj::C_HEAP, mtInternal) GrowableArray<unsigned char*>(20, true);1152_failed = false;1153}1154ResourceTracker::~ResourceTracker() {1155if (_failed) {1156for (int i=0; i<_allocations->length(); i++) {1157_env->deallocate(_allocations->at(i));1158}1159}1160delete _allocations;1161}11621163jvmtiError ResourceTracker::allocate(jlong size, unsigned char** mem_ptr) {1164unsigned char *ptr;1165jvmtiError err = _env->allocate(size, &ptr);1166if (err == JVMTI_ERROR_NONE) {1167_allocations->append(ptr);1168*mem_ptr = ptr;1169} else {1170*mem_ptr = NULL;1171_failed = true;1172}1173return err;1174}11751176unsigned char* ResourceTracker::allocate(jlong size) {1177unsigned char* ptr;1178allocate(size, &ptr);1179return ptr;1180}11811182char* ResourceTracker::strdup(const char* str) {1183char *dup_str = (char*)allocate(strlen(str)+1);1184if (dup_str != NULL) {1185strcpy(dup_str, str);1186}1187return dup_str;1188}11891190struct StackInfoNode {1191struct StackInfoNode *next;1192jvmtiStackInfo info;1193};11941195// Create a jvmtiStackInfo inside a linked list node and create a1196// buffer for the frame information, both allocated as resource objects.1197// Fill in both the jvmtiStackInfo and the jvmtiFrameInfo.1198// Note that either or both of thr and thread_oop1199// may be null if the thread is new or has exited.1200void1201VM_GetMultipleStackTraces::fill_frames(jthread jt, JavaThread *thr, oop thread_oop) {1202assert(SafepointSynchronize::is_at_safepoint(), "must be at safepoint");12031204jint state = 0;1205struct StackInfoNode *node = NEW_RESOURCE_OBJ(struct StackInfoNode);1206jvmtiStackInfo *infop = &(node->info);1207node->next = head();1208set_head(node);1209infop->frame_count = 0;1210infop->thread = jt;12111212if (thread_oop != NULL) {1213// get most state bits1214state = (jint)java_lang_Thread::get_thread_status(thread_oop);1215}12161217if (thr != NULL) { // add more state bits if there is a JavaThead to query1218// same as is_being_ext_suspended() but without locking1219if (thr->is_ext_suspended() || thr->is_external_suspend()) {1220state |= JVMTI_THREAD_STATE_SUSPENDED;1221}1222JavaThreadState jts = thr->thread_state();1223if (jts == _thread_in_native) {1224state |= JVMTI_THREAD_STATE_IN_NATIVE;1225}1226OSThread* osThread = thr->osthread();1227if (osThread != NULL && osThread->interrupted()) {1228state |= JVMTI_THREAD_STATE_INTERRUPTED;1229}1230}1231infop->state = state;12321233if (thr != NULL || (state & JVMTI_THREAD_STATE_ALIVE) != 0) {1234infop->frame_buffer = NEW_RESOURCE_ARRAY(jvmtiFrameInfo, max_frame_count());1235env()->get_stack_trace(thr, 0, max_frame_count(),1236infop->frame_buffer, &(infop->frame_count));1237} else {1238infop->frame_buffer = NULL;1239infop->frame_count = 0;1240}1241_frame_count_total += infop->frame_count;1242}12431244// Based on the stack information in the linked list, allocate memory1245// block to return and fill it from the info in the linked list.1246void1247VM_GetMultipleStackTraces::allocate_and_fill_stacks(jint thread_count) {1248// do I need to worry about alignment issues?1249jlong alloc_size = thread_count * sizeof(jvmtiStackInfo)1250+ _frame_count_total * sizeof(jvmtiFrameInfo);1251env()->allocate(alloc_size, (unsigned char **)&_stack_info);12521253// pointers to move through the newly allocated space as it is filled in1254jvmtiStackInfo *si = _stack_info + thread_count; // bottom of stack info1255jvmtiFrameInfo *fi = (jvmtiFrameInfo *)si; // is the top of frame info12561257// copy information in resource area into allocated buffer1258// insert stack info backwards since linked list is backwards1259// insert frame info forwards1260// walk the StackInfoNodes1261for (struct StackInfoNode *sin = head(); sin != NULL; sin = sin->next) {1262jint frame_count = sin->info.frame_count;1263size_t frames_size = frame_count * sizeof(jvmtiFrameInfo);1264--si;1265memcpy(si, &(sin->info), sizeof(jvmtiStackInfo));1266if (frames_size == 0) {1267si->frame_buffer = NULL;1268} else {1269memcpy(fi, sin->info.frame_buffer, frames_size);1270si->frame_buffer = fi; // point to the new allocated copy of the frames1271fi += frame_count;1272}1273}1274assert(si == _stack_info, "the last copied stack info must be the first record");1275assert((unsigned char *)fi == ((unsigned char *)_stack_info) + alloc_size,1276"the last copied frame info must be the last record");1277}127812791280void1281VM_GetThreadListStackTraces::doit() {1282assert(SafepointSynchronize::is_at_safepoint(), "must be at safepoint");12831284ResourceMark rm;1285for (int i = 0; i < _thread_count; ++i) {1286jthread jt = _thread_list[i];1287oop thread_oop = JNIHandles::resolve_external_guard(jt);1288if (thread_oop == NULL || !thread_oop->is_a(SystemDictionary::Thread_klass())) {1289set_result(JVMTI_ERROR_INVALID_THREAD);1290return;1291}1292fill_frames(jt, java_lang_Thread::thread(thread_oop), thread_oop);1293}1294allocate_and_fill_stacks(_thread_count);1295}12961297void1298VM_GetAllStackTraces::doit() {1299assert(SafepointSynchronize::is_at_safepoint(), "must be at safepoint");13001301ResourceMark rm;1302_final_thread_count = 0;1303for (JavaThread *jt = Threads::first(); jt != NULL; jt = jt->next()) {1304oop thread_oop = jt->threadObj();1305if (thread_oop != NULL &&1306!jt->is_exiting() &&1307java_lang_Thread::is_alive(thread_oop) &&1308!jt->is_hidden_from_external_view()) {1309++_final_thread_count;1310// Handle block of the calling thread is used to create local refs.1311fill_frames((jthread)JNIHandles::make_local(_calling_thread, thread_oop),1312jt, thread_oop);1313}1314}1315allocate_and_fill_stacks(_final_thread_count);1316}13171318// Verifies that the top frame is a java frame in an expected state.1319// Deoptimizes frame if needed.1320// Checks that the frame method signature matches the return type (tos).1321// HandleMark must be defined in the caller only.1322// It is to keep a ret_ob_h handle alive after return to the caller.1323jvmtiError1324JvmtiEnvBase::check_top_frame(JavaThread* current_thread, JavaThread* java_thread,1325jvalue value, TosState tos, Handle* ret_ob_h) {1326ResourceMark rm(current_thread);13271328vframe *vf = vframeFor(java_thread, 0);1329NULL_CHECK(vf, JVMTI_ERROR_NO_MORE_FRAMES);13301331javaVFrame *jvf = (javaVFrame*) vf;1332if (!vf->is_java_frame() || jvf->method()->is_native()) {1333return JVMTI_ERROR_OPAQUE_FRAME;1334}13351336// If the frame is a compiled one, need to deoptimize it.1337if (vf->is_compiled_frame()) {1338if (!vf->fr().can_be_deoptimized()) {1339return JVMTI_ERROR_OPAQUE_FRAME;1340}1341Deoptimization::deoptimize_frame(java_thread, jvf->fr().id());1342}13431344// Get information about method return type1345Symbol* signature = jvf->method()->signature();13461347ResultTypeFinder rtf(signature);1348TosState fr_tos = as_TosState(rtf.type());1349if (fr_tos != tos) {1350if (tos != itos || (fr_tos != btos && fr_tos != ztos && fr_tos != ctos && fr_tos != stos)) {1351return JVMTI_ERROR_TYPE_MISMATCH;1352}1353}13541355// Check that the jobject class matches the return type signature.1356jobject jobj = value.l;1357if (tos == atos && jobj != NULL) { // NULL reference is allowed1358Handle ob_h = Handle(current_thread, JNIHandles::resolve_external_guard(jobj));1359NULL_CHECK(ob_h, JVMTI_ERROR_INVALID_OBJECT);1360KlassHandle ob_kh = KlassHandle(current_thread, ob_h()->klass());1361NULL_CHECK(ob_kh, JVMTI_ERROR_INVALID_OBJECT);13621363// Method return type signature.1364char* ty_sign = 1 + strchr(signature->as_C_string(), ')');13651366if (!VM_GetOrSetLocal::is_assignable(ty_sign, ob_kh(), current_thread)) {1367return JVMTI_ERROR_TYPE_MISMATCH;1368}1369*ret_ob_h = ob_h;1370}1371return JVMTI_ERROR_NONE;1372} /* end check_top_frame */137313741375// ForceEarlyReturn<type> follows the PopFrame approach in many aspects.1376// Main difference is on the last stage in the interpreter.1377// The PopFrame stops method execution to continue execution1378// from the same method call instruction.1379// The ForceEarlyReturn forces return from method so the execution1380// continues at the bytecode following the method call.13811382// Threads_lock NOT held, java_thread not protected by lock1383// java_thread - pre-checked13841385jvmtiError1386JvmtiEnvBase::force_early_return(JavaThread* java_thread, jvalue value, TosState tos) {1387JavaThread* current_thread = JavaThread::current();1388HandleMark hm(current_thread);1389uint32_t debug_bits = 0;13901391// retrieve or create the state1392JvmtiThreadState* state = JvmtiThreadState::state_for(java_thread);1393if (state == NULL) {1394return JVMTI_ERROR_THREAD_NOT_ALIVE;1395}13961397// Check if java_thread is fully suspended1398if (!is_thread_fully_suspended(java_thread,1399true /* wait for suspend completion */,1400&debug_bits)) {1401return JVMTI_ERROR_THREAD_NOT_SUSPENDED;1402}14031404// Check to see if a ForceEarlyReturn was already in progress1405if (state->is_earlyret_pending()) {1406// Probably possible for JVMTI clients to trigger this, but the1407// JPDA backend shouldn't allow this to happen1408return JVMTI_ERROR_INTERNAL;1409}1410{1411// The same as for PopFrame. Workaround bug:1412// 4812902: popFrame hangs if the method is waiting at a synchronize1413// Catch this condition and return an error to avoid hanging.1414// Now JVMTI spec allows an implementation to bail out with an opaque1415// frame error.1416OSThread* osThread = java_thread->osthread();1417if (osThread->get_state() == MONITOR_WAIT) {1418return JVMTI_ERROR_OPAQUE_FRAME;1419}1420}1421Handle ret_ob_h = Handle();1422jvmtiError err = check_top_frame(current_thread, java_thread, value, tos, &ret_ob_h);1423if (err != JVMTI_ERROR_NONE) {1424return err;1425}1426assert(tos != atos || value.l == NULL || ret_ob_h() != NULL,1427"return object oop must not be NULL if jobject is not NULL");14281429// Update the thread state to reflect that the top frame must be1430// forced to return.1431// The current frame will be returned later when the suspended1432// thread is resumed and right before returning from VM to Java.1433// (see call_VM_base() in assembler_<cpu>.cpp).14341435state->set_earlyret_pending();1436state->set_earlyret_oop(ret_ob_h());1437state->set_earlyret_value(value, tos);14381439// Set pending step flag for this early return.1440// It is cleared when next step event is posted.1441state->set_pending_step_for_earlyret();14421443return JVMTI_ERROR_NONE;1444} /* end force_early_return */14451446void1447JvmtiMonitorClosure::do_monitor(ObjectMonitor* mon) {1448if ( _error != JVMTI_ERROR_NONE) {1449// Error occurred in previous iteration so no need to add1450// to the list.1451return;1452}1453if (mon->owner() == _java_thread ) {1454// Filter out on stack monitors collected during stack walk.1455oop obj = (oop)mon->object();1456bool found = false;1457for (int j = 0; j < _owned_monitors_list->length(); j++) {1458jobject jobj = ((jvmtiMonitorStackDepthInfo*)_owned_monitors_list->at(j))->monitor;1459oop check = JNIHandles::resolve(jobj);1460if (check == obj) {1461// On stack monitor already collected during the stack walk.1462found = true;1463break;1464}1465}1466if (found == false) {1467// This is off stack monitor (e.g. acquired via jni MonitorEnter).1468jvmtiError err;1469jvmtiMonitorStackDepthInfo *jmsdi;1470err = _env->allocate(sizeof(jvmtiMonitorStackDepthInfo), (unsigned char **)&jmsdi);1471if (err != JVMTI_ERROR_NONE) {1472_error = err;1473return;1474}1475Handle hobj(obj);1476jmsdi->monitor = _env->jni_reference(_calling_thread, hobj);1477// stack depth is unknown for this monitor.1478jmsdi->stack_depth = -1;1479_owned_monitors_list->append(jmsdi);1480}1481}1482}148314841485