jvmtiEnv.cpp revision 10420:c558850fac57
1/*
2 * Copyright (c) 2003, 2016, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation.
8 *
9 * This code is distributed in the hope that it will be useful, but WITHOUT
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
12 * version 2 for more details (a copy is included in the LICENSE file that
13 * accompanied this code).
14 *
15 * You should have received a copy of the GNU General Public License version
16 * 2 along with this work; if not, write to the Free Software Foundation,
17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
18 *
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
20 * or visit www.oracle.com if you need additional information or have any
21 * questions.
22 *
23 */
24
25#include "precompiled.hpp"
26#include "classfile/classLoaderExt.hpp"
27#include "classfile/systemDictionary.hpp"
28#include "classfile/vmSymbols.hpp"
29#include "interpreter/bytecodeStream.hpp"
30#include "interpreter/interpreter.hpp"
31#include "jvmtifiles/jvmtiEnv.hpp"
32#include "logging/log.hpp"
33#include "logging/logConfiguration.hpp"
34#include "memory/resourceArea.hpp"
35#include "memory/universe.inline.hpp"
36#include "oops/instanceKlass.hpp"
37#include "oops/objArrayOop.inline.hpp"
38#include "oops/oop.inline.hpp"
39#include "prims/jniCheck.hpp"
40#include "prims/jvm_misc.hpp"
41#include "prims/jvmtiAgentThread.hpp"
42#include "prims/jvmtiClassFileReconstituter.hpp"
43#include "prims/jvmtiCodeBlobEvents.hpp"
44#include "prims/jvmtiExtensions.hpp"
45#include "prims/jvmtiGetLoadedClasses.hpp"
46#include "prims/jvmtiImpl.hpp"
47#include "prims/jvmtiManageCapabilities.hpp"
48#include "prims/jvmtiRawMonitor.hpp"
49#include "prims/jvmtiRedefineClasses.hpp"
50#include "prims/jvmtiTagMap.hpp"
51#include "prims/jvmtiThreadState.inline.hpp"
52#include "prims/jvmtiUtil.hpp"
53#include "runtime/arguments.hpp"
54#include "runtime/deoptimization.hpp"
55#include "runtime/interfaceSupport.hpp"
56#include "runtime/javaCalls.hpp"
57#include "runtime/jfieldIDWorkaround.hpp"
58#include "runtime/osThread.hpp"
59#include "runtime/reflectionUtils.hpp"
60#include "runtime/signature.hpp"
61#include "runtime/thread.inline.hpp"
62#include "runtime/vframe.hpp"
63#include "runtime/vmThread.hpp"
64#include "services/threadService.hpp"
65#include "utilities/exceptions.hpp"
66#include "utilities/preserveException.hpp"
67
68
69#define FIXLATER 0 // REMOVE this when completed.
70
71 // FIXLATER: hook into JvmtiTrace
72#define TraceJVMTICalls false
73
74JvmtiEnv::JvmtiEnv(jint version) : JvmtiEnvBase(version) {
75}
76
77JvmtiEnv::~JvmtiEnv() {
78}
79
80JvmtiEnv*
81JvmtiEnv::create_a_jvmti(jint version) {
82  return new JvmtiEnv(version);
83}
84
85// VM operation class to copy jni function table at safepoint.
86// More than one java threads or jvmti agents may be reading/
87// modifying jni function tables. To reduce the risk of bad
88// interaction b/w these threads it is copied at safepoint.
89class VM_JNIFunctionTableCopier : public VM_Operation {
90 private:
91  const struct JNINativeInterface_ *_function_table;
92 public:
93  VM_JNIFunctionTableCopier(const struct JNINativeInterface_ *func_tbl) {
94    _function_table = func_tbl;
95  };
96
97  VMOp_Type type() const { return VMOp_JNIFunctionTableCopier; }
98  void doit() {
99    copy_jni_function_table(_function_table);
100  };
101};
102
103//
104// Do not change the "prefix" marker below, everything above it is copied
105// unchanged into the filled stub, everything below is controlled by the
106// stub filler (only method bodies are carried forward, and then only for
107// functionality still in the spec).
108//
109// end file prefix
110
111  //
112  // Memory Management functions
113  //
114
115// mem_ptr - pre-checked for NULL
116jvmtiError
117JvmtiEnv::Allocate(jlong size, unsigned char** mem_ptr) {
118  return allocate(size, mem_ptr);
119} /* end Allocate */
120
121
122// mem - NULL is a valid value, must be checked
123jvmtiError
124JvmtiEnv::Deallocate(unsigned char* mem) {
125  return deallocate(mem);
126} /* end Deallocate */
127
128// Threads_lock NOT held, java_thread not protected by lock
129// java_thread - pre-checked
130// data - NULL is a valid value, must be checked
131jvmtiError
132JvmtiEnv::SetThreadLocalStorage(JavaThread* java_thread, const void* data) {
133  JvmtiThreadState* state = java_thread->jvmti_thread_state();
134  if (state == NULL) {
135    if (data == NULL) {
136      // leaving state unset same as data set to NULL
137      return JVMTI_ERROR_NONE;
138    }
139    // otherwise, create the state
140    state = JvmtiThreadState::state_for(java_thread);
141    if (state == NULL) {
142      return JVMTI_ERROR_THREAD_NOT_ALIVE;
143    }
144  }
145  state->env_thread_state(this)->set_agent_thread_local_storage_data((void*)data);
146  return JVMTI_ERROR_NONE;
147} /* end SetThreadLocalStorage */
148
149
150// Threads_lock NOT held
151// thread - NOT pre-checked
152// data_ptr - pre-checked for NULL
153jvmtiError
154JvmtiEnv::GetThreadLocalStorage(jthread thread, void** data_ptr) {
155  JavaThread* current_thread = JavaThread::current();
156  if (thread == NULL) {
157    JvmtiThreadState* state = current_thread->jvmti_thread_state();
158    *data_ptr = (state == NULL) ? NULL :
159      state->env_thread_state(this)->get_agent_thread_local_storage_data();
160  } else {
161
162    // jvmti_GetThreadLocalStorage is "in native" and doesn't transition
163    // the thread to _thread_in_vm. However, when the TLS for a thread
164    // other than the current thread is required we need to transition
165    // from native so as to resolve the jthread.
166
167    ThreadInVMfromNative __tiv(current_thread);
168    VM_ENTRY_BASE(jvmtiError, JvmtiEnv::GetThreadLocalStorage , current_thread)
169    debug_only(VMNativeEntryWrapper __vew;)
170
171    oop thread_oop = JNIHandles::resolve_external_guard(thread);
172    if (thread_oop == NULL) {
173      return JVMTI_ERROR_INVALID_THREAD;
174    }
175    if (!thread_oop->is_a(SystemDictionary::Thread_klass())) {
176      return JVMTI_ERROR_INVALID_THREAD;
177    }
178    JavaThread* java_thread = java_lang_Thread::thread(thread_oop);
179    if (java_thread == NULL) {
180      return JVMTI_ERROR_THREAD_NOT_ALIVE;
181    }
182    JvmtiThreadState* state = java_thread->jvmti_thread_state();
183    *data_ptr = (state == NULL) ? NULL :
184      state->env_thread_state(this)->get_agent_thread_local_storage_data();
185  }
186  return JVMTI_ERROR_NONE;
187} /* end GetThreadLocalStorage */
188
189  //
190  // Module functions
191  //
192
193// module_count_ptr - pre-checked for NULL
194// modules_ptr - pre-checked for NULL
195jvmtiError
196JvmtiEnv::GetAllModules(jint* module_count_ptr, jobject** modules_ptr) {
197    JvmtiModuleClosure jmc;
198
199    return jmc.get_all_modules(this, module_count_ptr, modules_ptr);
200} /* end GetAllModules */
201
202
203  //
204  // Class functions
205  //
206
207// class_count_ptr - pre-checked for NULL
208// classes_ptr - pre-checked for NULL
209jvmtiError
210JvmtiEnv::GetLoadedClasses(jint* class_count_ptr, jclass** classes_ptr) {
211  return JvmtiGetLoadedClasses::getLoadedClasses(this, class_count_ptr, classes_ptr);
212} /* end GetLoadedClasses */
213
214
215// initiating_loader - NULL is a valid value, must be checked
216// class_count_ptr - pre-checked for NULL
217// classes_ptr - pre-checked for NULL
218jvmtiError
219JvmtiEnv::GetClassLoaderClasses(jobject initiating_loader, jint* class_count_ptr, jclass** classes_ptr) {
220  return JvmtiGetLoadedClasses::getClassLoaderClasses(this, initiating_loader,
221                                                  class_count_ptr, classes_ptr);
222} /* end GetClassLoaderClasses */
223
224// k_mirror - may be primitive, this must be checked
225// is_modifiable_class_ptr - pre-checked for NULL
226jvmtiError
227JvmtiEnv::IsModifiableClass(oop k_mirror, jboolean* is_modifiable_class_ptr) {
228  *is_modifiable_class_ptr = VM_RedefineClasses::is_modifiable_class(k_mirror)?
229                                                       JNI_TRUE : JNI_FALSE;
230  return JVMTI_ERROR_NONE;
231} /* end IsModifiableClass */
232
233// class_count - pre-checked to be greater than or equal to 0
234// classes - pre-checked for NULL
235jvmtiError
236JvmtiEnv::RetransformClasses(jint class_count, const jclass* classes) {
237//TODO: add locking
238
239  int index;
240  JavaThread* current_thread = JavaThread::current();
241  ResourceMark rm(current_thread);
242
243  jvmtiClassDefinition* class_definitions =
244                            NEW_RESOURCE_ARRAY(jvmtiClassDefinition, class_count);
245  NULL_CHECK(class_definitions, JVMTI_ERROR_OUT_OF_MEMORY);
246
247  for (index = 0; index < class_count; index++) {
248    HandleMark hm(current_thread);
249
250    jclass jcls = classes[index];
251    oop k_mirror = JNIHandles::resolve_external_guard(jcls);
252    if (k_mirror == NULL) {
253      return JVMTI_ERROR_INVALID_CLASS;
254    }
255    if (!k_mirror->is_a(SystemDictionary::Class_klass())) {
256      return JVMTI_ERROR_INVALID_CLASS;
257    }
258
259    if (java_lang_Class::is_primitive(k_mirror)) {
260      return JVMTI_ERROR_UNMODIFIABLE_CLASS;
261    }
262
263    Klass* k_oop = java_lang_Class::as_Klass(k_mirror);
264    KlassHandle klass(current_thread, k_oop);
265
266    jint status = klass->jvmti_class_status();
267    if (status & (JVMTI_CLASS_STATUS_ERROR)) {
268      return JVMTI_ERROR_INVALID_CLASS;
269    }
270    if (status & (JVMTI_CLASS_STATUS_ARRAY)) {
271      return JVMTI_ERROR_UNMODIFIABLE_CLASS;
272    }
273
274    instanceKlassHandle ikh(current_thread, k_oop);
275    if (ikh->get_cached_class_file_bytes() == NULL) {
276      // Not cached, we need to reconstitute the class file from the
277      // VM representation. We don't attach the reconstituted class
278      // bytes to the InstanceKlass here because they have not been
279      // validated and we're not at a safepoint.
280      JvmtiClassFileReconstituter reconstituter(ikh);
281      if (reconstituter.get_error() != JVMTI_ERROR_NONE) {
282        return reconstituter.get_error();
283      }
284
285      class_definitions[index].class_byte_count = (jint)reconstituter.class_file_size();
286      class_definitions[index].class_bytes      = (unsigned char*)
287                                                       reconstituter.class_file_bytes();
288    } else {
289      // it is cached, get it from the cache
290      class_definitions[index].class_byte_count = ikh->get_cached_class_file_len();
291      class_definitions[index].class_bytes      = ikh->get_cached_class_file_bytes();
292    }
293    class_definitions[index].klass              = jcls;
294  }
295  VM_RedefineClasses op(class_count, class_definitions, jvmti_class_load_kind_retransform);
296  VMThread::execute(&op);
297  return (op.check_error());
298} /* end RetransformClasses */
299
300
301// class_count - pre-checked to be greater than or equal to 0
302// class_definitions - pre-checked for NULL
303jvmtiError
304JvmtiEnv::RedefineClasses(jint class_count, const jvmtiClassDefinition* class_definitions) {
305//TODO: add locking
306  VM_RedefineClasses op(class_count, class_definitions, jvmti_class_load_kind_redefine);
307  VMThread::execute(&op);
308  return (op.check_error());
309} /* end RedefineClasses */
310
311
312  //
313  // Object functions
314  //
315
316// size_ptr - pre-checked for NULL
317jvmtiError
318JvmtiEnv::GetObjectSize(jobject object, jlong* size_ptr) {
319  oop mirror = JNIHandles::resolve_external_guard(object);
320  NULL_CHECK(mirror, JVMTI_ERROR_INVALID_OBJECT);
321
322  if (mirror->klass() == SystemDictionary::Class_klass() &&
323      !java_lang_Class::is_primitive(mirror)) {
324    Klass* k = java_lang_Class::as_Klass(mirror);
325    assert(k != NULL, "class for non-primitive mirror must exist");
326    *size_ptr = (jlong)k->size() * wordSize;
327  } else {
328    *size_ptr = (jlong)mirror->size() * wordSize;
329    }
330  return JVMTI_ERROR_NONE;
331} /* end GetObjectSize */
332
333  //
334  // Method functions
335  //
336
337// prefix - NULL is a valid value, must be checked
338jvmtiError
339JvmtiEnv::SetNativeMethodPrefix(const char* prefix) {
340  return prefix == NULL?
341              SetNativeMethodPrefixes(0, NULL) :
342              SetNativeMethodPrefixes(1, (char**)&prefix);
343} /* end SetNativeMethodPrefix */
344
345
346// prefix_count - pre-checked to be greater than or equal to 0
347// prefixes - pre-checked for NULL
348jvmtiError
349JvmtiEnv::SetNativeMethodPrefixes(jint prefix_count, char** prefixes) {
350  // Have to grab JVMTI thread state lock to be sure that some thread
351  // isn't accessing the prefixes at the same time we are setting them.
352  // No locks during VM bring-up.
353  if (Threads::number_of_threads() == 0) {
354    return set_native_method_prefixes(prefix_count, prefixes);
355  } else {
356    MutexLocker mu(JvmtiThreadState_lock);
357    return set_native_method_prefixes(prefix_count, prefixes);
358  }
359} /* end SetNativeMethodPrefixes */
360
361  //
362  // Event Management functions
363  //
364
365// callbacks - NULL is a valid value, must be checked
366// size_of_callbacks - pre-checked to be greater than or equal to 0
367jvmtiError
368JvmtiEnv::SetEventCallbacks(const jvmtiEventCallbacks* callbacks, jint size_of_callbacks) {
369  JvmtiEventController::set_event_callbacks(this, callbacks, size_of_callbacks);
370  return JVMTI_ERROR_NONE;
371} /* end SetEventCallbacks */
372
373
374// event_thread - NULL is a valid value, must be checked
375jvmtiError
376JvmtiEnv::SetEventNotificationMode(jvmtiEventMode mode, jvmtiEvent event_type, jthread event_thread,   ...) {
377  JavaThread* java_thread = NULL;
378  if (event_thread != NULL) {
379    oop thread_oop = JNIHandles::resolve_external_guard(event_thread);
380    if (thread_oop == NULL) {
381      return JVMTI_ERROR_INVALID_THREAD;
382    }
383    if (!thread_oop->is_a(SystemDictionary::Thread_klass())) {
384      return JVMTI_ERROR_INVALID_THREAD;
385    }
386    java_thread = java_lang_Thread::thread(thread_oop);
387    if (java_thread == NULL) {
388      return JVMTI_ERROR_THREAD_NOT_ALIVE;
389    }
390  }
391
392  // event_type must be valid
393  if (!JvmtiEventController::is_valid_event_type(event_type)) {
394    return JVMTI_ERROR_INVALID_EVENT_TYPE;
395  }
396
397  // global events cannot be controlled at thread level.
398  if (java_thread != NULL && JvmtiEventController::is_global_event(event_type)) {
399    return JVMTI_ERROR_ILLEGAL_ARGUMENT;
400  }
401
402  bool enabled = (mode == JVMTI_ENABLE);
403
404  // assure that needed capabilities are present
405  if (enabled && !JvmtiUtil::has_event_capability(event_type, get_capabilities())) {
406    return JVMTI_ERROR_MUST_POSSESS_CAPABILITY;
407  }
408
409  if (event_type == JVMTI_EVENT_CLASS_FILE_LOAD_HOOK && enabled) {
410    record_class_file_load_hook_enabled();
411  }
412  JvmtiEventController::set_user_enabled(this, java_thread, event_type, enabled);
413
414  return JVMTI_ERROR_NONE;
415} /* end SetEventNotificationMode */
416
417  //
418  // Capability functions
419  //
420
421// capabilities_ptr - pre-checked for NULL
422jvmtiError
423JvmtiEnv::GetPotentialCapabilities(jvmtiCapabilities* capabilities_ptr) {
424  JvmtiManageCapabilities::get_potential_capabilities(get_capabilities(),
425                                                      get_prohibited_capabilities(),
426                                                      capabilities_ptr);
427  return JVMTI_ERROR_NONE;
428} /* end GetPotentialCapabilities */
429
430
431// capabilities_ptr - pre-checked for NULL
432jvmtiError
433JvmtiEnv::AddCapabilities(const jvmtiCapabilities* capabilities_ptr) {
434  return JvmtiManageCapabilities::add_capabilities(get_capabilities(),
435                                                   get_prohibited_capabilities(),
436                                                   capabilities_ptr,
437                                                   get_capabilities());
438} /* end AddCapabilities */
439
440
441// capabilities_ptr - pre-checked for NULL
442jvmtiError
443JvmtiEnv::RelinquishCapabilities(const jvmtiCapabilities* capabilities_ptr) {
444  JvmtiManageCapabilities::relinquish_capabilities(get_capabilities(), capabilities_ptr, get_capabilities());
445  return JVMTI_ERROR_NONE;
446} /* end RelinquishCapabilities */
447
448
449// capabilities_ptr - pre-checked for NULL
450jvmtiError
451JvmtiEnv::GetCapabilities(jvmtiCapabilities* capabilities_ptr) {
452  JvmtiManageCapabilities::copy_capabilities(get_capabilities(), capabilities_ptr);
453  return JVMTI_ERROR_NONE;
454} /* end GetCapabilities */
455
456  //
457  // Class Loader Search functions
458  //
459
460// segment - pre-checked for NULL
461jvmtiError
462JvmtiEnv::AddToBootstrapClassLoaderSearch(const char* segment) {
463  jvmtiPhase phase = get_phase();
464  if (phase == JVMTI_PHASE_ONLOAD) {
465    Arguments::append_sysclasspath(segment);
466    return JVMTI_ERROR_NONE;
467  } else if (use_version_1_0_semantics()) {
468    // This JvmtiEnv requested version 1.0 semantics and this function
469    // is only allowed in the ONLOAD phase in version 1.0 so we need to
470    // return an error here.
471    return JVMTI_ERROR_WRONG_PHASE;
472  } else if (phase == JVMTI_PHASE_LIVE) {
473    // The phase is checked by the wrapper that called this function,
474    // but this thread could be racing with the thread that is
475    // terminating the VM so we check one more time.
476
477    // create the zip entry
478    ClassPathZipEntry* zip_entry = ClassLoader::create_class_path_zip_entry(segment);
479    if (zip_entry == NULL) {
480      return JVMTI_ERROR_ILLEGAL_ARGUMENT;
481    }
482
483    // lock the loader
484    Thread* thread = Thread::current();
485    HandleMark hm;
486    Handle loader_lock = Handle(thread, SystemDictionary::system_loader_lock());
487
488    ObjectLocker ol(loader_lock, thread);
489
490    // add the jar file to the bootclasspath
491    log_info(classload)("opened: %s", zip_entry->name());
492    ClassLoaderExt::append_boot_classpath(zip_entry);
493    return JVMTI_ERROR_NONE;
494  } else {
495    return JVMTI_ERROR_WRONG_PHASE;
496  }
497
498} /* end AddToBootstrapClassLoaderSearch */
499
500
501// segment - pre-checked for NULL
502jvmtiError
503JvmtiEnv::AddToSystemClassLoaderSearch(const char* segment) {
504  jvmtiPhase phase = get_phase();
505
506  if (phase == JVMTI_PHASE_ONLOAD) {
507    for (SystemProperty* p = Arguments::system_properties(); p != NULL; p = p->next()) {
508      if (strcmp("java.class.path", p->key()) == 0) {
509        p->append_value(segment);
510        break;
511      }
512    }
513    return JVMTI_ERROR_NONE;
514  } else if (phase == JVMTI_PHASE_LIVE) {
515    // The phase is checked by the wrapper that called this function,
516    // but this thread could be racing with the thread that is
517    // terminating the VM so we check one more time.
518    HandleMark hm;
519
520    // create the zip entry (which will open the zip file and hence
521    // check that the segment is indeed a zip file).
522    ClassPathZipEntry* zip_entry = ClassLoader::create_class_path_zip_entry(segment);
523    if (zip_entry == NULL) {
524      return JVMTI_ERROR_ILLEGAL_ARGUMENT;
525    }
526    delete zip_entry;   // no longer needed
527
528    // lock the loader
529    Thread* THREAD = Thread::current();
530    Handle loader = Handle(THREAD, SystemDictionary::java_system_loader());
531
532    ObjectLocker ol(loader, THREAD);
533
534    // need the path as java.lang.String
535    Handle path = java_lang_String::create_from_platform_dependent_str(segment, THREAD);
536    if (HAS_PENDING_EXCEPTION) {
537      CLEAR_PENDING_EXCEPTION;
538      return JVMTI_ERROR_INTERNAL;
539    }
540
541    instanceKlassHandle loader_ik(THREAD, loader->klass());
542
543    // Invoke the appendToClassPathForInstrumentation method - if the method
544    // is not found it means the loader doesn't support adding to the class path
545    // in the live phase.
546    {
547      JavaValue res(T_VOID);
548      JavaCalls::call_special(&res,
549                              loader,
550                              loader_ik,
551                              vmSymbols::appendToClassPathForInstrumentation_name(),
552                              vmSymbols::appendToClassPathForInstrumentation_signature(),
553                              path,
554                              THREAD);
555      if (HAS_PENDING_EXCEPTION) {
556        Symbol* ex_name = PENDING_EXCEPTION->klass()->name();
557        CLEAR_PENDING_EXCEPTION;
558
559        if (ex_name == vmSymbols::java_lang_NoSuchMethodError()) {
560          return JVMTI_ERROR_CLASS_LOADER_UNSUPPORTED;
561        } else {
562          return JVMTI_ERROR_INTERNAL;
563        }
564      }
565    }
566
567    return JVMTI_ERROR_NONE;
568  } else {
569    return JVMTI_ERROR_WRONG_PHASE;
570  }
571} /* end AddToSystemClassLoaderSearch */
572
573  //
574  // General functions
575  //
576
577// phase_ptr - pre-checked for NULL
578jvmtiError
579JvmtiEnv::GetPhase(jvmtiPhase* phase_ptr) {
580  *phase_ptr = phase();
581  return JVMTI_ERROR_NONE;
582} /* end GetPhase */
583
584
585jvmtiError
586JvmtiEnv::DisposeEnvironment() {
587  dispose();
588  return JVMTI_ERROR_NONE;
589} /* end DisposeEnvironment */
590
591
592// data - NULL is a valid value, must be checked
593jvmtiError
594JvmtiEnv::SetEnvironmentLocalStorage(const void* data) {
595  set_env_local_storage(data);
596  return JVMTI_ERROR_NONE;
597} /* end SetEnvironmentLocalStorage */
598
599
600// data_ptr - pre-checked for NULL
601jvmtiError
602JvmtiEnv::GetEnvironmentLocalStorage(void** data_ptr) {
603  *data_ptr = (void*)get_env_local_storage();
604  return JVMTI_ERROR_NONE;
605} /* end GetEnvironmentLocalStorage */
606
607// version_ptr - pre-checked for NULL
608jvmtiError
609JvmtiEnv::GetVersionNumber(jint* version_ptr) {
610  *version_ptr = JVMTI_VERSION;
611  return JVMTI_ERROR_NONE;
612} /* end GetVersionNumber */
613
614
615// name_ptr - pre-checked for NULL
616jvmtiError
617JvmtiEnv::GetErrorName(jvmtiError error, char** name_ptr) {
618  if (error < JVMTI_ERROR_NONE || error > JVMTI_ERROR_MAX) {
619    return JVMTI_ERROR_ILLEGAL_ARGUMENT;
620  }
621  const char *name = JvmtiUtil::error_name(error);
622  if (name == NULL) {
623    return JVMTI_ERROR_ILLEGAL_ARGUMENT;
624  }
625  size_t len = strlen(name) + 1;
626  jvmtiError err = allocate(len, (unsigned char**)name_ptr);
627  if (err == JVMTI_ERROR_NONE) {
628    memcpy(*name_ptr, name, len);
629  }
630  return err;
631} /* end GetErrorName */
632
633
634jvmtiError
635JvmtiEnv::SetVerboseFlag(jvmtiVerboseFlag flag, jboolean value) {
636  switch (flag) {
637  case JVMTI_VERBOSE_OTHER:
638    // ignore
639    break;
640  case JVMTI_VERBOSE_CLASS:
641    if (value == 0) {
642      LogConfiguration::parse_log_arguments("stdout", "classunload=off", NULL, NULL, NULL);
643      LogConfiguration::parse_log_arguments("stdout", "classload=off", NULL, NULL, NULL);
644    } else {
645      LogConfiguration::parse_log_arguments("stdout", "classload=info", NULL, NULL, NULL);
646      LogConfiguration::parse_log_arguments("stdout", "classunload=info", NULL, NULL, NULL);
647    }
648    break;
649  case JVMTI_VERBOSE_GC:
650    if (value == 0) {
651      LogConfiguration::configure_stdout(LogLevel::Off, true, LOG_TAGS(gc));
652    } else {
653      LogConfiguration::configure_stdout(LogLevel::Info, true, LOG_TAGS(gc));
654    }
655    break;
656  case JVMTI_VERBOSE_JNI:
657    PrintJNIResolving = value != 0;
658    break;
659  default:
660    return JVMTI_ERROR_ILLEGAL_ARGUMENT;
661  };
662  return JVMTI_ERROR_NONE;
663} /* end SetVerboseFlag */
664
665
666// format_ptr - pre-checked for NULL
667jvmtiError
668JvmtiEnv::GetJLocationFormat(jvmtiJlocationFormat* format_ptr) {
669  *format_ptr = JVMTI_JLOCATION_JVMBCI;
670  return JVMTI_ERROR_NONE;
671} /* end GetJLocationFormat */
672
673  //
674  // Thread functions
675  //
676
677// Threads_lock NOT held
678// thread - NOT pre-checked
679// thread_state_ptr - pre-checked for NULL
680jvmtiError
681JvmtiEnv::GetThreadState(jthread thread, jint* thread_state_ptr) {
682  jint state;
683  oop thread_oop;
684  JavaThread* thr;
685
686  if (thread == NULL) {
687    thread_oop = JavaThread::current()->threadObj();
688  } else {
689    thread_oop = JNIHandles::resolve_external_guard(thread);
690  }
691
692  if (thread_oop == NULL || !thread_oop->is_a(SystemDictionary::Thread_klass())) {
693    return JVMTI_ERROR_INVALID_THREAD;
694  }
695
696  // get most state bits
697  state = (jint)java_lang_Thread::get_thread_status(thread_oop);
698
699  // add more state bits
700  thr = java_lang_Thread::thread(thread_oop);
701  if (thr != NULL) {
702    JavaThreadState jts = thr->thread_state();
703
704    if (thr->is_being_ext_suspended()) {
705      state |= JVMTI_THREAD_STATE_SUSPENDED;
706    }
707    if (jts == _thread_in_native) {
708      state |= JVMTI_THREAD_STATE_IN_NATIVE;
709    }
710    OSThread* osThread = thr->osthread();
711    if (osThread != NULL && osThread->interrupted()) {
712      state |= JVMTI_THREAD_STATE_INTERRUPTED;
713    }
714  }
715
716  *thread_state_ptr = state;
717  return JVMTI_ERROR_NONE;
718} /* end GetThreadState */
719
720
721// thread_ptr - pre-checked for NULL
722jvmtiError
723JvmtiEnv::GetCurrentThread(jthread* thread_ptr) {
724  JavaThread* current_thread  = JavaThread::current();
725  *thread_ptr = (jthread)JNIHandles::make_local(current_thread, current_thread->threadObj());
726  return JVMTI_ERROR_NONE;
727} /* end GetCurrentThread */
728
729
730// threads_count_ptr - pre-checked for NULL
731// threads_ptr - pre-checked for NULL
732jvmtiError
733JvmtiEnv::GetAllThreads(jint* threads_count_ptr, jthread** threads_ptr) {
734  int nthreads        = 0;
735  Handle *thread_objs = NULL;
736  ResourceMark rm;
737  HandleMark hm;
738
739  // enumerate threads (including agent threads)
740  ThreadsListEnumerator tle(Thread::current(), true);
741  nthreads = tle.num_threads();
742  *threads_count_ptr = nthreads;
743
744  if (nthreads == 0) {
745    *threads_ptr = NULL;
746    return JVMTI_ERROR_NONE;
747  }
748
749  thread_objs = NEW_RESOURCE_ARRAY(Handle, nthreads);
750  NULL_CHECK(thread_objs, JVMTI_ERROR_OUT_OF_MEMORY);
751
752  for (int i=0; i < nthreads; i++) {
753    thread_objs[i] = Handle(tle.get_threadObj(i));
754  }
755
756  // have to make global handles outside of Threads_lock
757  jthread *jthreads  = new_jthreadArray(nthreads, thread_objs);
758  NULL_CHECK(jthreads, JVMTI_ERROR_OUT_OF_MEMORY);
759
760  *threads_ptr = jthreads;
761  return JVMTI_ERROR_NONE;
762} /* end GetAllThreads */
763
764
765// Threads_lock NOT held, java_thread not protected by lock
766// java_thread - pre-checked
767jvmtiError
768JvmtiEnv::SuspendThread(JavaThread* java_thread) {
769  // don't allow hidden thread suspend request.
770  if (java_thread->is_hidden_from_external_view()) {
771    return (JVMTI_ERROR_NONE);
772  }
773
774  {
775    MutexLockerEx ml(java_thread->SR_lock(), Mutex::_no_safepoint_check_flag);
776    if (java_thread->is_external_suspend()) {
777      // don't allow nested external suspend requests.
778      return (JVMTI_ERROR_THREAD_SUSPENDED);
779    }
780    if (java_thread->is_exiting()) { // thread is in the process of exiting
781      return (JVMTI_ERROR_THREAD_NOT_ALIVE);
782    }
783    java_thread->set_external_suspend();
784  }
785
786  if (!JvmtiSuspendControl::suspend(java_thread)) {
787    // the thread was in the process of exiting
788    return (JVMTI_ERROR_THREAD_NOT_ALIVE);
789  }
790  return JVMTI_ERROR_NONE;
791} /* end SuspendThread */
792
793
794// request_count - pre-checked to be greater than or equal to 0
795// request_list - pre-checked for NULL
796// results - pre-checked for NULL
797jvmtiError
798JvmtiEnv::SuspendThreadList(jint request_count, const jthread* request_list, jvmtiError* results) {
799  int needSafepoint = 0;  // > 0 if we need a safepoint
800  for (int i = 0; i < request_count; i++) {
801    JavaThread *java_thread = get_JavaThread(request_list[i]);
802    if (java_thread == NULL) {
803      results[i] = JVMTI_ERROR_INVALID_THREAD;
804      continue;
805    }
806    // the thread has not yet run or has exited (not on threads list)
807    if (java_thread->threadObj() == NULL) {
808      results[i] = JVMTI_ERROR_THREAD_NOT_ALIVE;
809      continue;
810    }
811    if (java_lang_Thread::thread(java_thread->threadObj()) == NULL) {
812      results[i] = JVMTI_ERROR_THREAD_NOT_ALIVE;
813      continue;
814    }
815    // don't allow hidden thread suspend request.
816    if (java_thread->is_hidden_from_external_view()) {
817      results[i] = JVMTI_ERROR_NONE;  // indicate successful suspend
818      continue;
819    }
820
821    {
822      MutexLockerEx ml(java_thread->SR_lock(), Mutex::_no_safepoint_check_flag);
823      if (java_thread->is_external_suspend()) {
824        // don't allow nested external suspend requests.
825        results[i] = JVMTI_ERROR_THREAD_SUSPENDED;
826        continue;
827      }
828      if (java_thread->is_exiting()) { // thread is in the process of exiting
829        results[i] = JVMTI_ERROR_THREAD_NOT_ALIVE;
830        continue;
831      }
832      java_thread->set_external_suspend();
833    }
834    if (java_thread->thread_state() == _thread_in_native) {
835      // We need to try and suspend native threads here. Threads in
836      // other states will self-suspend on their next transition.
837      if (!JvmtiSuspendControl::suspend(java_thread)) {
838        // The thread was in the process of exiting. Force another
839        // safepoint to make sure that this thread transitions.
840        needSafepoint++;
841        results[i] = JVMTI_ERROR_THREAD_NOT_ALIVE;
842        continue;
843      }
844    } else {
845      needSafepoint++;
846    }
847    results[i] = JVMTI_ERROR_NONE;  // indicate successful suspend
848  }
849  if (needSafepoint > 0) {
850    VM_ForceSafepoint vfs;
851    VMThread::execute(&vfs);
852  }
853  // per-thread suspend results returned via results parameter
854  return JVMTI_ERROR_NONE;
855} /* end SuspendThreadList */
856
857
858// Threads_lock NOT held, java_thread not protected by lock
859// java_thread - pre-checked
860jvmtiError
861JvmtiEnv::ResumeThread(JavaThread* java_thread) {
862  // don't allow hidden thread resume request.
863  if (java_thread->is_hidden_from_external_view()) {
864    return JVMTI_ERROR_NONE;
865  }
866
867  if (!java_thread->is_being_ext_suspended()) {
868    return JVMTI_ERROR_THREAD_NOT_SUSPENDED;
869  }
870
871  if (!JvmtiSuspendControl::resume(java_thread)) {
872    return JVMTI_ERROR_INTERNAL;
873  }
874  return JVMTI_ERROR_NONE;
875} /* end ResumeThread */
876
877
878// request_count - pre-checked to be greater than or equal to 0
879// request_list - pre-checked for NULL
880// results - pre-checked for NULL
881jvmtiError
882JvmtiEnv::ResumeThreadList(jint request_count, const jthread* request_list, jvmtiError* results) {
883  for (int i = 0; i < request_count; i++) {
884    JavaThread *java_thread = get_JavaThread(request_list[i]);
885    if (java_thread == NULL) {
886      results[i] = JVMTI_ERROR_INVALID_THREAD;
887      continue;
888    }
889    // don't allow hidden thread resume request.
890    if (java_thread->is_hidden_from_external_view()) {
891      results[i] = JVMTI_ERROR_NONE;  // indicate successful resume
892      continue;
893    }
894    if (!java_thread->is_being_ext_suspended()) {
895      results[i] = JVMTI_ERROR_THREAD_NOT_SUSPENDED;
896      continue;
897    }
898
899    if (!JvmtiSuspendControl::resume(java_thread)) {
900      results[i] = JVMTI_ERROR_INTERNAL;
901      continue;
902    }
903
904    results[i] = JVMTI_ERROR_NONE;  // indicate successful suspend
905  }
906  // per-thread resume results returned via results parameter
907  return JVMTI_ERROR_NONE;
908} /* end ResumeThreadList */
909
910
911// Threads_lock NOT held, java_thread not protected by lock
912// java_thread - pre-checked
913jvmtiError
914JvmtiEnv::StopThread(JavaThread* java_thread, jobject exception) {
915  oop e = JNIHandles::resolve_external_guard(exception);
916  NULL_CHECK(e, JVMTI_ERROR_NULL_POINTER);
917
918  JavaThread::send_async_exception(java_thread->threadObj(), e);
919
920  return JVMTI_ERROR_NONE;
921
922} /* end StopThread */
923
924
925// Threads_lock NOT held
926// thread - NOT pre-checked
927jvmtiError
928JvmtiEnv::InterruptThread(jthread thread) {
929  oop thread_oop = JNIHandles::resolve_external_guard(thread);
930  if (thread_oop == NULL || !thread_oop->is_a(SystemDictionary::Thread_klass()))
931    return JVMTI_ERROR_INVALID_THREAD;
932
933  JavaThread* current_thread  = JavaThread::current();
934
935  // Todo: this is a duplicate of JVM_Interrupt; share code in future
936  // Ensure that the C++ Thread and OSThread structures aren't freed before we operate
937  MutexLockerEx ml(current_thread->threadObj() == thread_oop ? NULL : Threads_lock);
938  // We need to re-resolve the java_thread, since a GC might have happened during the
939  // acquire of the lock
940
941  JavaThread* java_thread = java_lang_Thread::thread(JNIHandles::resolve_external_guard(thread));
942  NULL_CHECK(java_thread, JVMTI_ERROR_THREAD_NOT_ALIVE);
943
944  Thread::interrupt(java_thread);
945
946  return JVMTI_ERROR_NONE;
947} /* end InterruptThread */
948
949
950// Threads_lock NOT held
951// thread - NOT pre-checked
952// info_ptr - pre-checked for NULL
953jvmtiError
954JvmtiEnv::GetThreadInfo(jthread thread, jvmtiThreadInfo* info_ptr) {
955  ResourceMark rm;
956  HandleMark hm;
957
958  JavaThread* current_thread = JavaThread::current();
959
960  // if thread is NULL the current thread is used
961  oop thread_oop;
962  if (thread == NULL) {
963    thread_oop = current_thread->threadObj();
964  } else {
965    thread_oop = JNIHandles::resolve_external_guard(thread);
966  }
967  if (thread_oop == NULL || !thread_oop->is_a(SystemDictionary::Thread_klass()))
968    return JVMTI_ERROR_INVALID_THREAD;
969
970  Handle thread_obj(current_thread, thread_oop);
971  Handle name;
972  ThreadPriority priority;
973  Handle     thread_group;
974  Handle context_class_loader;
975  bool          is_daemon;
976
977  { MutexLocker mu(Threads_lock);
978
979    name = Handle(current_thread, java_lang_Thread::name(thread_obj()));
980    priority = java_lang_Thread::priority(thread_obj());
981    thread_group = Handle(current_thread, java_lang_Thread::threadGroup(thread_obj()));
982    is_daemon = java_lang_Thread::is_daemon(thread_obj());
983
984    oop loader = java_lang_Thread::context_class_loader(thread_obj());
985    context_class_loader = Handle(current_thread, loader);
986  }
987  { const char *n;
988
989    if (name() != NULL) {
990      n = java_lang_String::as_utf8_string(name());
991    } else {
992      n = UNICODE::as_utf8((jchar*) NULL, 0);
993    }
994
995    info_ptr->name = (char *) jvmtiMalloc(strlen(n)+1);
996    if (info_ptr->name == NULL)
997      return JVMTI_ERROR_OUT_OF_MEMORY;
998
999    strcpy(info_ptr->name, n);
1000  }
1001  info_ptr->is_daemon = is_daemon;
1002  info_ptr->priority  = priority;
1003
1004  info_ptr->context_class_loader = (context_class_loader.is_null()) ? NULL :
1005                                     jni_reference(context_class_loader);
1006  info_ptr->thread_group = jni_reference(thread_group);
1007
1008  return JVMTI_ERROR_NONE;
1009} /* end GetThreadInfo */
1010
1011
1012// Threads_lock NOT held, java_thread not protected by lock
1013// java_thread - pre-checked
1014// owned_monitor_count_ptr - pre-checked for NULL
1015// owned_monitors_ptr - pre-checked for NULL
1016jvmtiError
1017JvmtiEnv::GetOwnedMonitorInfo(JavaThread* java_thread, jint* owned_monitor_count_ptr, jobject** owned_monitors_ptr) {
1018  jvmtiError err = JVMTI_ERROR_NONE;
1019  JavaThread* calling_thread = JavaThread::current();
1020
1021  // growable array of jvmti monitors info on the C-heap
1022  GrowableArray<jvmtiMonitorStackDepthInfo*> *owned_monitors_list =
1023      new (ResourceObj::C_HEAP, mtInternal) GrowableArray<jvmtiMonitorStackDepthInfo*>(1, true);
1024
1025  // It is only safe to perform the direct operation on the current
1026  // thread. All other usage needs to use a vm-safepoint-op for safety.
1027  if (java_thread == calling_thread) {
1028    err = get_owned_monitors(calling_thread, java_thread, owned_monitors_list);
1029  } else {
1030    // JVMTI get monitors info at safepoint. Do not require target thread to
1031    // be suspended.
1032    VM_GetOwnedMonitorInfo op(this, calling_thread, java_thread, owned_monitors_list);
1033    VMThread::execute(&op);
1034    err = op.result();
1035  }
1036  jint owned_monitor_count = owned_monitors_list->length();
1037  if (err == JVMTI_ERROR_NONE) {
1038    if ((err = allocate(owned_monitor_count * sizeof(jobject *),
1039                      (unsigned char**)owned_monitors_ptr)) == JVMTI_ERROR_NONE) {
1040      // copy into the returned array
1041      for (int i = 0; i < owned_monitor_count; i++) {
1042        (*owned_monitors_ptr)[i] =
1043          ((jvmtiMonitorStackDepthInfo*)owned_monitors_list->at(i))->monitor;
1044      }
1045      *owned_monitor_count_ptr = owned_monitor_count;
1046    }
1047  }
1048  // clean up.
1049  for (int i = 0; i < owned_monitor_count; i++) {
1050    deallocate((unsigned char*)owned_monitors_list->at(i));
1051  }
1052  delete owned_monitors_list;
1053
1054  return err;
1055} /* end GetOwnedMonitorInfo */
1056
1057
1058// Threads_lock NOT held, java_thread not protected by lock
1059// java_thread - pre-checked
1060// monitor_info_count_ptr - pre-checked for NULL
1061// monitor_info_ptr - pre-checked for NULL
1062jvmtiError
1063JvmtiEnv::GetOwnedMonitorStackDepthInfo(JavaThread* java_thread, jint* monitor_info_count_ptr, jvmtiMonitorStackDepthInfo** monitor_info_ptr) {
1064  jvmtiError err = JVMTI_ERROR_NONE;
1065  JavaThread* calling_thread  = JavaThread::current();
1066
1067  // growable array of jvmti monitors info on the C-heap
1068  GrowableArray<jvmtiMonitorStackDepthInfo*> *owned_monitors_list =
1069         new (ResourceObj::C_HEAP, mtInternal) GrowableArray<jvmtiMonitorStackDepthInfo*>(1, true);
1070
1071  // It is only safe to perform the direct operation on the current
1072  // thread. All other usage needs to use a vm-safepoint-op for safety.
1073  if (java_thread == calling_thread) {
1074    err = get_owned_monitors(calling_thread, java_thread, owned_monitors_list);
1075  } else {
1076    // JVMTI get owned monitors info at safepoint. Do not require target thread to
1077    // be suspended.
1078    VM_GetOwnedMonitorInfo op(this, calling_thread, java_thread, owned_monitors_list);
1079    VMThread::execute(&op);
1080    err = op.result();
1081  }
1082
1083  jint owned_monitor_count = owned_monitors_list->length();
1084  if (err == JVMTI_ERROR_NONE) {
1085    if ((err = allocate(owned_monitor_count * sizeof(jvmtiMonitorStackDepthInfo),
1086                      (unsigned char**)monitor_info_ptr)) == JVMTI_ERROR_NONE) {
1087      // copy to output array.
1088      for (int i = 0; i < owned_monitor_count; i++) {
1089        (*monitor_info_ptr)[i].monitor =
1090          ((jvmtiMonitorStackDepthInfo*)owned_monitors_list->at(i))->monitor;
1091        (*monitor_info_ptr)[i].stack_depth =
1092          ((jvmtiMonitorStackDepthInfo*)owned_monitors_list->at(i))->stack_depth;
1093      }
1094    }
1095    *monitor_info_count_ptr = owned_monitor_count;
1096  }
1097
1098  // clean up.
1099  for (int i = 0; i < owned_monitor_count; i++) {
1100    deallocate((unsigned char*)owned_monitors_list->at(i));
1101  }
1102  delete owned_monitors_list;
1103
1104  return err;
1105} /* end GetOwnedMonitorStackDepthInfo */
1106
1107
1108// Threads_lock NOT held, java_thread not protected by lock
1109// java_thread - pre-checked
1110// monitor_ptr - pre-checked for NULL
1111jvmtiError
1112JvmtiEnv::GetCurrentContendedMonitor(JavaThread* java_thread, jobject* monitor_ptr) {
1113  jvmtiError err = JVMTI_ERROR_NONE;
1114  JavaThread* calling_thread  = JavaThread::current();
1115
1116  // It is only safe to perform the direct operation on the current
1117  // thread. All other usage needs to use a vm-safepoint-op for safety.
1118  if (java_thread == calling_thread) {
1119    err = get_current_contended_monitor(calling_thread, java_thread, monitor_ptr);
1120  } else {
1121    // get contended monitor information at safepoint.
1122    VM_GetCurrentContendedMonitor op(this, calling_thread, java_thread, monitor_ptr);
1123    VMThread::execute(&op);
1124    err = op.result();
1125  }
1126  return err;
1127} /* end GetCurrentContendedMonitor */
1128
1129
1130// Threads_lock NOT held
1131// thread - NOT pre-checked
1132// proc - pre-checked for NULL
1133// arg - NULL is a valid value, must be checked
1134jvmtiError
1135JvmtiEnv::RunAgentThread(jthread thread, jvmtiStartFunction proc, const void* arg, jint priority) {
1136  oop thread_oop = JNIHandles::resolve_external_guard(thread);
1137  if (thread_oop == NULL || !thread_oop->is_a(SystemDictionary::Thread_klass())) {
1138    return JVMTI_ERROR_INVALID_THREAD;
1139  }
1140  if (priority < JVMTI_THREAD_MIN_PRIORITY || priority > JVMTI_THREAD_MAX_PRIORITY) {
1141    return JVMTI_ERROR_INVALID_PRIORITY;
1142  }
1143
1144  //Thread-self
1145  JavaThread* current_thread = JavaThread::current();
1146
1147  Handle thread_hndl(current_thread, thread_oop);
1148  {
1149    MutexLocker mu(Threads_lock); // grab Threads_lock
1150
1151    JvmtiAgentThread *new_thread = new JvmtiAgentThread(this, proc, arg);
1152
1153    // At this point it may be possible that no osthread was created for the
1154    // JavaThread due to lack of memory.
1155    if (new_thread == NULL || new_thread->osthread() == NULL) {
1156      if (new_thread) delete new_thread;
1157      return JVMTI_ERROR_OUT_OF_MEMORY;
1158    }
1159
1160    java_lang_Thread::set_thread(thread_hndl(), new_thread);
1161    java_lang_Thread::set_priority(thread_hndl(), (ThreadPriority)priority);
1162    java_lang_Thread::set_daemon(thread_hndl());
1163
1164    new_thread->set_threadObj(thread_hndl());
1165    Threads::add(new_thread);
1166    Thread::start(new_thread);
1167  } // unlock Threads_lock
1168
1169  return JVMTI_ERROR_NONE;
1170} /* end RunAgentThread */
1171
1172  //
1173  // Thread Group functions
1174  //
1175
1176// group_count_ptr - pre-checked for NULL
1177// groups_ptr - pre-checked for NULL
1178jvmtiError
1179JvmtiEnv::GetTopThreadGroups(jint* group_count_ptr, jthreadGroup** groups_ptr) {
1180  JavaThread* current_thread = JavaThread::current();
1181
1182  // Only one top level thread group now.
1183  *group_count_ptr = 1;
1184
1185  // Allocate memory to store global-refs to the thread groups.
1186  // Assume this area is freed by caller.
1187  *groups_ptr = (jthreadGroup *) jvmtiMalloc((sizeof(jthreadGroup)) * (*group_count_ptr));
1188
1189  NULL_CHECK(*groups_ptr, JVMTI_ERROR_OUT_OF_MEMORY);
1190
1191  // Convert oop to Handle, then convert Handle to global-ref.
1192  {
1193    HandleMark hm(current_thread);
1194    Handle system_thread_group(current_thread, Universe::system_thread_group());
1195    *groups_ptr[0] = jni_reference(system_thread_group);
1196  }
1197
1198  return JVMTI_ERROR_NONE;
1199} /* end GetTopThreadGroups */
1200
1201
1202// info_ptr - pre-checked for NULL
1203jvmtiError
1204JvmtiEnv::GetThreadGroupInfo(jthreadGroup group, jvmtiThreadGroupInfo* info_ptr) {
1205  ResourceMark rm;
1206  HandleMark hm;
1207
1208  JavaThread* current_thread = JavaThread::current();
1209
1210  Handle group_obj (current_thread, JNIHandles::resolve_external_guard(group));
1211  NULL_CHECK(group_obj(), JVMTI_ERROR_INVALID_THREAD_GROUP);
1212
1213  const char* name;
1214  Handle parent_group;
1215  bool is_daemon;
1216  ThreadPriority max_priority;
1217
1218  { MutexLocker mu(Threads_lock);
1219
1220    name         = java_lang_ThreadGroup::name(group_obj());
1221    parent_group = Handle(current_thread, java_lang_ThreadGroup::parent(group_obj()));
1222    is_daemon    = java_lang_ThreadGroup::is_daemon(group_obj());
1223    max_priority = java_lang_ThreadGroup::maxPriority(group_obj());
1224  }
1225
1226  info_ptr->is_daemon    = is_daemon;
1227  info_ptr->max_priority = max_priority;
1228  info_ptr->parent       = jni_reference(parent_group);
1229
1230  if (name != NULL) {
1231    info_ptr->name = (char*)jvmtiMalloc(strlen(name)+1);
1232    NULL_CHECK(info_ptr->name, JVMTI_ERROR_OUT_OF_MEMORY);
1233    strcpy(info_ptr->name, name);
1234  } else {
1235    info_ptr->name = NULL;
1236  }
1237
1238  return JVMTI_ERROR_NONE;
1239} /* end GetThreadGroupInfo */
1240
1241
1242// thread_count_ptr - pre-checked for NULL
1243// threads_ptr - pre-checked for NULL
1244// group_count_ptr - pre-checked for NULL
1245// groups_ptr - pre-checked for NULL
1246jvmtiError
1247JvmtiEnv::GetThreadGroupChildren(jthreadGroup group, jint* thread_count_ptr, jthread** threads_ptr, jint* group_count_ptr, jthreadGroup** groups_ptr) {
1248  JavaThread* current_thread = JavaThread::current();
1249  oop group_obj = (oop) JNIHandles::resolve_external_guard(group);
1250  NULL_CHECK(group_obj, JVMTI_ERROR_INVALID_THREAD_GROUP);
1251
1252  Handle *thread_objs = NULL;
1253  Handle *group_objs  = NULL;
1254  int nthreads = 0;
1255  int ngroups = 0;
1256  int hidden_threads = 0;
1257
1258  ResourceMark rm;
1259  HandleMark hm;
1260
1261  Handle group_hdl(current_thread, group_obj);
1262
1263  { MutexLocker mu(Threads_lock);
1264
1265    nthreads = java_lang_ThreadGroup::nthreads(group_hdl());
1266    ngroups  = java_lang_ThreadGroup::ngroups(group_hdl());
1267
1268    if (nthreads > 0) {
1269      objArrayOop threads = java_lang_ThreadGroup::threads(group_hdl());
1270      assert(nthreads <= threads->length(), "too many threads");
1271      thread_objs = NEW_RESOURCE_ARRAY(Handle,nthreads);
1272      for (int i=0, j=0; i<nthreads; i++) {
1273        oop thread_obj = threads->obj_at(i);
1274        assert(thread_obj != NULL, "thread_obj is NULL");
1275        JavaThread *javathread = java_lang_Thread::thread(thread_obj);
1276        // Filter out hidden java threads.
1277        if (javathread != NULL && javathread->is_hidden_from_external_view()) {
1278          hidden_threads++;
1279          continue;
1280        }
1281        thread_objs[j++] = Handle(current_thread, thread_obj);
1282      }
1283      nthreads -= hidden_threads;
1284    }
1285    if (ngroups > 0) {
1286      objArrayOop groups = java_lang_ThreadGroup::groups(group_hdl());
1287      assert(ngroups <= groups->length(), "too many threads");
1288      group_objs = NEW_RESOURCE_ARRAY(Handle,ngroups);
1289      for (int i=0; i<ngroups; i++) {
1290        oop group_obj = groups->obj_at(i);
1291        assert(group_obj != NULL, "group_obj != NULL");
1292        group_objs[i] = Handle(current_thread, group_obj);
1293      }
1294    }
1295  }
1296
1297  // have to make global handles outside of Threads_lock
1298  *group_count_ptr  = ngroups;
1299  *thread_count_ptr = nthreads;
1300  *threads_ptr     = new_jthreadArray(nthreads, thread_objs);
1301  *groups_ptr      = new_jthreadGroupArray(ngroups, group_objs);
1302  if ((nthreads > 0) && (*threads_ptr == NULL)) {
1303    return JVMTI_ERROR_OUT_OF_MEMORY;
1304  }
1305  if ((ngroups > 0) && (*groups_ptr == NULL)) {
1306    return JVMTI_ERROR_OUT_OF_MEMORY;
1307  }
1308
1309  return JVMTI_ERROR_NONE;
1310} /* end GetThreadGroupChildren */
1311
1312
1313  //
1314  // Stack Frame functions
1315  //
1316
1317// Threads_lock NOT held, java_thread not protected by lock
1318// java_thread - pre-checked
1319// max_frame_count - pre-checked to be greater than or equal to 0
1320// frame_buffer - pre-checked for NULL
1321// count_ptr - pre-checked for NULL
1322jvmtiError
1323JvmtiEnv::GetStackTrace(JavaThread* java_thread, jint start_depth, jint max_frame_count, jvmtiFrameInfo* frame_buffer, jint* count_ptr) {
1324  jvmtiError err = JVMTI_ERROR_NONE;
1325
1326  // It is only safe to perform the direct operation on the current
1327  // thread. All other usage needs to use a vm-safepoint-op for safety.
1328  if (java_thread == JavaThread::current()) {
1329    err = get_stack_trace(java_thread, start_depth, max_frame_count, frame_buffer, count_ptr);
1330  } else {
1331    // JVMTI get stack trace at safepoint. Do not require target thread to
1332    // be suspended.
1333    VM_GetStackTrace op(this, java_thread, start_depth, max_frame_count, frame_buffer, count_ptr);
1334    VMThread::execute(&op);
1335    err = op.result();
1336  }
1337
1338  return err;
1339} /* end GetStackTrace */
1340
1341
1342// max_frame_count - pre-checked to be greater than or equal to 0
1343// stack_info_ptr - pre-checked for NULL
1344// thread_count_ptr - pre-checked for NULL
1345jvmtiError
1346JvmtiEnv::GetAllStackTraces(jint max_frame_count, jvmtiStackInfo** stack_info_ptr, jint* thread_count_ptr) {
1347  jvmtiError err = JVMTI_ERROR_NONE;
1348  JavaThread* calling_thread = JavaThread::current();
1349
1350  // JVMTI get stack traces at safepoint.
1351  VM_GetAllStackTraces op(this, calling_thread, max_frame_count);
1352  VMThread::execute(&op);
1353  *thread_count_ptr = op.final_thread_count();
1354  *stack_info_ptr = op.stack_info();
1355  err = op.result();
1356  return err;
1357} /* end GetAllStackTraces */
1358
1359
1360// thread_count - pre-checked to be greater than or equal to 0
1361// thread_list - pre-checked for NULL
1362// max_frame_count - pre-checked to be greater than or equal to 0
1363// stack_info_ptr - pre-checked for NULL
1364jvmtiError
1365JvmtiEnv::GetThreadListStackTraces(jint thread_count, const jthread* thread_list, jint max_frame_count, jvmtiStackInfo** stack_info_ptr) {
1366  jvmtiError err = JVMTI_ERROR_NONE;
1367  // JVMTI get stack traces at safepoint.
1368  VM_GetThreadListStackTraces op(this, thread_count, thread_list, max_frame_count);
1369  VMThread::execute(&op);
1370  err = op.result();
1371  if (err == JVMTI_ERROR_NONE) {
1372    *stack_info_ptr = op.stack_info();
1373  }
1374  return err;
1375} /* end GetThreadListStackTraces */
1376
1377
1378// Threads_lock NOT held, java_thread not protected by lock
1379// java_thread - pre-checked
1380// count_ptr - pre-checked for NULL
1381jvmtiError
1382JvmtiEnv::GetFrameCount(JavaThread* java_thread, jint* count_ptr) {
1383  jvmtiError err = JVMTI_ERROR_NONE;
1384
1385  // retrieve or create JvmtiThreadState.
1386  JvmtiThreadState* state = JvmtiThreadState::state_for(java_thread);
1387  if (state == NULL) {
1388    return JVMTI_ERROR_THREAD_NOT_ALIVE;
1389  }
1390
1391  // It is only safe to perform the direct operation on the current
1392  // thread. All other usage needs to use a vm-safepoint-op for safety.
1393  if (java_thread == JavaThread::current()) {
1394    err = get_frame_count(state, count_ptr);
1395  } else {
1396    // get java stack frame count at safepoint.
1397    VM_GetFrameCount op(this, state, count_ptr);
1398    VMThread::execute(&op);
1399    err = op.result();
1400  }
1401  return err;
1402} /* end GetFrameCount */
1403
1404
1405// Threads_lock NOT held, java_thread not protected by lock
1406// java_thread - pre-checked
1407jvmtiError
1408JvmtiEnv::PopFrame(JavaThread* java_thread) {
1409  JavaThread* current_thread  = JavaThread::current();
1410  HandleMark hm(current_thread);
1411  uint32_t debug_bits = 0;
1412
1413  // retrieve or create the state
1414  JvmtiThreadState* state = JvmtiThreadState::state_for(java_thread);
1415  if (state == NULL) {
1416    return JVMTI_ERROR_THREAD_NOT_ALIVE;
1417  }
1418
1419  // Check if java_thread is fully suspended
1420  if (!is_thread_fully_suspended(java_thread, true /* wait for suspend completion */, &debug_bits)) {
1421    return JVMTI_ERROR_THREAD_NOT_SUSPENDED;
1422  }
1423  // Check to see if a PopFrame was already in progress
1424  if (java_thread->popframe_condition() != JavaThread::popframe_inactive) {
1425    // Probably possible for JVMTI clients to trigger this, but the
1426    // JPDA backend shouldn't allow this to happen
1427    return JVMTI_ERROR_INTERNAL;
1428  }
1429
1430  {
1431    // Was workaround bug
1432    //    4812902: popFrame hangs if the method is waiting at a synchronize
1433    // Catch this condition and return an error to avoid hanging.
1434    // Now JVMTI spec allows an implementation to bail out with an opaque frame error.
1435    OSThread* osThread = java_thread->osthread();
1436    if (osThread->get_state() == MONITOR_WAIT) {
1437      return JVMTI_ERROR_OPAQUE_FRAME;
1438    }
1439  }
1440
1441  {
1442    ResourceMark rm(current_thread);
1443    // Check if there are more than one Java frame in this thread, that the top two frames
1444    // are Java (not native) frames, and that there is no intervening VM frame
1445    int frame_count = 0;
1446    bool is_interpreted[2];
1447    intptr_t *frame_sp[2];
1448    // The 2-nd arg of constructor is needed to stop iterating at java entry frame.
1449    for (vframeStream vfs(java_thread, true); !vfs.at_end(); vfs.next()) {
1450      methodHandle mh(current_thread, vfs.method());
1451      if (mh->is_native()) return(JVMTI_ERROR_OPAQUE_FRAME);
1452      is_interpreted[frame_count] = vfs.is_interpreted_frame();
1453      frame_sp[frame_count] = vfs.frame_id();
1454      if (++frame_count > 1) break;
1455    }
1456    if (frame_count < 2)  {
1457      // We haven't found two adjacent non-native Java frames on the top.
1458      // There can be two situations here:
1459      //  1. There are no more java frames
1460      //  2. Two top java frames are separated by non-java native frames
1461      if(vframeFor(java_thread, 1) == NULL) {
1462        return JVMTI_ERROR_NO_MORE_FRAMES;
1463      } else {
1464        // Intervening non-java native or VM frames separate java frames.
1465        // Current implementation does not support this. See bug #5031735.
1466        // In theory it is possible to pop frames in such cases.
1467        return JVMTI_ERROR_OPAQUE_FRAME;
1468      }
1469    }
1470
1471    // If any of the top 2 frames is a compiled one, need to deoptimize it
1472    for (int i = 0; i < 2; i++) {
1473      if (!is_interpreted[i]) {
1474        Deoptimization::deoptimize_frame(java_thread, frame_sp[i]);
1475      }
1476    }
1477
1478    // Update the thread state to reflect that the top frame is popped
1479    // so that cur_stack_depth is maintained properly and all frameIDs
1480    // are invalidated.
1481    // The current frame will be popped later when the suspended thread
1482    // is resumed and right before returning from VM to Java.
1483    // (see call_VM_base() in assembler_<cpu>.cpp).
1484
1485    // It's fine to update the thread state here because no JVMTI events
1486    // shall be posted for this PopFrame.
1487
1488    // It is only safe to perform the direct operation on the current
1489    // thread. All other usage needs to use a vm-safepoint-op for safety.
1490    if (java_thread == JavaThread::current()) {
1491      state->update_for_pop_top_frame();
1492    } else {
1493      VM_UpdateForPopTopFrame op(state);
1494      VMThread::execute(&op);
1495      jvmtiError err = op.result();
1496      if (err != JVMTI_ERROR_NONE) {
1497        return err;
1498      }
1499    }
1500
1501    java_thread->set_popframe_condition(JavaThread::popframe_pending_bit);
1502    // Set pending step flag for this popframe and it is cleared when next
1503    // step event is posted.
1504    state->set_pending_step_for_popframe();
1505  }
1506
1507  return JVMTI_ERROR_NONE;
1508} /* end PopFrame */
1509
1510
1511// Threads_lock NOT held, java_thread not protected by lock
1512// java_thread - pre-checked
1513// java_thread - unchecked
1514// depth - pre-checked as non-negative
1515// method_ptr - pre-checked for NULL
1516// location_ptr - pre-checked for NULL
1517jvmtiError
1518JvmtiEnv::GetFrameLocation(JavaThread* java_thread, jint depth, jmethodID* method_ptr, jlocation* location_ptr) {
1519  jvmtiError err = JVMTI_ERROR_NONE;
1520
1521  // It is only safe to perform the direct operation on the current
1522  // thread. All other usage needs to use a vm-safepoint-op for safety.
1523  if (java_thread == JavaThread::current()) {
1524    err = get_frame_location(java_thread, depth, method_ptr, location_ptr);
1525  } else {
1526    // JVMTI get java stack frame location at safepoint.
1527    VM_GetFrameLocation op(this, java_thread, depth, method_ptr, location_ptr);
1528    VMThread::execute(&op);
1529    err = op.result();
1530  }
1531  return err;
1532} /* end GetFrameLocation */
1533
1534
1535// Threads_lock NOT held, java_thread not protected by lock
1536// java_thread - pre-checked
1537// java_thread - unchecked
1538// depth - pre-checked as non-negative
1539jvmtiError
1540JvmtiEnv::NotifyFramePop(JavaThread* java_thread, jint depth) {
1541  jvmtiError err = JVMTI_ERROR_NONE;
1542  ResourceMark rm;
1543  uint32_t debug_bits = 0;
1544
1545  JvmtiThreadState *state = JvmtiThreadState::state_for(java_thread);
1546  if (state == NULL) {
1547    return JVMTI_ERROR_THREAD_NOT_ALIVE;
1548  }
1549
1550  if (!JvmtiEnv::is_thread_fully_suspended(java_thread, true, &debug_bits)) {
1551      return JVMTI_ERROR_THREAD_NOT_SUSPENDED;
1552  }
1553
1554  if (TraceJVMTICalls) {
1555    JvmtiSuspendControl::print();
1556  }
1557
1558  vframe *vf = vframeFor(java_thread, depth);
1559  if (vf == NULL) {
1560    return JVMTI_ERROR_NO_MORE_FRAMES;
1561  }
1562
1563  if (!vf->is_java_frame() || ((javaVFrame*) vf)->method()->is_native()) {
1564    return JVMTI_ERROR_OPAQUE_FRAME;
1565  }
1566
1567  assert(vf->frame_pointer() != NULL, "frame pointer mustn't be NULL");
1568
1569  // It is only safe to perform the direct operation on the current
1570  // thread. All other usage needs to use a vm-safepoint-op for safety.
1571  if (java_thread == JavaThread::current()) {
1572    int frame_number = state->count_frames() - depth;
1573    state->env_thread_state(this)->set_frame_pop(frame_number);
1574  } else {
1575    VM_SetFramePop op(this, state, depth);
1576    VMThread::execute(&op);
1577    err = op.result();
1578  }
1579  return err;
1580} /* end NotifyFramePop */
1581
1582
1583  //
1584  // Force Early Return functions
1585  //
1586
1587// Threads_lock NOT held, java_thread not protected by lock
1588// java_thread - pre-checked
1589jvmtiError
1590JvmtiEnv::ForceEarlyReturnObject(JavaThread* java_thread, jobject value) {
1591  jvalue val;
1592  val.l = value;
1593  return force_early_return(java_thread, val, atos);
1594} /* end ForceEarlyReturnObject */
1595
1596
1597// Threads_lock NOT held, java_thread not protected by lock
1598// java_thread - pre-checked
1599jvmtiError
1600JvmtiEnv::ForceEarlyReturnInt(JavaThread* java_thread, jint value) {
1601  jvalue val;
1602  val.i = value;
1603  return force_early_return(java_thread, val, itos);
1604} /* end ForceEarlyReturnInt */
1605
1606
1607// Threads_lock NOT held, java_thread not protected by lock
1608// java_thread - pre-checked
1609jvmtiError
1610JvmtiEnv::ForceEarlyReturnLong(JavaThread* java_thread, jlong value) {
1611  jvalue val;
1612  val.j = value;
1613  return force_early_return(java_thread, val, ltos);
1614} /* end ForceEarlyReturnLong */
1615
1616
1617// Threads_lock NOT held, java_thread not protected by lock
1618// java_thread - pre-checked
1619jvmtiError
1620JvmtiEnv::ForceEarlyReturnFloat(JavaThread* java_thread, jfloat value) {
1621  jvalue val;
1622  val.f = value;
1623  return force_early_return(java_thread, val, ftos);
1624} /* end ForceEarlyReturnFloat */
1625
1626
1627// Threads_lock NOT held, java_thread not protected by lock
1628// java_thread - pre-checked
1629jvmtiError
1630JvmtiEnv::ForceEarlyReturnDouble(JavaThread* java_thread, jdouble value) {
1631  jvalue val;
1632  val.d = value;
1633  return force_early_return(java_thread, val, dtos);
1634} /* end ForceEarlyReturnDouble */
1635
1636
1637// Threads_lock NOT held, java_thread not protected by lock
1638// java_thread - pre-checked
1639jvmtiError
1640JvmtiEnv::ForceEarlyReturnVoid(JavaThread* java_thread) {
1641  jvalue val;
1642  val.j = 0L;
1643  return force_early_return(java_thread, val, vtos);
1644} /* end ForceEarlyReturnVoid */
1645
1646
1647  //
1648  // Heap functions
1649  //
1650
1651// klass - NULL is a valid value, must be checked
1652// initial_object - NULL is a valid value, must be checked
1653// callbacks - pre-checked for NULL
1654// user_data - NULL is a valid value, must be checked
1655jvmtiError
1656JvmtiEnv::FollowReferences(jint heap_filter, jclass klass, jobject initial_object, const jvmtiHeapCallbacks* callbacks, const void* user_data) {
1657  // check klass if provided
1658  Klass* k_oop = NULL;
1659  if (klass != NULL) {
1660    oop k_mirror = JNIHandles::resolve_external_guard(klass);
1661    if (k_mirror == NULL) {
1662      return JVMTI_ERROR_INVALID_CLASS;
1663    }
1664    if (java_lang_Class::is_primitive(k_mirror)) {
1665      return JVMTI_ERROR_NONE;
1666    }
1667    k_oop = java_lang_Class::as_Klass(k_mirror);
1668    if (k_oop == NULL) {
1669      return JVMTI_ERROR_INVALID_CLASS;
1670    }
1671  }
1672
1673  Thread *thread = Thread::current();
1674  HandleMark hm(thread);
1675  KlassHandle kh (thread, k_oop);
1676
1677  TraceTime t("FollowReferences", TraceJVMTIObjectTagging);
1678  JvmtiTagMap::tag_map_for(this)->follow_references(heap_filter, kh, initial_object, callbacks, user_data);
1679  return JVMTI_ERROR_NONE;
1680} /* end FollowReferences */
1681
1682
1683// klass - NULL is a valid value, must be checked
1684// callbacks - pre-checked for NULL
1685// user_data - NULL is a valid value, must be checked
1686jvmtiError
1687JvmtiEnv::IterateThroughHeap(jint heap_filter, jclass klass, const jvmtiHeapCallbacks* callbacks, const void* user_data) {
1688  // check klass if provided
1689  Klass* k_oop = NULL;
1690  if (klass != NULL) {
1691    oop k_mirror = JNIHandles::resolve_external_guard(klass);
1692    if (k_mirror == NULL) {
1693      return JVMTI_ERROR_INVALID_CLASS;
1694    }
1695    if (java_lang_Class::is_primitive(k_mirror)) {
1696      return JVMTI_ERROR_NONE;
1697    }
1698    k_oop = java_lang_Class::as_Klass(k_mirror);
1699    if (k_oop == NULL) {
1700      return JVMTI_ERROR_INVALID_CLASS;
1701    }
1702  }
1703
1704  Thread *thread = Thread::current();
1705  HandleMark hm(thread);
1706  KlassHandle kh (thread, k_oop);
1707
1708  TraceTime t("IterateThroughHeap", TraceJVMTIObjectTagging);
1709  JvmtiTagMap::tag_map_for(this)->iterate_through_heap(heap_filter, kh, callbacks, user_data);
1710  return JVMTI_ERROR_NONE;
1711} /* end IterateThroughHeap */
1712
1713
1714// tag_ptr - pre-checked for NULL
1715jvmtiError
1716JvmtiEnv::GetTag(jobject object, jlong* tag_ptr) {
1717  oop o = JNIHandles::resolve_external_guard(object);
1718  NULL_CHECK(o, JVMTI_ERROR_INVALID_OBJECT);
1719  *tag_ptr = JvmtiTagMap::tag_map_for(this)->get_tag(object);
1720  return JVMTI_ERROR_NONE;
1721} /* end GetTag */
1722
1723
1724jvmtiError
1725JvmtiEnv::SetTag(jobject object, jlong tag) {
1726  oop o = JNIHandles::resolve_external_guard(object);
1727  NULL_CHECK(o, JVMTI_ERROR_INVALID_OBJECT);
1728  JvmtiTagMap::tag_map_for(this)->set_tag(object, tag);
1729  return JVMTI_ERROR_NONE;
1730} /* end SetTag */
1731
1732
1733// tag_count - pre-checked to be greater than or equal to 0
1734// tags - pre-checked for NULL
1735// count_ptr - pre-checked for NULL
1736// object_result_ptr - NULL is a valid value, must be checked
1737// tag_result_ptr - NULL is a valid value, must be checked
1738jvmtiError
1739JvmtiEnv::GetObjectsWithTags(jint tag_count, const jlong* tags, jint* count_ptr, jobject** object_result_ptr, jlong** tag_result_ptr) {
1740  TraceTime t("GetObjectsWithTags", TraceJVMTIObjectTagging);
1741  return JvmtiTagMap::tag_map_for(this)->get_objects_with_tags((jlong*)tags, tag_count, count_ptr, object_result_ptr, tag_result_ptr);
1742} /* end GetObjectsWithTags */
1743
1744
1745jvmtiError
1746JvmtiEnv::ForceGarbageCollection() {
1747  Universe::heap()->collect(GCCause::_jvmti_force_gc);
1748  return JVMTI_ERROR_NONE;
1749} /* end ForceGarbageCollection */
1750
1751
1752  //
1753  // Heap (1.0) functions
1754  //
1755
1756// object_reference_callback - pre-checked for NULL
1757// user_data - NULL is a valid value, must be checked
1758jvmtiError
1759JvmtiEnv::IterateOverObjectsReachableFromObject(jobject object, jvmtiObjectReferenceCallback object_reference_callback, const void* user_data) {
1760  oop o = JNIHandles::resolve_external_guard(object);
1761  NULL_CHECK(o, JVMTI_ERROR_INVALID_OBJECT);
1762  JvmtiTagMap::tag_map_for(this)->iterate_over_objects_reachable_from_object(object, object_reference_callback, user_data);
1763  return JVMTI_ERROR_NONE;
1764} /* end IterateOverObjectsReachableFromObject */
1765
1766
1767// heap_root_callback - NULL is a valid value, must be checked
1768// stack_ref_callback - NULL is a valid value, must be checked
1769// object_ref_callback - NULL is a valid value, must be checked
1770// user_data - NULL is a valid value, must be checked
1771jvmtiError
1772JvmtiEnv::IterateOverReachableObjects(jvmtiHeapRootCallback heap_root_callback, jvmtiStackReferenceCallback stack_ref_callback, jvmtiObjectReferenceCallback object_ref_callback, const void* user_data) {
1773  TraceTime t("IterateOverReachableObjects", TraceJVMTIObjectTagging);
1774  JvmtiTagMap::tag_map_for(this)->iterate_over_reachable_objects(heap_root_callback, stack_ref_callback, object_ref_callback, user_data);
1775  return JVMTI_ERROR_NONE;
1776} /* end IterateOverReachableObjects */
1777
1778
1779// heap_object_callback - pre-checked for NULL
1780// user_data - NULL is a valid value, must be checked
1781jvmtiError
1782JvmtiEnv::IterateOverHeap(jvmtiHeapObjectFilter object_filter, jvmtiHeapObjectCallback heap_object_callback, const void* user_data) {
1783  TraceTime t("IterateOverHeap", TraceJVMTIObjectTagging);
1784  Thread *thread = Thread::current();
1785  HandleMark hm(thread);
1786  JvmtiTagMap::tag_map_for(this)->iterate_over_heap(object_filter, KlassHandle(), heap_object_callback, user_data);
1787  return JVMTI_ERROR_NONE;
1788} /* end IterateOverHeap */
1789
1790
1791// k_mirror - may be primitive, this must be checked
1792// heap_object_callback - pre-checked for NULL
1793// user_data - NULL is a valid value, must be checked
1794jvmtiError
1795JvmtiEnv::IterateOverInstancesOfClass(oop k_mirror, jvmtiHeapObjectFilter object_filter, jvmtiHeapObjectCallback heap_object_callback, const void* user_data) {
1796  if (java_lang_Class::is_primitive(k_mirror)) {
1797    // DO PRIMITIVE CLASS PROCESSING
1798    return JVMTI_ERROR_NONE;
1799  }
1800  Klass* k_oop = java_lang_Class::as_Klass(k_mirror);
1801  if (k_oop == NULL) {
1802    return JVMTI_ERROR_INVALID_CLASS;
1803  }
1804  Thread *thread = Thread::current();
1805  HandleMark hm(thread);
1806  KlassHandle klass (thread, k_oop);
1807  TraceTime t("IterateOverInstancesOfClass", TraceJVMTIObjectTagging);
1808  JvmtiTagMap::tag_map_for(this)->iterate_over_heap(object_filter, klass, heap_object_callback, user_data);
1809  return JVMTI_ERROR_NONE;
1810} /* end IterateOverInstancesOfClass */
1811
1812
1813  //
1814  // Local Variable functions
1815  //
1816
1817// Threads_lock NOT held, java_thread not protected by lock
1818// java_thread - pre-checked
1819// java_thread - unchecked
1820// depth - pre-checked as non-negative
1821// value_ptr - pre-checked for NULL
1822jvmtiError
1823JvmtiEnv::GetLocalObject(JavaThread* java_thread, jint depth, jint slot, jobject* value_ptr) {
1824  JavaThread* current_thread = JavaThread::current();
1825  // rm object is created to clean up the javaVFrame created in
1826  // doit_prologue(), but after doit() is finished with it.
1827  ResourceMark rm(current_thread);
1828
1829  VM_GetOrSetLocal op(java_thread, current_thread, depth, slot);
1830  VMThread::execute(&op);
1831  jvmtiError err = op.result();
1832  if (err != JVMTI_ERROR_NONE) {
1833    return err;
1834  } else {
1835    *value_ptr = op.value().l;
1836    return JVMTI_ERROR_NONE;
1837  }
1838} /* end GetLocalObject */
1839
1840// Threads_lock NOT held, java_thread not protected by lock
1841// java_thread - pre-checked
1842// java_thread - unchecked
1843// depth - pre-checked as non-negative
1844// value - pre-checked for NULL
1845jvmtiError
1846JvmtiEnv::GetLocalInstance(JavaThread* java_thread, jint depth, jobject* value_ptr){
1847  JavaThread* current_thread = JavaThread::current();
1848  // rm object is created to clean up the javaVFrame created in
1849  // doit_prologue(), but after doit() is finished with it.
1850  ResourceMark rm(current_thread);
1851
1852  VM_GetReceiver op(java_thread, current_thread, depth);
1853  VMThread::execute(&op);
1854  jvmtiError err = op.result();
1855  if (err != JVMTI_ERROR_NONE) {
1856    return err;
1857  } else {
1858    *value_ptr = op.value().l;
1859    return JVMTI_ERROR_NONE;
1860  }
1861} /* end GetLocalInstance */
1862
1863
1864// Threads_lock NOT held, java_thread not protected by lock
1865// java_thread - pre-checked
1866// java_thread - unchecked
1867// depth - pre-checked as non-negative
1868// value_ptr - pre-checked for NULL
1869jvmtiError
1870JvmtiEnv::GetLocalInt(JavaThread* java_thread, jint depth, jint slot, jint* value_ptr) {
1871  // rm object is created to clean up the javaVFrame created in
1872  // doit_prologue(), but after doit() is finished with it.
1873  ResourceMark rm;
1874
1875  VM_GetOrSetLocal op(java_thread, depth, slot, T_INT);
1876  VMThread::execute(&op);
1877  *value_ptr = op.value().i;
1878  return op.result();
1879} /* end GetLocalInt */
1880
1881
1882// Threads_lock NOT held, java_thread not protected by lock
1883// java_thread - pre-checked
1884// java_thread - unchecked
1885// depth - pre-checked as non-negative
1886// value_ptr - pre-checked for NULL
1887jvmtiError
1888JvmtiEnv::GetLocalLong(JavaThread* java_thread, jint depth, jint slot, jlong* value_ptr) {
1889  // rm object is created to clean up the javaVFrame created in
1890  // doit_prologue(), but after doit() is finished with it.
1891  ResourceMark rm;
1892
1893  VM_GetOrSetLocal op(java_thread, depth, slot, T_LONG);
1894  VMThread::execute(&op);
1895  *value_ptr = op.value().j;
1896  return op.result();
1897} /* end GetLocalLong */
1898
1899
1900// Threads_lock NOT held, java_thread not protected by lock
1901// java_thread - pre-checked
1902// java_thread - unchecked
1903// depth - pre-checked as non-negative
1904// value_ptr - pre-checked for NULL
1905jvmtiError
1906JvmtiEnv::GetLocalFloat(JavaThread* java_thread, jint depth, jint slot, jfloat* value_ptr) {
1907  // rm object is created to clean up the javaVFrame created in
1908  // doit_prologue(), but after doit() is finished with it.
1909  ResourceMark rm;
1910
1911  VM_GetOrSetLocal op(java_thread, depth, slot, T_FLOAT);
1912  VMThread::execute(&op);
1913  *value_ptr = op.value().f;
1914  return op.result();
1915} /* end GetLocalFloat */
1916
1917
1918// Threads_lock NOT held, java_thread not protected by lock
1919// java_thread - pre-checked
1920// java_thread - unchecked
1921// depth - pre-checked as non-negative
1922// value_ptr - pre-checked for NULL
1923jvmtiError
1924JvmtiEnv::GetLocalDouble(JavaThread* java_thread, jint depth, jint slot, jdouble* value_ptr) {
1925  // rm object is created to clean up the javaVFrame created in
1926  // doit_prologue(), but after doit() is finished with it.
1927  ResourceMark rm;
1928
1929  VM_GetOrSetLocal op(java_thread, depth, slot, T_DOUBLE);
1930  VMThread::execute(&op);
1931  *value_ptr = op.value().d;
1932  return op.result();
1933} /* end GetLocalDouble */
1934
1935
1936// Threads_lock NOT held, java_thread not protected by lock
1937// java_thread - pre-checked
1938// java_thread - unchecked
1939// depth - pre-checked as non-negative
1940jvmtiError
1941JvmtiEnv::SetLocalObject(JavaThread* java_thread, jint depth, jint slot, jobject value) {
1942  // rm object is created to clean up the javaVFrame created in
1943  // doit_prologue(), but after doit() is finished with it.
1944  ResourceMark rm;
1945  jvalue val;
1946  val.l = value;
1947  VM_GetOrSetLocal op(java_thread, depth, slot, T_OBJECT, val);
1948  VMThread::execute(&op);
1949  return op.result();
1950} /* end SetLocalObject */
1951
1952
1953// Threads_lock NOT held, java_thread not protected by lock
1954// java_thread - pre-checked
1955// java_thread - unchecked
1956// depth - pre-checked as non-negative
1957jvmtiError
1958JvmtiEnv::SetLocalInt(JavaThread* java_thread, jint depth, jint slot, jint value) {
1959  // rm object is created to clean up the javaVFrame created in
1960  // doit_prologue(), but after doit() is finished with it.
1961  ResourceMark rm;
1962  jvalue val;
1963  val.i = value;
1964  VM_GetOrSetLocal op(java_thread, depth, slot, T_INT, val);
1965  VMThread::execute(&op);
1966  return op.result();
1967} /* end SetLocalInt */
1968
1969
1970// Threads_lock NOT held, java_thread not protected by lock
1971// java_thread - pre-checked
1972// java_thread - unchecked
1973// depth - pre-checked as non-negative
1974jvmtiError
1975JvmtiEnv::SetLocalLong(JavaThread* java_thread, jint depth, jint slot, jlong value) {
1976  // rm object is created to clean up the javaVFrame created in
1977  // doit_prologue(), but after doit() is finished with it.
1978  ResourceMark rm;
1979  jvalue val;
1980  val.j = value;
1981  VM_GetOrSetLocal op(java_thread, depth, slot, T_LONG, val);
1982  VMThread::execute(&op);
1983  return op.result();
1984} /* end SetLocalLong */
1985
1986
1987// Threads_lock NOT held, java_thread not protected by lock
1988// java_thread - pre-checked
1989// java_thread - unchecked
1990// depth - pre-checked as non-negative
1991jvmtiError
1992JvmtiEnv::SetLocalFloat(JavaThread* java_thread, jint depth, jint slot, jfloat value) {
1993  // rm object is created to clean up the javaVFrame created in
1994  // doit_prologue(), but after doit() is finished with it.
1995  ResourceMark rm;
1996  jvalue val;
1997  val.f = value;
1998  VM_GetOrSetLocal op(java_thread, depth, slot, T_FLOAT, val);
1999  VMThread::execute(&op);
2000  return op.result();
2001} /* end SetLocalFloat */
2002
2003
2004// Threads_lock NOT held, java_thread not protected by lock
2005// java_thread - pre-checked
2006// java_thread - unchecked
2007// depth - pre-checked as non-negative
2008jvmtiError
2009JvmtiEnv::SetLocalDouble(JavaThread* java_thread, jint depth, jint slot, jdouble value) {
2010  // rm object is created to clean up the javaVFrame created in
2011  // doit_prologue(), but after doit() is finished with it.
2012  ResourceMark rm;
2013  jvalue val;
2014  val.d = value;
2015  VM_GetOrSetLocal op(java_thread, depth, slot, T_DOUBLE, val);
2016  VMThread::execute(&op);
2017  return op.result();
2018} /* end SetLocalDouble */
2019
2020
2021  //
2022  // Breakpoint functions
2023  //
2024
2025// method_oop - pre-checked for validity, but may be NULL meaning obsolete method
2026jvmtiError
2027JvmtiEnv::SetBreakpoint(Method* method_oop, jlocation location) {
2028  NULL_CHECK(method_oop, JVMTI_ERROR_INVALID_METHODID);
2029  if (location < 0) {   // simple invalid location check first
2030    return JVMTI_ERROR_INVALID_LOCATION;
2031  }
2032  // verify that the breakpoint is not past the end of the method
2033  if (location >= (jlocation) method_oop->code_size()) {
2034    return JVMTI_ERROR_INVALID_LOCATION;
2035  }
2036
2037  ResourceMark rm;
2038  JvmtiBreakpoint bp(method_oop, location);
2039  JvmtiBreakpoints& jvmti_breakpoints = JvmtiCurrentBreakpoints::get_jvmti_breakpoints();
2040  if (jvmti_breakpoints.set(bp) == JVMTI_ERROR_DUPLICATE)
2041    return JVMTI_ERROR_DUPLICATE;
2042
2043  if (TraceJVMTICalls) {
2044    jvmti_breakpoints.print();
2045  }
2046
2047  return JVMTI_ERROR_NONE;
2048} /* end SetBreakpoint */
2049
2050
2051// method_oop - pre-checked for validity, but may be NULL meaning obsolete method
2052jvmtiError
2053JvmtiEnv::ClearBreakpoint(Method* method_oop, jlocation location) {
2054  NULL_CHECK(method_oop, JVMTI_ERROR_INVALID_METHODID);
2055
2056  if (location < 0) {   // simple invalid location check first
2057    return JVMTI_ERROR_INVALID_LOCATION;
2058  }
2059
2060  // verify that the breakpoint is not past the end of the method
2061  if (location >= (jlocation) method_oop->code_size()) {
2062    return JVMTI_ERROR_INVALID_LOCATION;
2063  }
2064
2065  JvmtiBreakpoint bp(method_oop, location);
2066
2067  JvmtiBreakpoints& jvmti_breakpoints = JvmtiCurrentBreakpoints::get_jvmti_breakpoints();
2068  if (jvmti_breakpoints.clear(bp) == JVMTI_ERROR_NOT_FOUND)
2069    return JVMTI_ERROR_NOT_FOUND;
2070
2071  if (TraceJVMTICalls) {
2072    jvmti_breakpoints.print();
2073  }
2074
2075  return JVMTI_ERROR_NONE;
2076} /* end ClearBreakpoint */
2077
2078
2079  //
2080  // Watched Field functions
2081  //
2082
2083jvmtiError
2084JvmtiEnv::SetFieldAccessWatch(fieldDescriptor* fdesc_ptr) {
2085  // make sure we haven't set this watch before
2086  if (fdesc_ptr->is_field_access_watched()) return JVMTI_ERROR_DUPLICATE;
2087  fdesc_ptr->set_is_field_access_watched(true);
2088
2089  JvmtiEventController::change_field_watch(JVMTI_EVENT_FIELD_ACCESS, true);
2090
2091  return JVMTI_ERROR_NONE;
2092} /* end SetFieldAccessWatch */
2093
2094
2095jvmtiError
2096JvmtiEnv::ClearFieldAccessWatch(fieldDescriptor* fdesc_ptr) {
2097  // make sure we have a watch to clear
2098  if (!fdesc_ptr->is_field_access_watched()) return JVMTI_ERROR_NOT_FOUND;
2099  fdesc_ptr->set_is_field_access_watched(false);
2100
2101  JvmtiEventController::change_field_watch(JVMTI_EVENT_FIELD_ACCESS, false);
2102
2103  return JVMTI_ERROR_NONE;
2104} /* end ClearFieldAccessWatch */
2105
2106
2107jvmtiError
2108JvmtiEnv::SetFieldModificationWatch(fieldDescriptor* fdesc_ptr) {
2109  // make sure we haven't set this watch before
2110  if (fdesc_ptr->is_field_modification_watched()) return JVMTI_ERROR_DUPLICATE;
2111  fdesc_ptr->set_is_field_modification_watched(true);
2112
2113  JvmtiEventController::change_field_watch(JVMTI_EVENT_FIELD_MODIFICATION, true);
2114
2115  return JVMTI_ERROR_NONE;
2116} /* end SetFieldModificationWatch */
2117
2118
2119jvmtiError
2120JvmtiEnv::ClearFieldModificationWatch(fieldDescriptor* fdesc_ptr) {
2121   // make sure we have a watch to clear
2122  if (!fdesc_ptr->is_field_modification_watched()) return JVMTI_ERROR_NOT_FOUND;
2123  fdesc_ptr->set_is_field_modification_watched(false);
2124
2125  JvmtiEventController::change_field_watch(JVMTI_EVENT_FIELD_MODIFICATION, false);
2126
2127  return JVMTI_ERROR_NONE;
2128} /* end ClearFieldModificationWatch */
2129
2130  //
2131  // Class functions
2132  //
2133
2134
2135// k_mirror - may be primitive, this must be checked
2136// signature_ptr - NULL is a valid value, must be checked
2137// generic_ptr - NULL is a valid value, must be checked
2138jvmtiError
2139JvmtiEnv::GetClassSignature(oop k_mirror, char** signature_ptr, char** generic_ptr) {
2140  ResourceMark rm;
2141  bool isPrimitive = java_lang_Class::is_primitive(k_mirror);
2142  Klass* k = NULL;
2143  if (!isPrimitive) {
2144    k = java_lang_Class::as_Klass(k_mirror);
2145    NULL_CHECK(k, JVMTI_ERROR_INVALID_CLASS);
2146  }
2147  if (signature_ptr != NULL) {
2148    char* result = NULL;
2149    if (isPrimitive) {
2150      char tchar = type2char(java_lang_Class::primitive_type(k_mirror));
2151      result = (char*) jvmtiMalloc(2);
2152      result[0] = tchar;
2153      result[1] = '\0';
2154    } else {
2155      const char* class_sig = k->signature_name();
2156      result = (char *) jvmtiMalloc(strlen(class_sig)+1);
2157      strcpy(result, class_sig);
2158    }
2159    *signature_ptr = result;
2160  }
2161  if (generic_ptr != NULL) {
2162    *generic_ptr = NULL;
2163    if (!isPrimitive && k->is_instance_klass()) {
2164      Symbol* soo = InstanceKlass::cast(k)->generic_signature();
2165      if (soo != NULL) {
2166        const char *gen_sig = soo->as_C_string();
2167        if (gen_sig != NULL) {
2168          char* gen_result;
2169          jvmtiError err = allocate(strlen(gen_sig) + 1,
2170                                    (unsigned char **)&gen_result);
2171          if (err != JVMTI_ERROR_NONE) {
2172            return err;
2173          }
2174          strcpy(gen_result, gen_sig);
2175          *generic_ptr = gen_result;
2176        }
2177      }
2178    }
2179  }
2180  return JVMTI_ERROR_NONE;
2181} /* end GetClassSignature */
2182
2183
2184// k_mirror - may be primitive, this must be checked
2185// status_ptr - pre-checked for NULL
2186jvmtiError
2187JvmtiEnv::GetClassStatus(oop k_mirror, jint* status_ptr) {
2188  jint result = 0;
2189  if (java_lang_Class::is_primitive(k_mirror)) {
2190    result |= JVMTI_CLASS_STATUS_PRIMITIVE;
2191  } else {
2192    Klass* k = java_lang_Class::as_Klass(k_mirror);
2193    NULL_CHECK(k, JVMTI_ERROR_INVALID_CLASS);
2194    result = k->jvmti_class_status();
2195  }
2196  *status_ptr = result;
2197
2198  return JVMTI_ERROR_NONE;
2199} /* end GetClassStatus */
2200
2201
2202// k_mirror - may be primitive, this must be checked
2203// source_name_ptr - pre-checked for NULL
2204jvmtiError
2205JvmtiEnv::GetSourceFileName(oop k_mirror, char** source_name_ptr) {
2206  if (java_lang_Class::is_primitive(k_mirror)) {
2207     return JVMTI_ERROR_ABSENT_INFORMATION;
2208  }
2209  Klass* k_klass = java_lang_Class::as_Klass(k_mirror);
2210  NULL_CHECK(k_klass, JVMTI_ERROR_INVALID_CLASS);
2211
2212  if (!k_klass->is_instance_klass()) {
2213    return JVMTI_ERROR_ABSENT_INFORMATION;
2214  }
2215
2216  Symbol* sfnOop = InstanceKlass::cast(k_klass)->source_file_name();
2217  NULL_CHECK(sfnOop, JVMTI_ERROR_ABSENT_INFORMATION);
2218  {
2219    JavaThread* current_thread  = JavaThread::current();
2220    ResourceMark rm(current_thread);
2221    const char* sfncp = (const char*) sfnOop->as_C_string();
2222    *source_name_ptr = (char *) jvmtiMalloc(strlen(sfncp)+1);
2223    strcpy(*source_name_ptr, sfncp);
2224  }
2225
2226  return JVMTI_ERROR_NONE;
2227} /* end GetSourceFileName */
2228
2229
2230// k_mirror - may be primitive, this must be checked
2231// modifiers_ptr - pre-checked for NULL
2232jvmtiError
2233JvmtiEnv::GetClassModifiers(oop k_mirror, jint* modifiers_ptr) {
2234  JavaThread* current_thread  = JavaThread::current();
2235  jint result = 0;
2236  if (!java_lang_Class::is_primitive(k_mirror)) {
2237    Klass* k = java_lang_Class::as_Klass(k_mirror);
2238    NULL_CHECK(k, JVMTI_ERROR_INVALID_CLASS);
2239    result = k->compute_modifier_flags(current_thread);
2240    JavaThread* THREAD = current_thread; // pass to macros
2241    if (HAS_PENDING_EXCEPTION) {
2242      CLEAR_PENDING_EXCEPTION;
2243      return JVMTI_ERROR_INTERNAL;
2244    };
2245
2246    // Reset the deleted  ACC_SUPER bit ( deleted in compute_modifier_flags()).
2247    if(k->is_super()) {
2248      result |= JVM_ACC_SUPER;
2249    }
2250  } else {
2251    result = (JVM_ACC_ABSTRACT | JVM_ACC_FINAL | JVM_ACC_PUBLIC);
2252  }
2253  *modifiers_ptr = result;
2254
2255  return JVMTI_ERROR_NONE;
2256} /* end GetClassModifiers */
2257
2258
2259// k_mirror - may be primitive, this must be checked
2260// method_count_ptr - pre-checked for NULL
2261// methods_ptr - pre-checked for NULL
2262jvmtiError
2263JvmtiEnv::GetClassMethods(oop k_mirror, jint* method_count_ptr, jmethodID** methods_ptr) {
2264  JavaThread* current_thread  = JavaThread::current();
2265  HandleMark hm(current_thread);
2266
2267  if (java_lang_Class::is_primitive(k_mirror)) {
2268    *method_count_ptr = 0;
2269    *methods_ptr = (jmethodID*) jvmtiMalloc(0 * sizeof(jmethodID));
2270    return JVMTI_ERROR_NONE;
2271  }
2272  Klass* k = java_lang_Class::as_Klass(k_mirror);
2273  NULL_CHECK(k, JVMTI_ERROR_INVALID_CLASS);
2274
2275  // Return CLASS_NOT_PREPARED error as per JVMTI spec.
2276  if (!(k->jvmti_class_status() & (JVMTI_CLASS_STATUS_PREPARED|JVMTI_CLASS_STATUS_ARRAY) )) {
2277    return JVMTI_ERROR_CLASS_NOT_PREPARED;
2278  }
2279
2280  if (!k->is_instance_klass()) {
2281    *method_count_ptr = 0;
2282    *methods_ptr = (jmethodID*) jvmtiMalloc(0 * sizeof(jmethodID));
2283    return JVMTI_ERROR_NONE;
2284  }
2285  instanceKlassHandle instanceK_h(current_thread, k);
2286  // Allocate the result and fill it in
2287  int result_length = instanceK_h->methods()->length();
2288  jmethodID* result_list = (jmethodID*)jvmtiMalloc(result_length * sizeof(jmethodID));
2289  int index;
2290  bool jmethodids_found = true;
2291
2292  if (JvmtiExport::can_maintain_original_method_order()) {
2293    // Use the original method ordering indices stored in the class, so we can emit
2294    // jmethodIDs in the order they appeared in the class file
2295    for (index = 0; index < result_length; index++) {
2296      Method* m = instanceK_h->methods()->at(index);
2297      int original_index = instanceK_h->method_ordering()->at(index);
2298      assert(original_index >= 0 && original_index < result_length, "invalid original method index");
2299      jmethodID id;
2300      if (jmethodids_found) {
2301        id = m->find_jmethod_id_or_null();
2302        if (id == NULL) {
2303          // If we find an uninitialized value, make sure there is
2304          // enough space for all the uninitialized values we might
2305          // find.
2306          instanceK_h->ensure_space_for_methodids(index);
2307          jmethodids_found = false;
2308          id = m->jmethod_id();
2309        }
2310      } else {
2311        id = m->jmethod_id();
2312      }
2313      result_list[original_index] = id;
2314    }
2315  } else {
2316    // otherwise just copy in any order
2317    for (index = 0; index < result_length; index++) {
2318      Method* m = instanceK_h->methods()->at(index);
2319      jmethodID id;
2320      if (jmethodids_found) {
2321        id = m->find_jmethod_id_or_null();
2322        if (id == NULL) {
2323          // If we find an uninitialized value, make sure there is
2324          // enough space for all the uninitialized values we might
2325          // find.
2326          instanceK_h->ensure_space_for_methodids(index);
2327          jmethodids_found = false;
2328          id = m->jmethod_id();
2329        }
2330      } else {
2331        id = m->jmethod_id();
2332      }
2333      result_list[index] = id;
2334    }
2335  }
2336  // Fill in return value.
2337  *method_count_ptr = result_length;
2338  *methods_ptr = result_list;
2339
2340  return JVMTI_ERROR_NONE;
2341} /* end GetClassMethods */
2342
2343
2344// k_mirror - may be primitive, this must be checked
2345// field_count_ptr - pre-checked for NULL
2346// fields_ptr - pre-checked for NULL
2347jvmtiError
2348JvmtiEnv::GetClassFields(oop k_mirror, jint* field_count_ptr, jfieldID** fields_ptr) {
2349  if (java_lang_Class::is_primitive(k_mirror)) {
2350    *field_count_ptr = 0;
2351    *fields_ptr = (jfieldID*) jvmtiMalloc(0 * sizeof(jfieldID));
2352    return JVMTI_ERROR_NONE;
2353  }
2354  JavaThread* current_thread = JavaThread::current();
2355  HandleMark hm(current_thread);
2356  Klass* k = java_lang_Class::as_Klass(k_mirror);
2357  NULL_CHECK(k, JVMTI_ERROR_INVALID_CLASS);
2358
2359  // Return CLASS_NOT_PREPARED error as per JVMTI spec.
2360  if (!(k->jvmti_class_status() & (JVMTI_CLASS_STATUS_PREPARED|JVMTI_CLASS_STATUS_ARRAY) )) {
2361    return JVMTI_ERROR_CLASS_NOT_PREPARED;
2362  }
2363
2364  if (!k->is_instance_klass()) {
2365    *field_count_ptr = 0;
2366    *fields_ptr = (jfieldID*) jvmtiMalloc(0 * sizeof(jfieldID));
2367    return JVMTI_ERROR_NONE;
2368  }
2369
2370
2371  instanceKlassHandle instanceK_h(current_thread, k);
2372
2373  int result_count = 0;
2374  // First, count the fields.
2375  FilteredFieldStream flds(instanceK_h, true, true);
2376  result_count = flds.field_count();
2377
2378  // Allocate the result and fill it in
2379  jfieldID* result_list = (jfieldID*) jvmtiMalloc(result_count * sizeof(jfieldID));
2380  // The JVMTI spec requires fields in the order they occur in the class file,
2381  // this is the reverse order of what FieldStream hands out.
2382  int id_index = (result_count - 1);
2383
2384  for (FilteredFieldStream src_st(instanceK_h, true, true); !src_st.eos(); src_st.next()) {
2385    result_list[id_index--] = jfieldIDWorkaround::to_jfieldID(
2386                                            instanceK_h, src_st.offset(),
2387                                            src_st.access_flags().is_static());
2388  }
2389  assert(id_index == -1, "just checking");
2390  // Fill in the results
2391  *field_count_ptr = result_count;
2392  *fields_ptr = result_list;
2393
2394  return JVMTI_ERROR_NONE;
2395} /* end GetClassFields */
2396
2397
2398// k_mirror - may be primitive, this must be checked
2399// interface_count_ptr - pre-checked for NULL
2400// interfaces_ptr - pre-checked for NULL
2401jvmtiError
2402JvmtiEnv::GetImplementedInterfaces(oop k_mirror, jint* interface_count_ptr, jclass** interfaces_ptr) {
2403  {
2404    if (java_lang_Class::is_primitive(k_mirror)) {
2405      *interface_count_ptr = 0;
2406      *interfaces_ptr = (jclass*) jvmtiMalloc(0 * sizeof(jclass));
2407      return JVMTI_ERROR_NONE;
2408    }
2409    JavaThread* current_thread = JavaThread::current();
2410    HandleMark hm(current_thread);
2411    Klass* k = java_lang_Class::as_Klass(k_mirror);
2412    NULL_CHECK(k, JVMTI_ERROR_INVALID_CLASS);
2413
2414    // Return CLASS_NOT_PREPARED error as per JVMTI spec.
2415    if (!(k->jvmti_class_status() & (JVMTI_CLASS_STATUS_PREPARED|JVMTI_CLASS_STATUS_ARRAY) ))
2416      return JVMTI_ERROR_CLASS_NOT_PREPARED;
2417
2418    if (!k->is_instance_klass()) {
2419      *interface_count_ptr = 0;
2420      *interfaces_ptr = (jclass*) jvmtiMalloc(0 * sizeof(jclass));
2421      return JVMTI_ERROR_NONE;
2422    }
2423
2424    Array<Klass*>* interface_list = InstanceKlass::cast(k)->local_interfaces();
2425    const int result_length = (interface_list == NULL ? 0 : interface_list->length());
2426    jclass* result_list = (jclass*) jvmtiMalloc(result_length * sizeof(jclass));
2427    for (int i_index = 0; i_index < result_length; i_index += 1) {
2428      Klass* klass_at = interface_list->at(i_index);
2429      assert(klass_at->is_klass(), "interfaces must be Klass*s");
2430      assert(klass_at->is_interface(), "interfaces must be interfaces");
2431      oop mirror_at = klass_at->java_mirror();
2432      Handle handle_at = Handle(current_thread, mirror_at);
2433      result_list[i_index] = (jclass) jni_reference(handle_at);
2434    }
2435    *interface_count_ptr = result_length;
2436    *interfaces_ptr = result_list;
2437  }
2438
2439  return JVMTI_ERROR_NONE;
2440} /* end GetImplementedInterfaces */
2441
2442
2443// k_mirror - may be primitive, this must be checked
2444// minor_version_ptr - pre-checked for NULL
2445// major_version_ptr - pre-checked for NULL
2446jvmtiError
2447JvmtiEnv::GetClassVersionNumbers(oop k_mirror, jint* minor_version_ptr, jint* major_version_ptr) {
2448  if (java_lang_Class::is_primitive(k_mirror)) {
2449    return JVMTI_ERROR_ABSENT_INFORMATION;
2450  }
2451  Klass* k_oop = java_lang_Class::as_Klass(k_mirror);
2452  Thread *thread = Thread::current();
2453  HandleMark hm(thread);
2454  KlassHandle klass(thread, k_oop);
2455
2456  jint status = klass->jvmti_class_status();
2457  if (status & (JVMTI_CLASS_STATUS_ERROR)) {
2458    return JVMTI_ERROR_INVALID_CLASS;
2459  }
2460  if (status & (JVMTI_CLASS_STATUS_ARRAY)) {
2461    return JVMTI_ERROR_ABSENT_INFORMATION;
2462  }
2463
2464  instanceKlassHandle ik(thread, k_oop);
2465  *minor_version_ptr = ik->minor_version();
2466  *major_version_ptr = ik->major_version();
2467
2468  return JVMTI_ERROR_NONE;
2469} /* end GetClassVersionNumbers */
2470
2471
2472// k_mirror - may be primitive, this must be checked
2473// constant_pool_count_ptr - pre-checked for NULL
2474// constant_pool_byte_count_ptr - pre-checked for NULL
2475// constant_pool_bytes_ptr - pre-checked for NULL
2476jvmtiError
2477JvmtiEnv::GetConstantPool(oop k_mirror, jint* constant_pool_count_ptr, jint* constant_pool_byte_count_ptr, unsigned char** constant_pool_bytes_ptr) {
2478  if (java_lang_Class::is_primitive(k_mirror)) {
2479    return JVMTI_ERROR_ABSENT_INFORMATION;
2480  }
2481
2482  Klass* k_oop = java_lang_Class::as_Klass(k_mirror);
2483  Thread *thread = Thread::current();
2484  HandleMark hm(thread);
2485  ResourceMark rm(thread);
2486  KlassHandle klass(thread, k_oop);
2487
2488  jint status = klass->jvmti_class_status();
2489  if (status & (JVMTI_CLASS_STATUS_ERROR)) {
2490    return JVMTI_ERROR_INVALID_CLASS;
2491  }
2492  if (status & (JVMTI_CLASS_STATUS_ARRAY)) {
2493    return JVMTI_ERROR_ABSENT_INFORMATION;
2494  }
2495
2496  instanceKlassHandle ikh(thread, k_oop);
2497  JvmtiConstantPoolReconstituter reconstituter(ikh);
2498  if (reconstituter.get_error() != JVMTI_ERROR_NONE) {
2499    return reconstituter.get_error();
2500  }
2501
2502  unsigned char *cpool_bytes;
2503  int cpool_size = reconstituter.cpool_size();
2504  if (reconstituter.get_error() != JVMTI_ERROR_NONE) {
2505    return reconstituter.get_error();
2506  }
2507  jvmtiError res = allocate(cpool_size, &cpool_bytes);
2508  if (res != JVMTI_ERROR_NONE) {
2509    return res;
2510  }
2511  reconstituter.copy_cpool_bytes(cpool_bytes);
2512  if (reconstituter.get_error() != JVMTI_ERROR_NONE) {
2513    return reconstituter.get_error();
2514  }
2515
2516  constantPoolHandle  constants(thread, ikh->constants());
2517  *constant_pool_count_ptr      = constants->length();
2518  *constant_pool_byte_count_ptr = cpool_size;
2519  *constant_pool_bytes_ptr      = cpool_bytes;
2520
2521  return JVMTI_ERROR_NONE;
2522} /* end GetConstantPool */
2523
2524
2525// k_mirror - may be primitive, this must be checked
2526// is_interface_ptr - pre-checked for NULL
2527jvmtiError
2528JvmtiEnv::IsInterface(oop k_mirror, jboolean* is_interface_ptr) {
2529  {
2530    bool result = false;
2531    if (!java_lang_Class::is_primitive(k_mirror)) {
2532      Klass* k = java_lang_Class::as_Klass(k_mirror);
2533      if (k != NULL && k->is_interface()) {
2534        result = true;
2535      }
2536    }
2537    *is_interface_ptr = result;
2538  }
2539
2540  return JVMTI_ERROR_NONE;
2541} /* end IsInterface */
2542
2543
2544// k_mirror - may be primitive, this must be checked
2545// is_array_class_ptr - pre-checked for NULL
2546jvmtiError
2547JvmtiEnv::IsArrayClass(oop k_mirror, jboolean* is_array_class_ptr) {
2548  {
2549    bool result = false;
2550    if (!java_lang_Class::is_primitive(k_mirror)) {
2551      Klass* k = java_lang_Class::as_Klass(k_mirror);
2552      if (k != NULL && k->is_array_klass()) {
2553        result = true;
2554      }
2555    }
2556    *is_array_class_ptr = result;
2557  }
2558
2559  return JVMTI_ERROR_NONE;
2560} /* end IsArrayClass */
2561
2562
2563// k_mirror - may be primitive, this must be checked
2564// classloader_ptr - pre-checked for NULL
2565jvmtiError
2566JvmtiEnv::GetClassLoader(oop k_mirror, jobject* classloader_ptr) {
2567  {
2568    if (java_lang_Class::is_primitive(k_mirror)) {
2569      *classloader_ptr = (jclass) jni_reference(Handle());
2570      return JVMTI_ERROR_NONE;
2571    }
2572    JavaThread* current_thread = JavaThread::current();
2573    HandleMark hm(current_thread);
2574    Klass* k = java_lang_Class::as_Klass(k_mirror);
2575    NULL_CHECK(k, JVMTI_ERROR_INVALID_CLASS);
2576
2577    oop result_oop = k->class_loader();
2578    if (result_oop == NULL) {
2579      *classloader_ptr = (jclass) jni_reference(Handle());
2580      return JVMTI_ERROR_NONE;
2581    }
2582    Handle result_handle = Handle(current_thread, result_oop);
2583    jclass result_jnihandle = (jclass) jni_reference(result_handle);
2584    *classloader_ptr = result_jnihandle;
2585  }
2586  return JVMTI_ERROR_NONE;
2587} /* end GetClassLoader */
2588
2589
2590// k_mirror - may be primitive, this must be checked
2591// source_debug_extension_ptr - pre-checked for NULL
2592jvmtiError
2593JvmtiEnv::GetSourceDebugExtension(oop k_mirror, char** source_debug_extension_ptr) {
2594  {
2595    if (java_lang_Class::is_primitive(k_mirror)) {
2596      return JVMTI_ERROR_ABSENT_INFORMATION;
2597    }
2598    Klass* k = java_lang_Class::as_Klass(k_mirror);
2599    NULL_CHECK(k, JVMTI_ERROR_INVALID_CLASS);
2600    if (!k->is_instance_klass()) {
2601      return JVMTI_ERROR_ABSENT_INFORMATION;
2602    }
2603    const char* sde = InstanceKlass::cast(k)->source_debug_extension();
2604    NULL_CHECK(sde, JVMTI_ERROR_ABSENT_INFORMATION);
2605
2606    {
2607      *source_debug_extension_ptr = (char *) jvmtiMalloc(strlen(sde)+1);
2608      strcpy(*source_debug_extension_ptr, sde);
2609    }
2610  }
2611
2612  return JVMTI_ERROR_NONE;
2613} /* end GetSourceDebugExtension */
2614
2615  //
2616  // Object functions
2617  //
2618
2619// hash_code_ptr - pre-checked for NULL
2620jvmtiError
2621JvmtiEnv::GetObjectHashCode(jobject object, jint* hash_code_ptr) {
2622  oop mirror = JNIHandles::resolve_external_guard(object);
2623  NULL_CHECK(mirror, JVMTI_ERROR_INVALID_OBJECT);
2624  NULL_CHECK(hash_code_ptr, JVMTI_ERROR_NULL_POINTER);
2625
2626  {
2627    jint result = (jint) mirror->identity_hash();
2628    *hash_code_ptr = result;
2629  }
2630  return JVMTI_ERROR_NONE;
2631} /* end GetObjectHashCode */
2632
2633
2634// info_ptr - pre-checked for NULL
2635jvmtiError
2636JvmtiEnv::GetObjectMonitorUsage(jobject object, jvmtiMonitorUsage* info_ptr) {
2637  JavaThread* calling_thread = JavaThread::current();
2638  jvmtiError err = get_object_monitor_usage(calling_thread, object, info_ptr);
2639  if (err == JVMTI_ERROR_THREAD_NOT_SUSPENDED) {
2640    // Some of the critical threads were not suspended. go to a safepoint and try again
2641    VM_GetObjectMonitorUsage op(this, calling_thread, object, info_ptr);
2642    VMThread::execute(&op);
2643    err = op.result();
2644  }
2645  return err;
2646} /* end GetObjectMonitorUsage */
2647
2648
2649  //
2650  // Field functions
2651  //
2652
2653// name_ptr - NULL is a valid value, must be checked
2654// signature_ptr - NULL is a valid value, must be checked
2655// generic_ptr - NULL is a valid value, must be checked
2656jvmtiError
2657JvmtiEnv::GetFieldName(fieldDescriptor* fdesc_ptr, char** name_ptr, char** signature_ptr, char** generic_ptr) {
2658  JavaThread* current_thread  = JavaThread::current();
2659  ResourceMark rm(current_thread);
2660  if (name_ptr == NULL) {
2661    // just don't return the name
2662  } else {
2663    const char* fieldName = fdesc_ptr->name()->as_C_string();
2664    *name_ptr =  (char*) jvmtiMalloc(strlen(fieldName) + 1);
2665    if (*name_ptr == NULL)
2666      return JVMTI_ERROR_OUT_OF_MEMORY;
2667    strcpy(*name_ptr, fieldName);
2668  }
2669  if (signature_ptr== NULL) {
2670    // just don't return the signature
2671  } else {
2672    const char* fieldSignature = fdesc_ptr->signature()->as_C_string();
2673    *signature_ptr = (char*) jvmtiMalloc(strlen(fieldSignature) + 1);
2674    if (*signature_ptr == NULL)
2675      return JVMTI_ERROR_OUT_OF_MEMORY;
2676    strcpy(*signature_ptr, fieldSignature);
2677  }
2678  if (generic_ptr != NULL) {
2679    *generic_ptr = NULL;
2680    Symbol* soop = fdesc_ptr->generic_signature();
2681    if (soop != NULL) {
2682      const char* gen_sig = soop->as_C_string();
2683      if (gen_sig != NULL) {
2684        jvmtiError err = allocate(strlen(gen_sig) + 1, (unsigned char **)generic_ptr);
2685        if (err != JVMTI_ERROR_NONE) {
2686          return err;
2687        }
2688        strcpy(*generic_ptr, gen_sig);
2689      }
2690    }
2691  }
2692  return JVMTI_ERROR_NONE;
2693} /* end GetFieldName */
2694
2695
2696// declaring_class_ptr - pre-checked for NULL
2697jvmtiError
2698JvmtiEnv::GetFieldDeclaringClass(fieldDescriptor* fdesc_ptr, jclass* declaring_class_ptr) {
2699
2700  *declaring_class_ptr = get_jni_class_non_null(fdesc_ptr->field_holder());
2701  return JVMTI_ERROR_NONE;
2702} /* end GetFieldDeclaringClass */
2703
2704
2705// modifiers_ptr - pre-checked for NULL
2706jvmtiError
2707JvmtiEnv::GetFieldModifiers(fieldDescriptor* fdesc_ptr, jint* modifiers_ptr) {
2708
2709  AccessFlags resultFlags = fdesc_ptr->access_flags();
2710  jint result = resultFlags.as_int();
2711  *modifiers_ptr = result;
2712
2713  return JVMTI_ERROR_NONE;
2714} /* end GetFieldModifiers */
2715
2716
2717// is_synthetic_ptr - pre-checked for NULL
2718jvmtiError
2719JvmtiEnv::IsFieldSynthetic(fieldDescriptor* fdesc_ptr, jboolean* is_synthetic_ptr) {
2720  *is_synthetic_ptr = fdesc_ptr->is_synthetic();
2721  return JVMTI_ERROR_NONE;
2722} /* end IsFieldSynthetic */
2723
2724
2725  //
2726  // Method functions
2727  //
2728
2729// method_oop - pre-checked for validity, but may be NULL meaning obsolete method
2730// name_ptr - NULL is a valid value, must be checked
2731// signature_ptr - NULL is a valid value, must be checked
2732// generic_ptr - NULL is a valid value, must be checked
2733jvmtiError
2734JvmtiEnv::GetMethodName(Method* method_oop, char** name_ptr, char** signature_ptr, char** generic_ptr) {
2735  NULL_CHECK(method_oop, JVMTI_ERROR_INVALID_METHODID);
2736  JavaThread* current_thread  = JavaThread::current();
2737
2738  ResourceMark rm(current_thread); // get the utf8 name and signature
2739  if (name_ptr == NULL) {
2740    // just don't return the name
2741  } else {
2742    const char* utf8_name = (const char *) method_oop->name()->as_utf8();
2743    *name_ptr = (char *) jvmtiMalloc(strlen(utf8_name)+1);
2744    strcpy(*name_ptr, utf8_name);
2745  }
2746  if (signature_ptr == NULL) {
2747    // just don't return the signature
2748  } else {
2749    const char* utf8_signature = (const char *) method_oop->signature()->as_utf8();
2750    *signature_ptr = (char *) jvmtiMalloc(strlen(utf8_signature) + 1);
2751    strcpy(*signature_ptr, utf8_signature);
2752  }
2753
2754  if (generic_ptr != NULL) {
2755    *generic_ptr = NULL;
2756    Symbol* soop = method_oop->generic_signature();
2757    if (soop != NULL) {
2758      const char* gen_sig = soop->as_C_string();
2759      if (gen_sig != NULL) {
2760        jvmtiError err = allocate(strlen(gen_sig) + 1, (unsigned char **)generic_ptr);
2761        if (err != JVMTI_ERROR_NONE) {
2762          return err;
2763        }
2764        strcpy(*generic_ptr, gen_sig);
2765      }
2766    }
2767  }
2768  return JVMTI_ERROR_NONE;
2769} /* end GetMethodName */
2770
2771
2772// method_oop - pre-checked for validity, but may be NULL meaning obsolete method
2773// declaring_class_ptr - pre-checked for NULL
2774jvmtiError
2775JvmtiEnv::GetMethodDeclaringClass(Method* method_oop, jclass* declaring_class_ptr) {
2776  NULL_CHECK(method_oop, JVMTI_ERROR_INVALID_METHODID);
2777  (*declaring_class_ptr) = get_jni_class_non_null(method_oop->method_holder());
2778  return JVMTI_ERROR_NONE;
2779} /* end GetMethodDeclaringClass */
2780
2781
2782// method_oop - pre-checked for validity, but may be NULL meaning obsolete method
2783// modifiers_ptr - pre-checked for NULL
2784jvmtiError
2785JvmtiEnv::GetMethodModifiers(Method* method_oop, jint* modifiers_ptr) {
2786  NULL_CHECK(method_oop, JVMTI_ERROR_INVALID_METHODID);
2787  (*modifiers_ptr) = method_oop->access_flags().as_int() & JVM_RECOGNIZED_METHOD_MODIFIERS;
2788  return JVMTI_ERROR_NONE;
2789} /* end GetMethodModifiers */
2790
2791
2792// method_oop - pre-checked for validity, but may be NULL meaning obsolete method
2793// max_ptr - pre-checked for NULL
2794jvmtiError
2795JvmtiEnv::GetMaxLocals(Method* method_oop, jint* max_ptr) {
2796  NULL_CHECK(method_oop, JVMTI_ERROR_INVALID_METHODID);
2797  // get max stack
2798  (*max_ptr) = method_oop->max_locals();
2799  return JVMTI_ERROR_NONE;
2800} /* end GetMaxLocals */
2801
2802
2803// method_oop - pre-checked for validity, but may be NULL meaning obsolete method
2804// size_ptr - pre-checked for NULL
2805jvmtiError
2806JvmtiEnv::GetArgumentsSize(Method* method_oop, jint* size_ptr) {
2807  NULL_CHECK(method_oop, JVMTI_ERROR_INVALID_METHODID);
2808  // get size of arguments
2809
2810  (*size_ptr) = method_oop->size_of_parameters();
2811  return JVMTI_ERROR_NONE;
2812} /* end GetArgumentsSize */
2813
2814
2815// method_oop - pre-checked for validity, but may be NULL meaning obsolete method
2816// entry_count_ptr - pre-checked for NULL
2817// table_ptr - pre-checked for NULL
2818jvmtiError
2819JvmtiEnv::GetLineNumberTable(Method* method_oop, jint* entry_count_ptr, jvmtiLineNumberEntry** table_ptr) {
2820  NULL_CHECK(method_oop, JVMTI_ERROR_INVALID_METHODID);
2821  if (!method_oop->has_linenumber_table()) {
2822    return (JVMTI_ERROR_ABSENT_INFORMATION);
2823  }
2824
2825  // The line number table is compressed so we don't know how big it is until decompressed.
2826  // Decompression is really fast so we just do it twice.
2827
2828  // Compute size of table
2829  jint num_entries = 0;
2830  CompressedLineNumberReadStream stream(method_oop->compressed_linenumber_table());
2831  while (stream.read_pair()) {
2832    num_entries++;
2833  }
2834  jvmtiLineNumberEntry *jvmti_table =
2835            (jvmtiLineNumberEntry *)jvmtiMalloc(num_entries * (sizeof(jvmtiLineNumberEntry)));
2836
2837  // Fill jvmti table
2838  if (num_entries > 0) {
2839    int index = 0;
2840    CompressedLineNumberReadStream stream(method_oop->compressed_linenumber_table());
2841    while (stream.read_pair()) {
2842      jvmti_table[index].start_location = (jlocation) stream.bci();
2843      jvmti_table[index].line_number = (jint) stream.line();
2844      index++;
2845    }
2846    assert(index == num_entries, "sanity check");
2847  }
2848
2849  // Set up results
2850  (*entry_count_ptr) = num_entries;
2851  (*table_ptr) = jvmti_table;
2852
2853  return JVMTI_ERROR_NONE;
2854} /* end GetLineNumberTable */
2855
2856
2857// method_oop - pre-checked for validity, but may be NULL meaning obsolete method
2858// start_location_ptr - pre-checked for NULL
2859// end_location_ptr - pre-checked for NULL
2860jvmtiError
2861JvmtiEnv::GetMethodLocation(Method* method_oop, jlocation* start_location_ptr, jlocation* end_location_ptr) {
2862
2863  NULL_CHECK(method_oop, JVMTI_ERROR_INVALID_METHODID);
2864  // get start and end location
2865  (*end_location_ptr) = (jlocation) (method_oop->code_size() - 1);
2866  if (method_oop->code_size() == 0) {
2867    // there is no code so there is no start location
2868    (*start_location_ptr) = (jlocation)(-1);
2869  } else {
2870    (*start_location_ptr) = (jlocation)(0);
2871  }
2872
2873  return JVMTI_ERROR_NONE;
2874} /* end GetMethodLocation */
2875
2876
2877// method_oop - pre-checked for validity, but may be NULL meaning obsolete method
2878// entry_count_ptr - pre-checked for NULL
2879// table_ptr - pre-checked for NULL
2880jvmtiError
2881JvmtiEnv::GetLocalVariableTable(Method* method_oop, jint* entry_count_ptr, jvmtiLocalVariableEntry** table_ptr) {
2882
2883  NULL_CHECK(method_oop, JVMTI_ERROR_INVALID_METHODID);
2884  JavaThread* current_thread  = JavaThread::current();
2885
2886  // does the klass have any local variable information?
2887  InstanceKlass* ik = method_oop->method_holder();
2888  if (!ik->access_flags().has_localvariable_table()) {
2889    return (JVMTI_ERROR_ABSENT_INFORMATION);
2890  }
2891
2892  ConstantPool* constants = method_oop->constants();
2893  NULL_CHECK(constants, JVMTI_ERROR_ABSENT_INFORMATION);
2894
2895  // in the vm localvariable table representation, 6 consecutive elements in the table
2896  // represent a 6-tuple of shorts
2897  // [start_pc, length, name_index, descriptor_index, signature_index, index]
2898  jint num_entries = method_oop->localvariable_table_length();
2899  jvmtiLocalVariableEntry *jvmti_table = (jvmtiLocalVariableEntry *)
2900                jvmtiMalloc(num_entries * (sizeof(jvmtiLocalVariableEntry)));
2901
2902  if (num_entries > 0) {
2903    LocalVariableTableElement* table = method_oop->localvariable_table_start();
2904    for (int i = 0; i < num_entries; i++) {
2905      // get the 5 tuple information from the vm table
2906      jlocation start_location = (jlocation) table[i].start_bci;
2907      jint length = (jint) table[i].length;
2908      int name_index = (int) table[i].name_cp_index;
2909      int signature_index = (int) table[i].descriptor_cp_index;
2910      int generic_signature_index = (int) table[i].signature_cp_index;
2911      jint slot = (jint) table[i].slot;
2912
2913      // get utf8 name and signature
2914      char *name_buf = NULL;
2915      char *sig_buf = NULL;
2916      char *gen_sig_buf = NULL;
2917      {
2918        ResourceMark rm(current_thread);
2919
2920        const char *utf8_name = (const char *) constants->symbol_at(name_index)->as_utf8();
2921        name_buf = (char *) jvmtiMalloc(strlen(utf8_name)+1);
2922        strcpy(name_buf, utf8_name);
2923
2924        const char *utf8_signature = (const char *) constants->symbol_at(signature_index)->as_utf8();
2925        sig_buf = (char *) jvmtiMalloc(strlen(utf8_signature)+1);
2926        strcpy(sig_buf, utf8_signature);
2927
2928        if (generic_signature_index > 0) {
2929          const char *utf8_gen_sign = (const char *)
2930                                       constants->symbol_at(generic_signature_index)->as_utf8();
2931          gen_sig_buf = (char *) jvmtiMalloc(strlen(utf8_gen_sign)+1);
2932          strcpy(gen_sig_buf, utf8_gen_sign);
2933        }
2934      }
2935
2936      // fill in the jvmti local variable table
2937      jvmti_table[i].start_location = start_location;
2938      jvmti_table[i].length = length;
2939      jvmti_table[i].name = name_buf;
2940      jvmti_table[i].signature = sig_buf;
2941      jvmti_table[i].generic_signature = gen_sig_buf;
2942      jvmti_table[i].slot = slot;
2943    }
2944  }
2945
2946  // set results
2947  (*entry_count_ptr) = num_entries;
2948  (*table_ptr) = jvmti_table;
2949
2950  return JVMTI_ERROR_NONE;
2951} /* end GetLocalVariableTable */
2952
2953
2954// method_oop - pre-checked for validity, but may be NULL meaning obsolete method
2955// bytecode_count_ptr - pre-checked for NULL
2956// bytecodes_ptr - pre-checked for NULL
2957jvmtiError
2958JvmtiEnv::GetBytecodes(Method* method_oop, jint* bytecode_count_ptr, unsigned char** bytecodes_ptr) {
2959  NULL_CHECK(method_oop, JVMTI_ERROR_INVALID_METHODID);
2960
2961  HandleMark hm;
2962  methodHandle method(method_oop);
2963  jint size = (jint)method->code_size();
2964  jvmtiError err = allocate(size, bytecodes_ptr);
2965  if (err != JVMTI_ERROR_NONE) {
2966    return err;
2967  }
2968
2969  (*bytecode_count_ptr) = size;
2970  // get byte codes
2971  JvmtiClassFileReconstituter::copy_bytecodes(method, *bytecodes_ptr);
2972
2973  return JVMTI_ERROR_NONE;
2974} /* end GetBytecodes */
2975
2976
2977// method_oop - pre-checked for validity, but may be NULL meaning obsolete method
2978// is_native_ptr - pre-checked for NULL
2979jvmtiError
2980JvmtiEnv::IsMethodNative(Method* method_oop, jboolean* is_native_ptr) {
2981  NULL_CHECK(method_oop, JVMTI_ERROR_INVALID_METHODID);
2982  (*is_native_ptr) = method_oop->is_native();
2983  return JVMTI_ERROR_NONE;
2984} /* end IsMethodNative */
2985
2986
2987// method_oop - pre-checked for validity, but may be NULL meaning obsolete method
2988// is_synthetic_ptr - pre-checked for NULL
2989jvmtiError
2990JvmtiEnv::IsMethodSynthetic(Method* method_oop, jboolean* is_synthetic_ptr) {
2991  NULL_CHECK(method_oop, JVMTI_ERROR_INVALID_METHODID);
2992  (*is_synthetic_ptr) = method_oop->is_synthetic();
2993  return JVMTI_ERROR_NONE;
2994} /* end IsMethodSynthetic */
2995
2996
2997// method_oop - pre-checked for validity, but may be NULL meaning obsolete method
2998// is_obsolete_ptr - pre-checked for NULL
2999jvmtiError
3000JvmtiEnv::IsMethodObsolete(Method* method_oop, jboolean* is_obsolete_ptr) {
3001  if (use_version_1_0_semantics() &&
3002      get_capabilities()->can_redefine_classes == 0) {
3003    // This JvmtiEnv requested version 1.0 semantics and this function
3004    // requires the can_redefine_classes capability in version 1.0 so
3005    // we need to return an error here.
3006    return JVMTI_ERROR_MUST_POSSESS_CAPABILITY;
3007  }
3008
3009  if (method_oop == NULL || method_oop->is_obsolete()) {
3010    *is_obsolete_ptr = true;
3011  } else {
3012    *is_obsolete_ptr = false;
3013  }
3014  return JVMTI_ERROR_NONE;
3015} /* end IsMethodObsolete */
3016
3017  //
3018  // Raw Monitor functions
3019  //
3020
3021// name - pre-checked for NULL
3022// monitor_ptr - pre-checked for NULL
3023jvmtiError
3024JvmtiEnv::CreateRawMonitor(const char* name, jrawMonitorID* monitor_ptr) {
3025  JvmtiRawMonitor* rmonitor = new JvmtiRawMonitor(name);
3026  NULL_CHECK(rmonitor, JVMTI_ERROR_OUT_OF_MEMORY);
3027
3028  *monitor_ptr = (jrawMonitorID)rmonitor;
3029
3030  return JVMTI_ERROR_NONE;
3031} /* end CreateRawMonitor */
3032
3033
3034// rmonitor - pre-checked for validity
3035jvmtiError
3036JvmtiEnv::DestroyRawMonitor(JvmtiRawMonitor * rmonitor) {
3037  if (Threads::number_of_threads() == 0) {
3038    // Remove this  monitor from pending raw monitors list
3039    // if it has entered in onload or start phase.
3040    JvmtiPendingMonitors::destroy(rmonitor);
3041  } else {
3042    Thread* thread  = Thread::current();
3043    if (rmonitor->is_entered(thread)) {
3044      // The caller owns this monitor which we are about to destroy.
3045      // We exit the underlying synchronization object so that the
3046      // "delete monitor" call below can work without an assertion
3047      // failure on systems that don't like destroying synchronization
3048      // objects that are locked.
3049      int r;
3050      intptr_t recursion = rmonitor->recursions();
3051      for (intptr_t i=0; i <= recursion; i++) {
3052        r = rmonitor->raw_exit(thread);
3053        assert(r == ObjectMonitor::OM_OK, "raw_exit should have worked");
3054        if (r != ObjectMonitor::OM_OK) {  // robustness
3055          return JVMTI_ERROR_INTERNAL;
3056        }
3057      }
3058    }
3059    if (rmonitor->owner() != NULL) {
3060      // The caller is trying to destroy a monitor that is locked by
3061      // someone else. While this is not forbidden by the JVMTI
3062      // spec, it will cause an assertion failure on systems that don't
3063      // like destroying synchronization objects that are locked.
3064      // We indicate a problem with the error return (and leak the
3065      // monitor's memory).
3066      return JVMTI_ERROR_NOT_MONITOR_OWNER;
3067    }
3068  }
3069
3070  delete rmonitor;
3071
3072  return JVMTI_ERROR_NONE;
3073} /* end DestroyRawMonitor */
3074
3075
3076// rmonitor - pre-checked for validity
3077jvmtiError
3078JvmtiEnv::RawMonitorEnter(JvmtiRawMonitor * rmonitor) {
3079  if (Threads::number_of_threads() == 0) {
3080    // No JavaThreads exist so ObjectMonitor enter cannot be
3081    // used, add this raw monitor to the pending list.
3082    // The pending monitors will be actually entered when
3083    // the VM is setup.
3084    // See transition_pending_raw_monitors in create_vm()
3085    // in thread.cpp.
3086    JvmtiPendingMonitors::enter(rmonitor);
3087  } else {
3088    int r = 0;
3089    Thread* thread = Thread::current();
3090
3091    if (thread->is_Java_thread()) {
3092      JavaThread* current_thread = (JavaThread*)thread;
3093
3094#ifdef PROPER_TRANSITIONS
3095      // Not really unknown but ThreadInVMfromNative does more than we want
3096      ThreadInVMfromUnknown __tiv;
3097      {
3098        ThreadBlockInVM __tbivm(current_thread);
3099        r = rmonitor->raw_enter(current_thread);
3100      }
3101#else
3102      /* Transition to thread_blocked without entering vm state          */
3103      /* This is really evil. Normally you can't undo _thread_blocked    */
3104      /* transitions like this because it would cause us to miss a       */
3105      /* safepoint but since the thread was already in _thread_in_native */
3106      /* the thread is not leaving a safepoint safe state and it will    */
3107      /* block when it tries to return from native. We can't safepoint   */
3108      /* block in here because we could deadlock the vmthread. Blech.    */
3109
3110      JavaThreadState state = current_thread->thread_state();
3111      assert(state == _thread_in_native, "Must be _thread_in_native");
3112      // frame should already be walkable since we are in native
3113      assert(!current_thread->has_last_Java_frame() ||
3114             current_thread->frame_anchor()->walkable(), "Must be walkable");
3115      current_thread->set_thread_state(_thread_blocked);
3116
3117      r = rmonitor->raw_enter(current_thread);
3118      // restore state, still at a safepoint safe state
3119      current_thread->set_thread_state(state);
3120
3121#endif /* PROPER_TRANSITIONS */
3122      assert(r == ObjectMonitor::OM_OK, "raw_enter should have worked");
3123    } else {
3124      if (thread->is_VM_thread() || thread->is_ConcurrentGC_thread()) {
3125        r = rmonitor->raw_enter(thread);
3126      } else {
3127        ShouldNotReachHere();
3128      }
3129    }
3130
3131    if (r != ObjectMonitor::OM_OK) {  // robustness
3132      return JVMTI_ERROR_INTERNAL;
3133    }
3134  }
3135  return JVMTI_ERROR_NONE;
3136} /* end RawMonitorEnter */
3137
3138
3139// rmonitor - pre-checked for validity
3140jvmtiError
3141JvmtiEnv::RawMonitorExit(JvmtiRawMonitor * rmonitor) {
3142  jvmtiError err = JVMTI_ERROR_NONE;
3143
3144  if (Threads::number_of_threads() == 0) {
3145    // No JavaThreads exist so just remove this monitor from the pending list.
3146    // Bool value from exit is false if rmonitor is not in the list.
3147    if (!JvmtiPendingMonitors::exit(rmonitor)) {
3148      err = JVMTI_ERROR_NOT_MONITOR_OWNER;
3149    }
3150  } else {
3151    int r = 0;
3152    Thread* thread = Thread::current();
3153
3154    if (thread->is_Java_thread()) {
3155      JavaThread* current_thread = (JavaThread*)thread;
3156#ifdef PROPER_TRANSITIONS
3157      // Not really unknown but ThreadInVMfromNative does more than we want
3158      ThreadInVMfromUnknown __tiv;
3159#endif /* PROPER_TRANSITIONS */
3160      r = rmonitor->raw_exit(current_thread);
3161    } else {
3162      if (thread->is_VM_thread() || thread->is_ConcurrentGC_thread()) {
3163        r = rmonitor->raw_exit(thread);
3164      } else {
3165        ShouldNotReachHere();
3166      }
3167    }
3168
3169    if (r == ObjectMonitor::OM_ILLEGAL_MONITOR_STATE) {
3170      err = JVMTI_ERROR_NOT_MONITOR_OWNER;
3171    } else {
3172      assert(r == ObjectMonitor::OM_OK, "raw_exit should have worked");
3173      if (r != ObjectMonitor::OM_OK) {  // robustness
3174        err = JVMTI_ERROR_INTERNAL;
3175      }
3176    }
3177  }
3178  return err;
3179} /* end RawMonitorExit */
3180
3181
3182// rmonitor - pre-checked for validity
3183jvmtiError
3184JvmtiEnv::RawMonitorWait(JvmtiRawMonitor * rmonitor, jlong millis) {
3185  int r = 0;
3186  Thread* thread = Thread::current();
3187
3188  if (thread->is_Java_thread()) {
3189    JavaThread* current_thread = (JavaThread*)thread;
3190#ifdef PROPER_TRANSITIONS
3191    // Not really unknown but ThreadInVMfromNative does more than we want
3192    ThreadInVMfromUnknown __tiv;
3193    {
3194      ThreadBlockInVM __tbivm(current_thread);
3195      r = rmonitor->raw_wait(millis, true, current_thread);
3196    }
3197#else
3198    /* Transition to thread_blocked without entering vm state          */
3199    /* This is really evil. Normally you can't undo _thread_blocked    */
3200    /* transitions like this because it would cause us to miss a       */
3201    /* safepoint but since the thread was already in _thread_in_native */
3202    /* the thread is not leaving a safepoint safe state and it will    */
3203    /* block when it tries to return from native. We can't safepoint   */
3204    /* block in here because we could deadlock the vmthread. Blech.    */
3205
3206    JavaThreadState state = current_thread->thread_state();
3207    assert(state == _thread_in_native, "Must be _thread_in_native");
3208    // frame should already be walkable since we are in native
3209    assert(!current_thread->has_last_Java_frame() ||
3210           current_thread->frame_anchor()->walkable(), "Must be walkable");
3211    current_thread->set_thread_state(_thread_blocked);
3212
3213    r = rmonitor->raw_wait(millis, true, current_thread);
3214    // restore state, still at a safepoint safe state
3215    current_thread->set_thread_state(state);
3216
3217#endif /* PROPER_TRANSITIONS */
3218  } else {
3219    if (thread->is_VM_thread() || thread->is_ConcurrentGC_thread()) {
3220      r = rmonitor->raw_wait(millis, true, thread);
3221    } else {
3222      ShouldNotReachHere();
3223    }
3224  }
3225
3226  switch (r) {
3227  case ObjectMonitor::OM_INTERRUPTED:
3228    return JVMTI_ERROR_INTERRUPT;
3229  case ObjectMonitor::OM_ILLEGAL_MONITOR_STATE:
3230    return JVMTI_ERROR_NOT_MONITOR_OWNER;
3231  }
3232  assert(r == ObjectMonitor::OM_OK, "raw_wait should have worked");
3233  if (r != ObjectMonitor::OM_OK) {  // robustness
3234    return JVMTI_ERROR_INTERNAL;
3235  }
3236
3237  return JVMTI_ERROR_NONE;
3238} /* end RawMonitorWait */
3239
3240
3241// rmonitor - pre-checked for validity
3242jvmtiError
3243JvmtiEnv::RawMonitorNotify(JvmtiRawMonitor * rmonitor) {
3244  int r = 0;
3245  Thread* thread = Thread::current();
3246
3247  if (thread->is_Java_thread()) {
3248    JavaThread* current_thread = (JavaThread*)thread;
3249    // Not really unknown but ThreadInVMfromNative does more than we want
3250    ThreadInVMfromUnknown __tiv;
3251    r = rmonitor->raw_notify(current_thread);
3252  } else {
3253    if (thread->is_VM_thread() || thread->is_ConcurrentGC_thread()) {
3254      r = rmonitor->raw_notify(thread);
3255    } else {
3256      ShouldNotReachHere();
3257    }
3258  }
3259
3260  if (r == ObjectMonitor::OM_ILLEGAL_MONITOR_STATE) {
3261    return JVMTI_ERROR_NOT_MONITOR_OWNER;
3262  }
3263  assert(r == ObjectMonitor::OM_OK, "raw_notify should have worked");
3264  if (r != ObjectMonitor::OM_OK) {  // robustness
3265    return JVMTI_ERROR_INTERNAL;
3266  }
3267
3268  return JVMTI_ERROR_NONE;
3269} /* end RawMonitorNotify */
3270
3271
3272// rmonitor - pre-checked for validity
3273jvmtiError
3274JvmtiEnv::RawMonitorNotifyAll(JvmtiRawMonitor * rmonitor) {
3275  int r = 0;
3276  Thread* thread = Thread::current();
3277
3278  if (thread->is_Java_thread()) {
3279    JavaThread* current_thread = (JavaThread*)thread;
3280    ThreadInVMfromUnknown __tiv;
3281    r = rmonitor->raw_notifyAll(current_thread);
3282  } else {
3283    if (thread->is_VM_thread() || thread->is_ConcurrentGC_thread()) {
3284      r = rmonitor->raw_notifyAll(thread);
3285    } else {
3286      ShouldNotReachHere();
3287    }
3288  }
3289
3290  if (r == ObjectMonitor::OM_ILLEGAL_MONITOR_STATE) {
3291    return JVMTI_ERROR_NOT_MONITOR_OWNER;
3292  }
3293  assert(r == ObjectMonitor::OM_OK, "raw_notifyAll should have worked");
3294  if (r != ObjectMonitor::OM_OK) {  // robustness
3295    return JVMTI_ERROR_INTERNAL;
3296  }
3297
3298  return JVMTI_ERROR_NONE;
3299} /* end RawMonitorNotifyAll */
3300
3301
3302  //
3303  // JNI Function Interception functions
3304  //
3305
3306
3307// function_table - pre-checked for NULL
3308jvmtiError
3309JvmtiEnv::SetJNIFunctionTable(const jniNativeInterface* function_table) {
3310  // Copy jni function table at safepoint.
3311  VM_JNIFunctionTableCopier copier(function_table);
3312  VMThread::execute(&copier);
3313
3314  return JVMTI_ERROR_NONE;
3315} /* end SetJNIFunctionTable */
3316
3317
3318// function_table - pre-checked for NULL
3319jvmtiError
3320JvmtiEnv::GetJNIFunctionTable(jniNativeInterface** function_table) {
3321  *function_table=(jniNativeInterface*)jvmtiMalloc(sizeof(jniNativeInterface));
3322  if (*function_table == NULL)
3323    return JVMTI_ERROR_OUT_OF_MEMORY;
3324  memcpy(*function_table,(JavaThread::current())->get_jni_functions(),sizeof(jniNativeInterface));
3325  return JVMTI_ERROR_NONE;
3326} /* end GetJNIFunctionTable */
3327
3328
3329  //
3330  // Event Management functions
3331  //
3332
3333jvmtiError
3334JvmtiEnv::GenerateEvents(jvmtiEvent event_type) {
3335  // can only generate two event types
3336  if (event_type != JVMTI_EVENT_COMPILED_METHOD_LOAD &&
3337      event_type != JVMTI_EVENT_DYNAMIC_CODE_GENERATED) {
3338    return JVMTI_ERROR_ILLEGAL_ARGUMENT;
3339  }
3340
3341  // for compiled_method_load events we must check that the environment
3342  // has the can_generate_compiled_method_load_events capability.
3343  if (event_type == JVMTI_EVENT_COMPILED_METHOD_LOAD) {
3344    if (get_capabilities()->can_generate_compiled_method_load_events == 0) {
3345      return JVMTI_ERROR_MUST_POSSESS_CAPABILITY;
3346    }
3347    return JvmtiCodeBlobEvents::generate_compiled_method_load_events(this);
3348  } else {
3349    return JvmtiCodeBlobEvents::generate_dynamic_code_events(this);
3350  }
3351
3352} /* end GenerateEvents */
3353
3354
3355  //
3356  // Extension Mechanism functions
3357  //
3358
3359// extension_count_ptr - pre-checked for NULL
3360// extensions - pre-checked for NULL
3361jvmtiError
3362JvmtiEnv::GetExtensionFunctions(jint* extension_count_ptr, jvmtiExtensionFunctionInfo** extensions) {
3363  return JvmtiExtensions::get_functions(this, extension_count_ptr, extensions);
3364} /* end GetExtensionFunctions */
3365
3366
3367// extension_count_ptr - pre-checked for NULL
3368// extensions - pre-checked for NULL
3369jvmtiError
3370JvmtiEnv::GetExtensionEvents(jint* extension_count_ptr, jvmtiExtensionEventInfo** extensions) {
3371  return JvmtiExtensions::get_events(this, extension_count_ptr, extensions);
3372} /* end GetExtensionEvents */
3373
3374
3375// callback - NULL is a valid value, must be checked
3376jvmtiError
3377JvmtiEnv::SetExtensionEventCallback(jint extension_event_index, jvmtiExtensionEvent callback) {
3378  return JvmtiExtensions::set_event_callback(this, extension_event_index, callback);
3379} /* end SetExtensionEventCallback */
3380
3381  //
3382  // Timers functions
3383  //
3384
3385// info_ptr - pre-checked for NULL
3386jvmtiError
3387JvmtiEnv::GetCurrentThreadCpuTimerInfo(jvmtiTimerInfo* info_ptr) {
3388  os::current_thread_cpu_time_info(info_ptr);
3389  return JVMTI_ERROR_NONE;
3390} /* end GetCurrentThreadCpuTimerInfo */
3391
3392
3393// nanos_ptr - pre-checked for NULL
3394jvmtiError
3395JvmtiEnv::GetCurrentThreadCpuTime(jlong* nanos_ptr) {
3396  *nanos_ptr = os::current_thread_cpu_time();
3397  return JVMTI_ERROR_NONE;
3398} /* end GetCurrentThreadCpuTime */
3399
3400
3401// info_ptr - pre-checked for NULL
3402jvmtiError
3403JvmtiEnv::GetThreadCpuTimerInfo(jvmtiTimerInfo* info_ptr) {
3404  os::thread_cpu_time_info(info_ptr);
3405  return JVMTI_ERROR_NONE;
3406} /* end GetThreadCpuTimerInfo */
3407
3408
3409// Threads_lock NOT held, java_thread not protected by lock
3410// java_thread - pre-checked
3411// nanos_ptr - pre-checked for NULL
3412jvmtiError
3413JvmtiEnv::GetThreadCpuTime(JavaThread* java_thread, jlong* nanos_ptr) {
3414  *nanos_ptr = os::thread_cpu_time(java_thread);
3415  return JVMTI_ERROR_NONE;
3416} /* end GetThreadCpuTime */
3417
3418
3419// info_ptr - pre-checked for NULL
3420jvmtiError
3421JvmtiEnv::GetTimerInfo(jvmtiTimerInfo* info_ptr) {
3422  os::javaTimeNanos_info(info_ptr);
3423  return JVMTI_ERROR_NONE;
3424} /* end GetTimerInfo */
3425
3426
3427// nanos_ptr - pre-checked for NULL
3428jvmtiError
3429JvmtiEnv::GetTime(jlong* nanos_ptr) {
3430  *nanos_ptr = os::javaTimeNanos();
3431  return JVMTI_ERROR_NONE;
3432} /* end GetTime */
3433
3434
3435// processor_count_ptr - pre-checked for NULL
3436jvmtiError
3437JvmtiEnv::GetAvailableProcessors(jint* processor_count_ptr) {
3438  *processor_count_ptr = os::active_processor_count();
3439  return JVMTI_ERROR_NONE;
3440} /* end GetAvailableProcessors */
3441
3442  //
3443  // System Properties functions
3444  //
3445
3446// count_ptr - pre-checked for NULL
3447// property_ptr - pre-checked for NULL
3448jvmtiError
3449JvmtiEnv::GetSystemProperties(jint* count_ptr, char*** property_ptr) {
3450  jvmtiError err = JVMTI_ERROR_NONE;
3451
3452  *count_ptr = Arguments::PropertyList_count(Arguments::system_properties());
3453
3454  err = allocate(*count_ptr * sizeof(char *), (unsigned char **)property_ptr);
3455  if (err != JVMTI_ERROR_NONE) {
3456    return err;
3457  }
3458  int i = 0 ;
3459  for (SystemProperty* p = Arguments::system_properties(); p != NULL && i < *count_ptr; p = p->next(), i++) {
3460    const char *key = p->key();
3461    char **tmp_value = *property_ptr+i;
3462    err = allocate((strlen(key)+1) * sizeof(char), (unsigned char**)tmp_value);
3463    if (err == JVMTI_ERROR_NONE) {
3464      strcpy(*tmp_value, key);
3465    } else {
3466      // clean up previously allocated memory.
3467      for (int j=0; j<i; j++) {
3468        Deallocate((unsigned char*)*property_ptr+j);
3469      }
3470      Deallocate((unsigned char*)property_ptr);
3471      break;
3472    }
3473  }
3474  return err;
3475} /* end GetSystemProperties */
3476
3477
3478// property - pre-checked for NULL
3479// value_ptr - pre-checked for NULL
3480jvmtiError
3481JvmtiEnv::GetSystemProperty(const char* property, char** value_ptr) {
3482  jvmtiError err = JVMTI_ERROR_NONE;
3483  const char *value;
3484
3485  value = Arguments::PropertyList_get_value(Arguments::system_properties(), property);
3486  if (value == NULL) {
3487    err =  JVMTI_ERROR_NOT_AVAILABLE;
3488  } else {
3489    err = allocate((strlen(value)+1) * sizeof(char), (unsigned char **)value_ptr);
3490    if (err == JVMTI_ERROR_NONE) {
3491      strcpy(*value_ptr, value);
3492    }
3493  }
3494  return err;
3495} /* end GetSystemProperty */
3496
3497
3498// property - pre-checked for NULL
3499// value - NULL is a valid value, must be checked
3500jvmtiError
3501JvmtiEnv::SetSystemProperty(const char* property, const char* value_ptr) {
3502  jvmtiError err =JVMTI_ERROR_NOT_AVAILABLE;
3503
3504  for (SystemProperty* p = Arguments::system_properties(); p != NULL; p = p->next()) {
3505    if (strcmp(property, p->key()) == 0) {
3506      if (p->set_writeable_value(value_ptr)) {
3507        err =  JVMTI_ERROR_NONE;
3508      }
3509    }
3510  }
3511  return err;
3512} /* end SetSystemProperty */
3513