]> gcc.gnu.org Git - gcc.git/blob - libjava/jvmti.cc
jvmti.cc (_Jv_JVMTI_GetErrorName): Now static.
[gcc.git] / libjava / jvmti.cc
1 // jvmti.cc - JVMTI implementation
2
3 /* Copyright (C) 2006 Free Software Foundation
4
5 This file is part of libgcj.
6
7 This software is copyrighted work licensed under the terms of the
8 Libgcj License. Please consult the file "LIBGCJ_LICENSE" for
9 details. */
10
11 #include <config.h>
12 #include <platform.h>
13
14 #include <jvm.h>
15 #include <java-threads.h>
16 #include <java-gc.h>
17 #include <jvmti.h>
18 #include "jvmti-int.h"
19
20 #include <gcj/method.h>
21
22 #include <gnu/classpath/SystemProperties.h>
23 #include <gnu/gcj/runtime/BootClassLoader.h>
24 #include <java/lang/Class.h>
25 #include <java/lang/ClassLoader.h>
26 #include <java/lang/Object.h>
27 #include <java/lang/Thread.h>
28 #include <java/lang/Throwable.h>
29 #include <java/lang/VMClassLoader.h>
30 #include <java/lang/reflect/Field.h>
31 #include <java/lang/reflect/Modifier.h>
32 #include <java/util/Collection.h>
33 #include <java/util/HashMap.h>
34 #include <java/net/URL.h>
35
36 static void check_enabled_events (void);
37 static void check_enabled_event (jvmtiEvent);
38
39 extern struct JNINativeInterface _Jv_JNIFunctions;
40
41 struct _Jv_rawMonitorID
42 {
43 _Jv_Mutex_t mutex;
44 _Jv_ConditionVariable_t condition;
45 };
46
47 /* A simple linked list of all JVMTI environments. Since
48 events must be delivered to environments in the order
49 in which the environments were created, new environments
50 are added to the end of the list. */
51 struct jvmti_env_list
52 {
53 jvmtiEnv *env;
54 struct jvmti_env_list *next;
55 };
56 static struct jvmti_env_list *_jvmtiEnvironments = NULL;
57 static java::lang::Object *_envListLock = NULL;
58 #define FOREACH_ENVIRONMENT(Ele) \
59 for (Ele = _jvmtiEnvironments; Ele != NULL; Ele = Ele->next)
60
61 // Some commonly-used checks
62
63 #define THREAD_DEFAULT_TO_CURRENT(Ajthread) \
64 do \
65 { \
66 if (Ajthread == NULL) \
67 Ajthread = java::lang::Thread::currentThread (); \
68 } \
69 while (0)
70
71 #define THREAD_CHECK_VALID(Athread) \
72 do \
73 { \
74 if (!java::lang::Thread::class$.isAssignableFrom (&(Athread->class$))) \
75 return JVMTI_ERROR_INVALID_THREAD; \
76 } \
77 while (0)
78
79 #define THREAD_CHECK_IS_ALIVE(Athread) \
80 do \
81 { \
82 if (!Athread->isAlive ()) \
83 return JVMTI_ERROR_THREAD_NOT_ALIVE; \
84 } \
85 while (0)
86
87 // FIXME: if current phase is not set in Phases,
88 // return JVMTI_ERROR_WRONG_PHASE
89 #define REQUIRE_PHASE(Env, Phases)
90
91 #define NULL_CHECK(Ptr) \
92 do \
93 { \
94 if (Ptr == NULL) \
95 return JVMTI_ERROR_NULL_POINTER; \
96 } \
97 while (0)
98
99 #define ILLEGAL_ARGUMENT(Cond) \
100 do \
101 { \
102 if ((Cond)) \
103 return JVMTI_ERROR_ILLEGAL_ARGUMENT; \
104 } \
105 while (0)
106
107 static jvmtiError JNICALL
108 _Jv_JVMTI_SuspendThread (MAYBE_UNUSED jvmtiEnv *env, jthread thread)
109 {
110 using namespace java::lang;
111
112 THREAD_DEFAULT_TO_CURRENT (thread);
113
114 Thread *t = reinterpret_cast<Thread *> (thread);
115 THREAD_CHECK_VALID (t);
116 THREAD_CHECK_IS_ALIVE (t);
117
118 _Jv_Thread_t *data = _Jv_ThreadGetData (t);
119 _Jv_SuspendThread (data);
120 return JVMTI_ERROR_NONE;
121 }
122
123 static jvmtiError JNICALL
124 _Jv_JVMTI_ResumeThread (MAYBE_UNUSED jvmtiEnv *env, jthread thread)
125 {
126 using namespace java::lang;
127
128 THREAD_DEFAULT_TO_CURRENT (thread);
129
130 Thread *t = reinterpret_cast<Thread *> (thread);
131 THREAD_CHECK_VALID (t);
132 THREAD_CHECK_IS_ALIVE (t);
133
134 _Jv_Thread_t *data = _Jv_ThreadGetData (t);
135 _Jv_ResumeThread (data);
136 return JVMTI_ERROR_NONE;
137 }
138
139 static jvmtiError JNICALL
140 _Jv_JVMTI_InterruptThread (MAYBE_UNUSED jvmtiEnv *env, jthread thread)
141 {
142 using namespace java::lang;
143
144 REQUIRE_PHASE (env, JVMTI_PHASE_LIVE);
145 // FIXME: capability handling? 'can_signal_thread'
146 if (thread == NULL)
147 return JVMTI_ERROR_INVALID_THREAD;
148
149 Thread *real_thread = reinterpret_cast<Thread *> (thread);
150 THREAD_CHECK_VALID (real_thread);
151 THREAD_CHECK_IS_ALIVE (real_thread);
152 real_thread->interrupt();
153 return JVMTI_ERROR_NONE;
154 }
155
156 static jvmtiError JNICALL
157 _Jv_JVMTI_CreateRawMonitor (MAYBE_UNUSED jvmtiEnv *env, const char *name,
158 jrawMonitorID *result)
159 {
160 REQUIRE_PHASE (env, JVMTI_PHASE_ONLOAD | JVMTI_PHASE_LIVE);
161 NULL_CHECK (name);
162 NULL_CHECK (result);
163 *result = (jrawMonitorID) _Jv_MallocUnchecked (sizeof (_Jv_rawMonitorID));
164 if (*result == NULL)
165 return JVMTI_ERROR_OUT_OF_MEMORY;
166 _Jv_MutexInit (&(*result)->mutex);
167 _Jv_CondInit (&(*result)->condition);
168 return JVMTI_ERROR_NONE;
169 }
170
171 static jvmtiError JNICALL
172 _Jv_JVMTI_DestroyRawMonitor (MAYBE_UNUSED jvmtiEnv *env, jrawMonitorID monitor)
173 {
174 REQUIRE_PHASE (env, JVMTI_PHASE_ONLOAD | JVMTI_PHASE_LIVE);
175 // Note we have no better way of knowing whether this object is
176 // really a raw monitor.
177 if (monitor == NULL)
178 return JVMTI_ERROR_INVALID_MONITOR;
179 // FIXME: perform checks on monitor, release it if this thread owns
180 // it.
181 #ifdef _Jv_HaveMutexDestroy
182 _Jv_MutexDestroy (&monitor->mutex);
183 #endif
184 _Jv_Free (monitor);
185 return JVMTI_ERROR_NONE;
186 }
187
188 static jvmtiError JNICALL
189 _Jv_JVMTI_RawMonitorEnter (MAYBE_UNUSED jvmtiEnv *env, jrawMonitorID monitor)
190 {
191 if (monitor == NULL)
192 return JVMTI_ERROR_INVALID_MONITOR;
193 _Jv_MutexLock (&monitor->mutex);
194 return JVMTI_ERROR_NONE;
195 }
196
197 static jvmtiError JNICALL
198 _Jv_JVMTI_RawMonitorExit (MAYBE_UNUSED jvmtiEnv *env, jrawMonitorID monitor)
199 {
200 if (monitor == NULL)
201 return JVMTI_ERROR_INVALID_MONITOR;
202 if (_Jv_MutexUnlock (&monitor->mutex))
203 return JVMTI_ERROR_NOT_MONITOR_OWNER;
204 return JVMTI_ERROR_NONE;
205 }
206
207 static jvmtiError JNICALL
208 _Jv_JVMTI_RawMonitorWait (MAYBE_UNUSED jvmtiEnv *env, jrawMonitorID monitor,
209 jlong millis)
210 {
211 if (monitor == NULL)
212 return JVMTI_ERROR_INVALID_MONITOR;
213 int r = _Jv_CondWait (&monitor->condition, &monitor->mutex, millis, 0);
214 if (r == _JV_NOT_OWNER)
215 return JVMTI_ERROR_NOT_MONITOR_OWNER;
216 if (r == _JV_INTERRUPTED)
217 return JVMTI_ERROR_INTERRUPT;
218 return JVMTI_ERROR_NONE;
219 }
220
221 static jvmtiError JNICALL
222 _Jv_JVMTI_RawMonitorNotify (MAYBE_UNUSED jvmtiEnv *env, jrawMonitorID monitor)
223 {
224 if (monitor == NULL)
225 return JVMTI_ERROR_INVALID_MONITOR;
226 if (_Jv_CondNotify (&monitor->condition, &monitor->mutex) == _JV_NOT_OWNER)
227 return JVMTI_ERROR_NOT_MONITOR_OWNER;
228 return JVMTI_ERROR_NONE;
229 }
230
231 static jvmtiError JNICALL
232 _Jv_JVMTI_RawMonitorNotifyAll (MAYBE_UNUSED jvmtiEnv *env,
233 jrawMonitorID monitor)
234 {
235 if (monitor == NULL)
236 return JVMTI_ERROR_INVALID_MONITOR;
237 if (_Jv_CondNotifyAll (&monitor->condition, &monitor->mutex)
238 == _JV_NOT_OWNER)
239 return JVMTI_ERROR_NOT_MONITOR_OWNER;
240 return JVMTI_ERROR_NONE;
241 }
242
243 static jvmtiError JNICALL
244 _Jv_JVMTI_Allocate (MAYBE_UNUSED jvmtiEnv *env, jlong size,
245 unsigned char **result)
246 {
247 ILLEGAL_ARGUMENT (size < 0);
248 NULL_CHECK (result);
249 if (size == 0)
250 *result = NULL;
251 else
252 {
253 *result = (unsigned char *) _Jv_MallocUnchecked (size);
254 if (*result == NULL)
255 return JVMTI_ERROR_OUT_OF_MEMORY;
256 }
257 return JVMTI_ERROR_NONE;
258 }
259
260 static jvmtiError JNICALL
261 _Jv_JVMTI_Deallocate (MAYBE_UNUSED jvmtiEnv *env, unsigned char *mem)
262 {
263 if (mem != NULL)
264 _Jv_Free (mem);
265 return JVMTI_ERROR_NONE;
266 }
267
268 static jvmtiError JNICALL
269 _Jv_JVMTI_GetClassModifiers (MAYBE_UNUSED jvmtiEnv *env, jclass klass,
270 jint *mods)
271 {
272 REQUIRE_PHASE (env, JVMTI_PHASE_START | JVMTI_PHASE_LIVE);
273 // Don't bother checking KLASS' type.
274 if (klass == NULL)
275 return JVMTI_ERROR_INVALID_CLASS;
276 NULL_CHECK (mods);
277 *mods = klass->getModifiers();
278 return JVMTI_ERROR_NONE;
279 }
280
281 static jvmtiError JNICALL
282 _Jv_JVMTI_GetClassMethods (MAYBE_UNUSED jvmtiEnv *env, jclass klass,
283 jint *count_ptr, jmethodID **methods_ptr)
284 {
285 REQUIRE_PHASE (env, JVMTI_PHASE_START | JVMTI_PHASE_LIVE);
286 // FIXME: capability can_maintain_original_method_order
287 // Don't bother checking KLASS' type.
288 if (klass == NULL)
289 return JVMTI_ERROR_INVALID_CLASS;
290 NULL_CHECK (count_ptr);
291 NULL_CHECK (methods_ptr);
292 *count_ptr = JvNumMethods(klass);
293
294 *methods_ptr
295 = (jmethodID *) _Jv_MallocUnchecked (*count_ptr * sizeof (jmethodID));
296 if (*methods_ptr == NULL)
297 return JVMTI_ERROR_OUT_OF_MEMORY;
298
299 jmethodID start = JvGetFirstMethod (klass);
300 for (jint i = 0; i < *count_ptr; ++i)
301 // FIXME: correct?
302 (*methods_ptr)[i] = start + i;
303
304 return JVMTI_ERROR_NONE;
305 }
306
307 static jvmtiError JNICALL
308 _Jv_JVMTI_IsInterface (MAYBE_UNUSED jvmtiEnv *env, jclass klass,
309 jboolean *result)
310 {
311 REQUIRE_PHASE (env, JVMTI_PHASE_START | JVMTI_PHASE_LIVE);
312 if (klass == NULL)
313 return JVMTI_ERROR_INVALID_CLASS;
314 NULL_CHECK (result);
315 *result = klass->isInterface();
316 return JVMTI_ERROR_NONE;
317 }
318
319 static jvmtiError JNICALL
320 _Jv_JVMTI_IsArrayClass (MAYBE_UNUSED jvmtiEnv *env, jclass klass,
321 jboolean *result)
322 {
323 REQUIRE_PHASE (env, JVMTI_PHASE_START | JVMTI_PHASE_LIVE);
324 if (klass == NULL)
325 return JVMTI_ERROR_INVALID_CLASS;
326 NULL_CHECK (result);
327 *result = klass->isArray();
328 return JVMTI_ERROR_NONE;
329 }
330
331 static jvmtiError JNICALL
332 _Jv_JVMTI_GetClassLoader (MAYBE_UNUSED jvmtiEnv *env, jclass klass,
333 jobject *result)
334 {
335 REQUIRE_PHASE (env, JVMTI_PHASE_START | JVMTI_PHASE_LIVE);
336 if (klass == NULL)
337 return JVMTI_ERROR_INVALID_CLASS;
338 NULL_CHECK (result);
339 *result = klass->getClassLoaderInternal();
340 return JVMTI_ERROR_NONE;
341 }
342
343 static jvmtiError JNICALL
344 _Jv_JVMTI_GetObjectHashCode (MAYBE_UNUSED jvmtiEnv *env, jobject obj,
345 jint *result)
346 {
347 REQUIRE_PHASE (env, JVMTI_PHASE_START | JVMTI_PHASE_LIVE);
348 if (obj == NULL)
349 return JVMTI_ERROR_INVALID_OBJECT;
350 NULL_CHECK (result);
351 *result = _Jv_HashCode (obj);
352 return JVMTI_ERROR_NONE;
353 }
354
355 static jvmtiError JNICALL
356 _Jv_JVMTI_GetFieldModifiers (MAYBE_UNUSED jvmtiEnv *env, jclass klass,
357 jfieldID field, jint *result)
358 {
359 REQUIRE_PHASE (env, JVMTI_PHASE_START | JVMTI_PHASE_LIVE);
360 if (klass == NULL)
361 return JVMTI_ERROR_INVALID_CLASS;
362 if (field == NULL)
363 return JVMTI_ERROR_INVALID_FIELDID;
364 NULL_CHECK (result);
365 *result = field->getModifiers();
366 return JVMTI_ERROR_NONE;
367 }
368
369 static jvmtiError JNICALL
370 _Jv_JVMTI_IsFieldSynthetic (MAYBE_UNUSED jvmtiEnv *env, jclass klass,
371 jfieldID field, jboolean *result)
372 {
373 REQUIRE_PHASE (env, JVMTI_PHASE_START | JVMTI_PHASE_LIVE);
374 if (klass == NULL)
375 return JVMTI_ERROR_INVALID_CLASS;
376 if (field == NULL)
377 return JVMTI_ERROR_INVALID_FIELDID;
378 NULL_CHECK (result);
379
380 // FIXME: capability can_get_synthetic_attribute
381 *result = ((field->getModifiers() & java::lang::reflect::Modifier::SYNTHETIC)
382 != 0);
383 return JVMTI_ERROR_NONE;
384 }
385
386 static jvmtiError JNICALL
387 _Jv_JVMTI_GetMethodModifiers (MAYBE_UNUSED jvmtiEnv *env, jmethodID method,
388 jint *result)
389 {
390 REQUIRE_PHASE (env, JVMTI_PHASE_START | JVMTI_PHASE_LIVE);
391 if (method == NULL)
392 return JVMTI_ERROR_INVALID_METHODID;
393 NULL_CHECK (result);
394
395 // FIXME: mask off some internal bits...
396 *result = method->accflags;
397 return JVMTI_ERROR_NONE;
398 }
399
400 static jvmtiError JNICALL
401 _Jv_JVMTI_IsMethodNative (MAYBE_UNUSED jvmtiEnv *env, jmethodID method,
402 jboolean *result)
403 {
404 REQUIRE_PHASE (env, JVMTI_PHASE_START | JVMTI_PHASE_LIVE);
405 if (method == NULL)
406 return JVMTI_ERROR_INVALID_METHODID;
407 NULL_CHECK (result);
408
409 *result = ((method->accflags & java::lang::reflect::Modifier::NATIVE) != 0);
410 return JVMTI_ERROR_NONE;
411 }
412
413 static jvmtiError JNICALL
414 _Jv_JVMTI_IsMethodSynthetic (MAYBE_UNUSED jvmtiEnv *env, jmethodID method,
415 jboolean *result)
416 {
417 REQUIRE_PHASE (env, JVMTI_PHASE_START | JVMTI_PHASE_LIVE);
418 if (method == NULL)
419 return JVMTI_ERROR_INVALID_METHODID;
420 NULL_CHECK (result);
421
422 // FIXME capability can_get_synthetic_attribute
423
424 *result = ((method->accflags & java::lang::reflect::Modifier::SYNTHETIC)
425 != 0);
426 return JVMTI_ERROR_NONE;
427 }
428
429 static jvmtiError JNICALL
430 _Jv_JVMTI_GetClassLoaderClasses (MAYBE_UNUSED jvmtiEnv *env,
431 jobject init_loader,
432 jint *count_ptr,
433 jclass **result_ptr)
434 {
435 using namespace java::lang;
436 using namespace java::util;
437
438 REQUIRE_PHASE (env, JVMTI_PHASE_LIVE);
439 NULL_CHECK (count_ptr);
440 NULL_CHECK (result_ptr);
441
442 ClassLoader *loader = (ClassLoader *) init_loader;
443 if (loader == NULL)
444 loader = VMClassLoader::bootLoader;
445
446 Collection *values = loader->loadedClasses->values();
447 jobjectArray array = values->toArray();
448 *count_ptr = array->length;
449 jobject *elts = elements (array);
450 jclass *result
451 = (jclass *) _Jv_MallocUnchecked (*count_ptr * sizeof (jclass));
452 if (result == NULL)
453 return JVMTI_ERROR_OUT_OF_MEMORY;
454
455 // FIXME: JNI references...
456 memcpy (result, elts, *count_ptr * sizeof (jclass));
457
458 *result_ptr = result;
459
460 return JVMTI_ERROR_NONE;
461 }
462
463 static jvmtiError JNICALL
464 _Jv_JVMTI_ForceGarbageCollection (MAYBE_UNUSED jvmtiEnv *env)
465 {
466 REQUIRE_PHASE (env, JVMTI_PHASE_LIVE);
467 _Jv_RunGC();
468 return JVMTI_ERROR_NONE;
469 }
470
471 static jvmtiError JNICALL
472 _Jv_JVMTI_SetJNIFunctionTable (MAYBE_UNUSED jvmtiEnv *env,
473 const jniNativeInterface *function_table)
474 {
475 REQUIRE_PHASE (env, JVMTI_PHASE_START | JVMTI_PHASE_LIVE);
476 NULL_CHECK (function_table);
477 memcpy (&_Jv_JNIFunctions, function_table, sizeof (jniNativeInterface));
478 return JVMTI_ERROR_NONE;
479 }
480
481 static jvmtiError JNICALL
482 _Jv_JVMTI_GetJNIFunctionTable (MAYBE_UNUSED jvmtiEnv *env,
483 jniNativeInterface **function_table)
484 {
485 REQUIRE_PHASE (env, JVMTI_PHASE_START | JVMTI_PHASE_LIVE);
486 NULL_CHECK (function_table);
487 *function_table
488 = (jniNativeInterface *) _Jv_MallocUnchecked (sizeof (jniNativeInterface));
489 if (*function_table == NULL)
490 return JVMTI_ERROR_OUT_OF_MEMORY;
491 memcpy (*function_table, &_Jv_JNIFunctions, sizeof (jniNativeInterface));
492 return JVMTI_ERROR_NONE;
493 }
494
495 static jvmtiError JNICALL
496 _Jv_JVMTI_DisposeEnvironment (jvmtiEnv *env)
497 {
498 NULL_CHECK (env);
499
500 if (_jvmtiEnvironments == NULL)
501 return JVMTI_ERROR_INVALID_ENVIRONMENT;
502 else
503 {
504 JvSynchronize dummy (_envListLock);
505 if (_jvmtiEnvironments->env == env)
506 {
507 struct jvmti_env_list *next = _jvmtiEnvironments->next;
508 _Jv_Free (_jvmtiEnvironments);
509 _jvmtiEnvironments = next;
510 }
511 else
512 {
513 struct jvmti_env_list *e = _jvmtiEnvironments;
514 while (e->next != NULL && e->next->env != env)
515 e = e->next;
516 if (e->next == NULL)
517 return JVMTI_ERROR_INVALID_ENVIRONMENT;
518
519 struct jvmti_env_list *next = e->next->next;
520 _Jv_Free (e->next);
521 e->next = next;
522 }
523 }
524
525 _Jv_Free (env);
526
527 check_enabled_events ();
528
529 return JVMTI_ERROR_NONE;
530 }
531
532 static jvmtiError JNICALL
533 _Jv_JVMTI_GetSystemProperty (MAYBE_UNUSED jvmtiEnv *env, const char *property,
534 char **result)
535 {
536 REQUIRE_PHASE (env, JVMTI_PHASE_ONLOAD | JVMTI_PHASE_LIVE);
537 NULL_CHECK (property);
538 NULL_CHECK (result);
539
540 jstring name = JvNewStringUTF(property);
541 jstring result_str = gnu::classpath::SystemProperties::getProperty(name);
542
543 if (result_str == NULL)
544 return JVMTI_ERROR_NOT_AVAILABLE;
545
546 int len = JvGetStringUTFLength (result_str);
547 *result = (char *) _Jv_MallocUnchecked (len + 1);
548 if (*result == NULL)
549 return JVMTI_ERROR_OUT_OF_MEMORY;
550 JvGetStringUTFRegion (result_str, 0, result_str->length(), *result);
551 (*result)[len] = '\0';
552
553 return JVMTI_ERROR_NONE;
554 }
555
556 static jvmtiError JNICALL
557 _Jv_JVMTI_SetSystemProperty (MAYBE_UNUSED jvmtiEnv *env, const char *property,
558 const char *value)
559 {
560 REQUIRE_PHASE (env, JVMTI_PHASE_ONLOAD);
561
562 NULL_CHECK (property);
563 if (value == NULL)
564 {
565 // FIXME: When would a property not be writeable?
566 return JVMTI_ERROR_NONE;
567 }
568
569 jstring prop_str = JvNewStringUTF(property);
570 jstring value_str = JvNewStringUTF(value);
571 gnu::classpath::SystemProperties::setProperty(prop_str, value_str);
572 return JVMTI_ERROR_NONE;
573 }
574
575 static jvmtiError JNICALL
576 _Jv_JVMTI_GetTime (MAYBE_UNUSED jvmtiEnv *env, jlong *nanos_ptr)
577 {
578 NULL_CHECK (nanos_ptr);
579 *nanos_ptr = _Jv_platform_nanotime();
580 return JVMTI_ERROR_NONE;
581 }
582
583 static jvmtiError JNICALL
584 _Jv_JVMTI_GetAvailableProcessors (MAYBE_UNUSED jvmtiEnv *env,
585 jint *nprocessors_ptr)
586 {
587 NULL_CHECK (nprocessors_ptr);
588 #ifdef _SC_NPROCESSORS_ONLN
589 *nprocessors_ptr = sysconf(_SC_NPROCESSORS_ONLN);
590 #else
591 *nprocessors_ptr = 1;
592 #endif
593 return JVMTI_ERROR_NONE;
594 }
595
596 static jvmtiError JNICALL
597 _Jv_JVMTI_AddToBootstrapClassLoaderSearch (MAYBE_UNUSED jvmtiEnv *env,
598 const char *segment)
599 {
600 using namespace java::lang;
601 using namespace java::net;
602 using namespace gnu::gcj::runtime;
603
604 REQUIRE_PHASE (env, JVMTI_PHASE_ONLOAD);
605 NULL_CHECK (segment);
606
607 jstring str_segment = JvNewStringUTF(segment);
608 URL *url;
609 try
610 {
611 url = new URL(JvNewStringUTF("file"), NULL, str_segment);
612 }
613 catch (jthrowable ignore)
614 {
615 return JVMTI_ERROR_ILLEGAL_ARGUMENT;
616 }
617
618 BootClassLoader *loader = VMClassLoader::bootLoader;
619 // Don't call this too early.
620 // assert (loader != NULL);
621 loader->addURL(url);
622 return JVMTI_ERROR_NONE;
623 }
624
625 static jvmtiError JNICALL
626 _Jv_JVMTI_SetVerboseFlag (MAYBE_UNUSED jvmtiEnv *env, jvmtiVerboseFlag flag,
627 jboolean value)
628 {
629 switch (flag)
630 {
631 case JVMTI_VERBOSE_OTHER:
632 case JVMTI_VERBOSE_GC:
633 case JVMTI_VERBOSE_JNI:
634 // Ignore.
635 break;
636 case JVMTI_VERBOSE_CLASS:
637 gcj::verbose_class_flag = value;
638 break;
639 default:
640 return JVMTI_ERROR_ILLEGAL_ARGUMENT;
641 }
642 return JVMTI_ERROR_NONE;
643 }
644
645 static jvmtiError JNICALL
646 _Jv_JVMTI_GetObjectSize (MAYBE_UNUSED jvmtiEnv *env, jobject object,
647 jlong *result)
648 {
649 REQUIRE_PHASE (env, JVMTI_PHASE_START | JVMTI_PHASE_LIVE);
650 if (object == NULL)
651 return JVMTI_ERROR_INVALID_OBJECT;
652 NULL_CHECK (result);
653
654 jclass klass = object->getClass();
655 if (klass->isArray())
656 {
657 jclass comp = klass->getComponentType();
658 jint base
659 = (jint) (_Jv_uintptr_t) _Jv_GetArrayElementFromElementType(NULL,
660 klass->getComponentType());
661 // FIXME: correct for primitive types?
662 jint compSize = comp->size();
663 __JArray *array = (__JArray *) object;
664 *result = base + array->length * compSize;
665 }
666 else
667 {
668 // Note that if OBJECT is a String then it may (if
669 // str->data==str) take more space. Do we care?
670 *result = klass->size();
671 }
672 return JVMTI_ERROR_NONE;
673 }
674
675 /* An event is enabled only if it has both an event handler
676 and it is enabled in the environment. */
677 static void
678 check_enabled_event (jvmtiEvent type)
679 {
680 bool *enabled;
681 int offset;
682
683 #define GET_OFFSET(Event) \
684 do \
685 { \
686 enabled = &JVMTI::Event; \
687 offset = offsetof (jvmtiEventCallbacks, Event); \
688 } \
689 while (0)
690
691 switch (type)
692 {
693 case JVMTI_EVENT_VM_INIT:
694 GET_OFFSET (VMInit);
695 break;
696
697 case JVMTI_EVENT_VM_DEATH:
698 GET_OFFSET (VMDeath);
699 break;
700
701 case JVMTI_EVENT_THREAD_START:
702 GET_OFFSET (ThreadStart);
703 break;
704
705 case JVMTI_EVENT_THREAD_END:
706 GET_OFFSET (ThreadEnd);
707 break;
708
709 case JVMTI_EVENT_CLASS_FILE_LOAD_HOOK:
710 GET_OFFSET (ClassFileLoadHook);
711 break;
712
713 case JVMTI_EVENT_CLASS_LOAD:
714 GET_OFFSET (ClassLoad);
715 break;
716
717 case JVMTI_EVENT_CLASS_PREPARE:
718 GET_OFFSET (ClassPrepare);
719 break;
720
721 case JVMTI_EVENT_VM_START:
722 GET_OFFSET (VMStart);
723 break;
724
725 case JVMTI_EVENT_EXCEPTION:
726 GET_OFFSET (Exception);
727 break;
728
729 case JVMTI_EVENT_EXCEPTION_CATCH:
730 GET_OFFSET (ExceptionCatch);
731 break;
732
733 case JVMTI_EVENT_SINGLE_STEP:
734 GET_OFFSET (SingleStep);
735 break;
736
737 case JVMTI_EVENT_FRAME_POP:
738 GET_OFFSET (FramePop);
739 break;
740
741 case JVMTI_EVENT_BREAKPOINT:
742 GET_OFFSET (Breakpoint);
743 break;
744
745 case JVMTI_EVENT_FIELD_ACCESS:
746 GET_OFFSET (FieldAccess);
747 break;
748
749 case JVMTI_EVENT_FIELD_MODIFICATION:
750 GET_OFFSET (FieldModification);
751 break;
752
753 case JVMTI_EVENT_METHOD_ENTRY:
754 GET_OFFSET (MethodEntry);
755 break;
756
757 case JVMTI_EVENT_METHOD_EXIT:
758 GET_OFFSET (MethodExit);
759 break;
760
761 case JVMTI_EVENT_NATIVE_METHOD_BIND:
762 GET_OFFSET (NativeMethodBind);
763 break;
764
765 case JVMTI_EVENT_COMPILED_METHOD_LOAD:
766 GET_OFFSET (CompiledMethodLoad);
767 break;
768
769 case JVMTI_EVENT_COMPILED_METHOD_UNLOAD:
770 GET_OFFSET (CompiledMethodUnload);
771 break;
772
773 case JVMTI_EVENT_DYNAMIC_CODE_GENERATED:
774 GET_OFFSET (DynamicCodeGenerated);
775 break;
776
777 case JVMTI_EVENT_DATA_DUMP_REQUEST:
778 GET_OFFSET (DataDumpRequest);
779 break;
780
781 case JVMTI_EVENT_MONITOR_WAIT:
782 GET_OFFSET (MonitorWait);
783 break;
784
785 case JVMTI_EVENT_MONITOR_WAITED:
786 GET_OFFSET (MonitorWaited);
787 break;
788
789 case JVMTI_EVENT_MONITOR_CONTENDED_ENTER:
790 GET_OFFSET (MonitorContendedEnter);
791 break;
792
793 case JVMTI_EVENT_MONITOR_CONTENDED_ENTERED:
794 GET_OFFSET (MonitorContendedEntered);
795 break;
796
797 case JVMTI_EVENT_GARBAGE_COLLECTION_START:
798 GET_OFFSET (GarbageCollectionStart);
799 break;
800
801 case JVMTI_EVENT_GARBAGE_COLLECTION_FINISH:
802 GET_OFFSET (GarbageCollectionFinish);
803 break;
804
805 case JVMTI_EVENT_OBJECT_FREE:
806 GET_OFFSET (ObjectFree);
807 break;
808
809 case JVMTI_EVENT_VM_OBJECT_ALLOC:
810 GET_OFFSET (VMObjectAlloc);
811 break;
812
813 default:
814 fprintf (stderr,
815 "libgcj: check_enabled_event for unknown JVMTI event (%d)\n",
816 (int) type);
817 return;
818 }
819 #undef GET_OFFSET
820
821 int index = EVENT_INDEX (type); // safe since caller checks this
822
823 JvSynchronize dummy (_envListLock);
824 struct jvmti_env_list *e;
825 FOREACH_ENVIRONMENT (e)
826 {
827 char *addr
828 = reinterpret_cast<char *> (&e->env->callbacks) + offset;
829 void **callback = reinterpret_cast<void **> (addr);
830 if (e->env->enabled[index] && *callback != NULL)
831 {
832 *enabled = true;
833 return;
834 }
835 }
836
837 *enabled = false;
838 }
839
840 static void
841 check_enabled_events ()
842 {
843 check_enabled_event (JVMTI_EVENT_VM_INIT);
844 check_enabled_event (JVMTI_EVENT_VM_DEATH);
845 check_enabled_event (JVMTI_EVENT_THREAD_START);
846 check_enabled_event (JVMTI_EVENT_THREAD_END);
847 check_enabled_event (JVMTI_EVENT_CLASS_FILE_LOAD_HOOK);
848 check_enabled_event (JVMTI_EVENT_CLASS_LOAD);
849 check_enabled_event (JVMTI_EVENT_CLASS_PREPARE);
850 check_enabled_event (JVMTI_EVENT_VM_START);
851 check_enabled_event (JVMTI_EVENT_EXCEPTION);
852 check_enabled_event (JVMTI_EVENT_EXCEPTION_CATCH);
853 check_enabled_event (JVMTI_EVENT_SINGLE_STEP);
854 check_enabled_event (JVMTI_EVENT_FRAME_POP);
855 check_enabled_event (JVMTI_EVENT_BREAKPOINT);
856 check_enabled_event (JVMTI_EVENT_FIELD_ACCESS);
857 check_enabled_event (JVMTI_EVENT_FIELD_MODIFICATION);
858 check_enabled_event (JVMTI_EVENT_METHOD_ENTRY);
859 check_enabled_event (JVMTI_EVENT_METHOD_EXIT);
860 check_enabled_event (JVMTI_EVENT_NATIVE_METHOD_BIND);
861 check_enabled_event (JVMTI_EVENT_COMPILED_METHOD_LOAD);
862 check_enabled_event (JVMTI_EVENT_COMPILED_METHOD_UNLOAD);
863 check_enabled_event (JVMTI_EVENT_DYNAMIC_CODE_GENERATED);
864 check_enabled_event (JVMTI_EVENT_DATA_DUMP_REQUEST);
865 check_enabled_event (JVMTI_EVENT_MONITOR_WAIT);
866 check_enabled_event (JVMTI_EVENT_MONITOR_WAITED);
867 check_enabled_event (JVMTI_EVENT_MONITOR_CONTENDED_ENTER);
868 check_enabled_event (JVMTI_EVENT_MONITOR_CONTENDED_ENTERED);
869 check_enabled_event (JVMTI_EVENT_GARBAGE_COLLECTION_START);
870 check_enabled_event (JVMTI_EVENT_GARBAGE_COLLECTION_FINISH);
871 check_enabled_event (JVMTI_EVENT_OBJECT_FREE);
872 check_enabled_event (JVMTI_EVENT_VM_OBJECT_ALLOC);
873 }
874
875 static jvmtiError JNICALL
876 _Jv_JVMTI_SetEventNotificationMode (jvmtiEnv *env, jvmtiEventMode mode,
877 jvmtiEvent type, jthread event_thread, ...)
878 {
879 REQUIRE_PHASE (env, JVMTI_PHASE_ONLOAD | JVMTI_PHASE_LIVE);
880
881 if (event_thread != NULL)
882 {
883 using namespace java::lang;
884 Thread *t = reinterpret_cast<Thread *> (event_thread);
885 THREAD_CHECK_VALID (t);
886 THREAD_CHECK_IS_ALIVE (t);
887 }
888
889 bool enabled;
890 switch (mode)
891 {
892 case JVMTI_DISABLE:
893 enabled = false;
894 break;
895 case JVMTI_ENABLE:
896 enabled = true;
897 break;
898
899 default:
900 return JVMTI_ERROR_ILLEGAL_ARGUMENT;
901 }
902
903 switch (type)
904 {
905 case JVMTI_EVENT_VM_INIT:
906 case JVMTI_EVENT_VM_DEATH:
907 case JVMTI_EVENT_THREAD_START:
908 case JVMTI_EVENT_VM_START:
909 case JVMTI_EVENT_COMPILED_METHOD_LOAD:
910 case JVMTI_EVENT_COMPILED_METHOD_UNLOAD:
911 case JVMTI_EVENT_DYNAMIC_CODE_GENERATED:
912 case JVMTI_EVENT_DATA_DUMP_REQUEST:
913 ILLEGAL_ARGUMENT (event_thread != NULL);
914 break;
915
916 case JVMTI_EVENT_THREAD_END:
917 case JVMTI_EVENT_CLASS_FILE_LOAD_HOOK:
918 case JVMTI_EVENT_CLASS_LOAD:
919 case JVMTI_EVENT_CLASS_PREPARE:
920 case JVMTI_EVENT_EXCEPTION:
921 case JVMTI_EVENT_EXCEPTION_CATCH:
922 case JVMTI_EVENT_SINGLE_STEP:
923 case JVMTI_EVENT_FRAME_POP:
924 case JVMTI_EVENT_BREAKPOINT:
925 case JVMTI_EVENT_FIELD_ACCESS:
926 case JVMTI_EVENT_FIELD_MODIFICATION:
927 case JVMTI_EVENT_METHOD_ENTRY:
928 case JVMTI_EVENT_METHOD_EXIT:
929 case JVMTI_EVENT_NATIVE_METHOD_BIND:
930 case JVMTI_EVENT_MONITOR_WAIT:
931 case JVMTI_EVENT_MONITOR_WAITED:
932 case JVMTI_EVENT_MONITOR_CONTENDED_ENTER:
933 case JVMTI_EVENT_MONITOR_CONTENDED_ENTERED:
934 case JVMTI_EVENT_GARBAGE_COLLECTION_START:
935 case JVMTI_EVENT_GARBAGE_COLLECTION_FINISH:
936 case JVMTI_EVENT_OBJECT_FREE:
937 case JVMTI_EVENT_VM_OBJECT_ALLOC:
938 break;
939
940 default:
941 return JVMTI_ERROR_INVALID_EVENT_TYPE;
942 }
943
944 env->thread[EVENT_INDEX(type)] = event_thread;
945 env->enabled[EVENT_INDEX(type)] = enabled;
946 check_enabled_event (type);
947 return JVMTI_ERROR_NONE;
948 }
949
950 static jvmtiError JNICALL
951 _Jv_JVMTI_SetEventCallbacks (jvmtiEnv *env,
952 const jvmtiEventCallbacks *callbacks,
953 jint size_of_callbacks)
954 {
955 REQUIRE_PHASE (env, JVMTI_PHASE_ONLOAD | JVMTI_PHASE_LIVE);
956 ILLEGAL_ARGUMENT (size_of_callbacks < 0);
957
958 // Copy the list of callbacks into the environment
959 memcpy (&env->callbacks, callbacks, sizeof (jvmtiEventCallbacks));
960
961 /* Check which events are now enabeld (JVMTI makes no requirements
962 about the order in which SetEventCallbacks and SetEventNotifications
963 are called. So we must check all events here. */
964 check_enabled_events ();
965
966 return JVMTI_ERROR_NONE;
967 }
968
969 static jvmtiError JNICALL
970 _Jv_JVMTI_GetErrorName (MAYBE_UNUSED jvmtiEnv *env, jvmtiError error,
971 char **name_ptr)
972 {
973 NULL_CHECK (name_ptr);
974
975 const char *name;
976 switch (error)
977 {
978 case JVMTI_ERROR_NONE:
979 name = "none";
980 break;
981
982 case JVMTI_ERROR_NULL_POINTER:
983 name = "null pointer";
984 break;
985
986 case JVMTI_ERROR_OUT_OF_MEMORY:
987 name = "out of memory";
988 break;
989
990 case JVMTI_ERROR_ACCESS_DENIED:
991 name = "access denied";
992 break;
993
994 case JVMTI_ERROR_WRONG_PHASE:
995 name = "wrong phase";
996 break;
997
998 case JVMTI_ERROR_INTERNAL:
999 name = "internal error";
1000 break;
1001
1002 case JVMTI_ERROR_UNATTACHED_THREAD:
1003 name = "unattached thread";
1004 break;
1005
1006 case JVMTI_ERROR_INVALID_ENVIRONMENT:
1007 name = "invalid environment";
1008 break;
1009
1010 case JVMTI_ERROR_INVALID_PRIORITY:
1011 name = "invalid priority";
1012 break;
1013
1014 case JVMTI_ERROR_THREAD_NOT_SUSPENDED:
1015 name = "thread not suspended";
1016 break;
1017
1018 case JVMTI_ERROR_THREAD_SUSPENDED:
1019 name = "thread suspended";
1020 break;
1021
1022 case JVMTI_ERROR_THREAD_NOT_ALIVE:
1023 name = "thread not alive";
1024 break;
1025
1026 case JVMTI_ERROR_CLASS_NOT_PREPARED:
1027 name = "class not prepared";
1028 break;
1029
1030 case JVMTI_ERROR_NO_MORE_FRAMES:
1031 name = "no more frames";
1032 break;
1033
1034 case JVMTI_ERROR_OPAQUE_FRAME:
1035 name = "opaque frame";
1036 break;
1037
1038 case JVMTI_ERROR_DUPLICATE:
1039 name = "duplicate";
1040 break;
1041
1042 case JVMTI_ERROR_NOT_FOUND:
1043 name = "not found";
1044 break;
1045
1046 case JVMTI_ERROR_NOT_MONITOR_OWNER:
1047 name = "not monitor owner";
1048 break;
1049
1050 case JVMTI_ERROR_INTERRUPT:
1051 name = "interrupted";
1052 break;
1053
1054 case JVMTI_ERROR_UNMODIFIABLE_CLASS:
1055 name = "unmodifiable class";
1056 break;
1057
1058 case JVMTI_ERROR_NOT_AVAILABLE:
1059 name = "not available";
1060 break;
1061
1062 case JVMTI_ERROR_ABSENT_INFORMATION:
1063 name = "absent information";
1064 break;
1065
1066 case JVMTI_ERROR_INVALID_EVENT_TYPE:
1067 name = "invalid event type";
1068 break;
1069
1070 case JVMTI_ERROR_NATIVE_METHOD:
1071 name = "native method";
1072 break;
1073
1074 case JVMTI_ERROR_INVALID_THREAD:
1075 name = "invalid thread";
1076 break;
1077
1078 case JVMTI_ERROR_INVALID_THREAD_GROUP:
1079 name = "invalid thread group";
1080 break;
1081
1082 case JVMTI_ERROR_INVALID_OBJECT:
1083 name = "invalid object";
1084 break;
1085
1086 case JVMTI_ERROR_INVALID_CLASS:
1087 name = "invalid class";
1088 break;
1089
1090 case JVMTI_ERROR_INVALID_METHODID:
1091 name = "invalid method ID";
1092 break;
1093
1094 case JVMTI_ERROR_INVALID_LOCATION:
1095 name = "invalid location";
1096 break;
1097
1098 case JVMTI_ERROR_INVALID_FIELDID:
1099 name = "invalid field ID";
1100 break;
1101
1102 case JVMTI_ERROR_TYPE_MISMATCH:
1103 name = "type mismatch";
1104 break;
1105
1106 case JVMTI_ERROR_INVALID_SLOT:
1107 name = "invalid slot";
1108 break;
1109
1110 case JVMTI_ERROR_INVALID_MONITOR:
1111 name = "invalid monitor";
1112 break;
1113
1114 case JVMTI_ERROR_INVALID_CLASS_FORMAT:
1115 name = "invalid class format";
1116 break;
1117
1118 case JVMTI_ERROR_CIRCULAR_CLASS_DEFINITION:
1119 name = "circular class definition";
1120 break;
1121
1122 case JVMTI_ERROR_UNSUPPORTED_REDEFINITION_METHOD_ADDED:
1123 name = "unsupported redefinition: method added";
1124 break;
1125
1126 case JVMTI_ERROR_UNSUPPORTED_REDEFINITION_SCHEMA_CHANGED:
1127 name = "unsupported redefinition: schema changed";
1128 break;
1129
1130 case JVMTI_ERROR_INVALID_TYPESTATE:
1131 name = "invalid type state";
1132 break;
1133
1134 case JVMTI_ERROR_FAILS_VERIFICATION:
1135 name = "fails verification";
1136 break;
1137
1138 case JVMTI_ERROR_UNSUPPORTED_REDEFINITION_HIERARCHY_CHANGED:
1139 name = "unsupported redefinition: hierarchy changed";
1140 break;
1141
1142 case JVMTI_ERROR_UNSUPPORTED_REDEFINITION_METHOD_DELETED:
1143 name = "unsupported redefinition: method deleted";
1144 break;
1145
1146 case JVMTI_ERROR_UNSUPPORTED_VERSION:
1147 name = "unsupported version";
1148 break;
1149
1150 case JVMTI_ERROR_NAMES_DONT_MATCH:
1151 name = "names do not match";
1152 break;
1153
1154 case JVMTI_ERROR_UNSUPPORTED_REDEFINITION_CLASS_MODIFIERS_CHANGED:
1155 name = "unsupported redefinition: class modifiers changed";
1156 break;
1157
1158 case JVMTI_ERROR_UNSUPPORTED_REDEFINITION_METHOD_MODIFIERS_CHANGED:
1159 name = "unsupported redefinition: method modifiers changed";
1160 break;
1161
1162 case JVMTI_ERROR_MUST_POSSESS_CAPABILITY:
1163 name = "must possess capability";
1164 break;
1165
1166 case JVMTI_ERROR_ILLEGAL_ARGUMENT:
1167 name = "illegal argument";
1168 break;
1169
1170 default:
1171 return JVMTI_ERROR_ILLEGAL_ARGUMENT;
1172 }
1173
1174 *name_ptr = (char *) _Jv_MallocUnchecked (strlen (name) + 1);
1175 if (*name_ptr == NULL)
1176 return JVMTI_ERROR_OUT_OF_MEMORY;
1177
1178 strcpy (*name_ptr, name);
1179 return JVMTI_ERROR_NONE;
1180 }
1181
1182 #define RESERVED NULL
1183 #define UNIMPLEMENTED NULL
1184
1185 struct _Jv_jvmtiEnv _Jv_JVMTI_Interface =
1186 {
1187 RESERVED, // reserved1
1188 _Jv_JVMTI_SetEventNotificationMode, // SetEventNotificationMode
1189 RESERVED, // reserved3
1190 UNIMPLEMENTED, // GetAllThreads
1191 _Jv_JVMTI_SuspendThread, // SuspendThread
1192 _Jv_JVMTI_ResumeThread, // ResumeThread
1193 UNIMPLEMENTED, // StopThread
1194 _Jv_JVMTI_InterruptThread, // InterruptThread
1195 UNIMPLEMENTED, // GetThreadInfo
1196 UNIMPLEMENTED, // GetOwnedMonitorInfo
1197 UNIMPLEMENTED, // GetCurrentContendedMonitor
1198 UNIMPLEMENTED, // RunAgentThread
1199 UNIMPLEMENTED, // GetTopThreadGroups
1200 UNIMPLEMENTED, // GetThreadGroupInfo
1201 UNIMPLEMENTED, // GetThreadGroupChildren
1202 UNIMPLEMENTED, // GetFrameCount
1203 UNIMPLEMENTED, // GetThreadState
1204 RESERVED, // reserved18
1205 UNIMPLEMENTED, // GetFrameLocation
1206 UNIMPLEMENTED, // NotifyPopFrame
1207 UNIMPLEMENTED, // GetLocalObject
1208 UNIMPLEMENTED, // GetLocalInt
1209 UNIMPLEMENTED, // GetLocalLong
1210 UNIMPLEMENTED, // GetLocalFloat
1211 UNIMPLEMENTED, // GetLocalDouble
1212 UNIMPLEMENTED, // SetLocalObject
1213 UNIMPLEMENTED, // SetLocalInt
1214 UNIMPLEMENTED, // SetLocalLong
1215 UNIMPLEMENTED, // SetLocalFloat
1216 UNIMPLEMENTED, // SetLocalDouble
1217 _Jv_JVMTI_CreateRawMonitor, // CreateRawMonitor
1218 _Jv_JVMTI_DestroyRawMonitor, // DestroyRawMonitor
1219 _Jv_JVMTI_RawMonitorEnter, // RawMonitorEnter
1220 _Jv_JVMTI_RawMonitorExit, // RawMonitorExit
1221 _Jv_JVMTI_RawMonitorWait, // RawMonitorWait
1222 _Jv_JVMTI_RawMonitorNotify, // RawMonitorNotify
1223 _Jv_JVMTI_RawMonitorNotifyAll, // RawMonitorNotifyAll
1224 UNIMPLEMENTED, // SetBreakpoint
1225 UNIMPLEMENTED, // ClearBreakpoint
1226 RESERVED, // reserved40
1227 UNIMPLEMENTED, // SetFieldAccessWatch
1228 UNIMPLEMENTED, // ClearFieldAccessWatch
1229 UNIMPLEMENTED, // SetFieldModificationWatch
1230 UNIMPLEMENTED, // ClearFieldModificationWatch
1231 RESERVED, // reserved45
1232 _Jv_JVMTI_Allocate, // Allocate
1233 _Jv_JVMTI_Deallocate, // Deallocate
1234 UNIMPLEMENTED, // GetClassSignature
1235 UNIMPLEMENTED, // GetClassStatus
1236 UNIMPLEMENTED, // GetSourceFileName
1237 _Jv_JVMTI_GetClassModifiers, // GetClassModifiers
1238 _Jv_JVMTI_GetClassMethods, // GetClassMethods
1239 UNIMPLEMENTED, // GetClassFields
1240 UNIMPLEMENTED, // GetImplementedInterfaces
1241 _Jv_JVMTI_IsInterface, // IsInterface
1242 _Jv_JVMTI_IsArrayClass, // IsArrayClass
1243 _Jv_JVMTI_GetClassLoader, // GetClassLoader
1244 _Jv_JVMTI_GetObjectHashCode, // GetObjectHashCode
1245 UNIMPLEMENTED, // GetObjectMonitorUsage
1246 UNIMPLEMENTED, // GetFieldName
1247 UNIMPLEMENTED, // GetFieldDeclaringClass
1248 _Jv_JVMTI_GetFieldModifiers, // GetFieldModifiers
1249 _Jv_JVMTI_IsFieldSynthetic, // IsFieldSynthetic
1250 UNIMPLEMENTED, // GetMethodName
1251 UNIMPLEMENTED, // GetMethodDeclaringClass
1252 _Jv_JVMTI_GetMethodModifiers, // GetMethodModifers
1253 RESERVED, // reserved67
1254 UNIMPLEMENTED, // GetMaxLocals
1255 UNIMPLEMENTED, // GetArgumentsSize
1256 UNIMPLEMENTED, // GetLineNumberTable
1257 UNIMPLEMENTED, // GetMethodLocation
1258 UNIMPLEMENTED, // GetLocalVariableTable
1259 RESERVED, // reserved73
1260 RESERVED, // reserved74
1261 UNIMPLEMENTED, // GetBytecodes
1262 _Jv_JVMTI_IsMethodNative, // IsMethodNative
1263 _Jv_JVMTI_IsMethodSynthetic, // IsMethodSynthetic
1264 UNIMPLEMENTED, // GetLoadedClasses
1265 _Jv_JVMTI_GetClassLoaderClasses, // GetClassLoaderClasses
1266 UNIMPLEMENTED, // PopFrame
1267 RESERVED, // reserved81
1268 RESERVED, // reserved82
1269 RESERVED, // reserved83
1270 RESERVED, // reserved84
1271 RESERVED, // reserved85
1272 RESERVED, // reserved86
1273 UNIMPLEMENTED, // RedefineClasses
1274 UNIMPLEMENTED, // GetVersionNumber
1275 UNIMPLEMENTED, // GetCapabilities
1276 UNIMPLEMENTED, // GetSourceDebugExtension
1277 UNIMPLEMENTED, // IsMethodObsolete
1278 UNIMPLEMENTED, // SuspendThreadList
1279 UNIMPLEMENTED, // ResumeThreadList
1280 RESERVED, // reserved94
1281 RESERVED, // reserved95
1282 RESERVED, // reserved96
1283 RESERVED, // reserved97
1284 RESERVED, // reserved98
1285 RESERVED, // reserved99
1286 UNIMPLEMENTED, // GetAllStackTraces
1287 UNIMPLEMENTED, // GetThreadListStackTraces
1288 UNIMPLEMENTED, // GetThreadLocalStorage
1289 UNIMPLEMENTED, // SetThreadLocalStorage
1290 UNIMPLEMENTED, // GetStackTrace
1291 RESERVED, // reserved105
1292 UNIMPLEMENTED, // GetTag
1293 UNIMPLEMENTED, // SetTag
1294 _Jv_JVMTI_ForceGarbageCollection, // ForceGarbageCollection
1295 UNIMPLEMENTED, // IterateOverObjectsReachable
1296 UNIMPLEMENTED, // IterateOverReachableObjects
1297 UNIMPLEMENTED, // IterateOverHeap
1298 UNIMPLEMENTED, // IterateOverInstanceOfClass
1299 RESERVED, // reserved113
1300 UNIMPLEMENTED, // GetObjectsWithTags
1301 RESERVED, // reserved115
1302 RESERVED, // reserved116
1303 RESERVED, // reserved117
1304 RESERVED, // reserved118
1305 RESERVED, // reserved119
1306 _Jv_JVMTI_SetJNIFunctionTable, // SetJNIFunctionTable
1307 _Jv_JVMTI_GetJNIFunctionTable, // GetJNIFunctionTable
1308 _Jv_JVMTI_SetEventCallbacks, // SetEventCallbacks
1309 UNIMPLEMENTED, // GenerateEvents
1310 UNIMPLEMENTED, // GetExtensionFunctions
1311 UNIMPLEMENTED, // GetExtensionEvents
1312 UNIMPLEMENTED, // SetExtensionEventCallback
1313 _Jv_JVMTI_DisposeEnvironment, // DisposeEnvironment
1314 _Jv_JVMTI_GetErrorName, // GetErrorName
1315 UNIMPLEMENTED, // GetJLocationFormat
1316 UNIMPLEMENTED, // GetSystemProperties
1317 _Jv_JVMTI_GetSystemProperty, // GetSystemProperty
1318 _Jv_JVMTI_SetSystemProperty, // SetSystemProperty
1319 UNIMPLEMENTED, // GetPhase
1320 UNIMPLEMENTED, // GetCurrentThreadCpuTimerInfo
1321 UNIMPLEMENTED, // GetCurrentThreadCpuTime
1322 UNIMPLEMENTED, // GetThreadCpuTimerInfo
1323 UNIMPLEMENTED, // GetThreadCpuTime
1324 UNIMPLEMENTED, // GetTimerInfo
1325 _Jv_JVMTI_GetTime, // GetTime
1326 UNIMPLEMENTED, // GetPotentialCapabilities
1327 RESERVED, // reserved141
1328 UNIMPLEMENTED, // AddCapabilities
1329 UNIMPLEMENTED, // RelinquishCapabilities
1330 _Jv_JVMTI_GetAvailableProcessors, // GetAvailableProcessors
1331 RESERVED, // reserved145
1332 RESERVED, // reserved146
1333 UNIMPLEMENTED, // GetEnvironmentLocalStorage
1334 UNIMPLEMENTED, // SetEnvironmentLocalStorage
1335 _Jv_JVMTI_AddToBootstrapClassLoaderSearch, // AddToBootstrapClassLoaderSearch
1336 _Jv_JVMTI_SetVerboseFlag, // SetVerboseFlag
1337 RESERVED, // reserved151
1338 RESERVED, // reserved152
1339 RESERVED, // reserved153
1340 _Jv_JVMTI_GetObjectSize // GetObjectSize
1341 };
1342
1343 _Jv_JVMTIEnv *
1344 _Jv_GetJVMTIEnv (void)
1345 {
1346 _Jv_JVMTIEnv *env
1347 = (_Jv_JVMTIEnv *) _Jv_MallocUnchecked (sizeof (_Jv_JVMTIEnv));
1348 env->p = &_Jv_JVMTI_Interface;
1349
1350 {
1351 JvSynchronize dummy (_envListLock);
1352 struct jvmti_env_list *element
1353 = (struct jvmti_env_list *) _Jv_MallocUnchecked (sizeof (struct jvmti_env_list));
1354 element->env = env;
1355 element->next = NULL;
1356
1357 if (_jvmtiEnvironments == NULL)
1358 _jvmtiEnvironments = element;
1359 else
1360 {
1361 struct jvmti_env_list *e;
1362 for (e = _jvmtiEnvironments; e->next != NULL; e = e->next)
1363 ;
1364 e->next = element;
1365 }
1366 }
1367
1368 return env;
1369 }
1370
1371 void
1372 _Jv_JVMTI_Init ()
1373 {
1374 _jvmtiEnvironments = NULL;
1375 _envListLock = new java::lang::Object ();
1376
1377 // No environments, so this should set all JVMTI:: members to false
1378 check_enabled_events ();
1379 }
1380
1381 static void
1382 post_event (jvmtiEnv *env, jvmtiEvent type, jthread event_thread, va_list args)
1383 {
1384 #define ARG(Type,Name) Type Name = (Type) va_arg (args, Type)
1385
1386 #define GET_BOOLEAN_ARG(Name) \
1387 ARG (int, b); \
1388 jboolean Name = (b == 0) ? false : true
1389
1390 #define GET_CHAR_ARG(Name) \
1391 ARG (int, c); \
1392 char Name = static_cast<char> (c)
1393
1394 switch (type)
1395 {
1396 case JVMTI_EVENT_VM_INIT:
1397 if (env->callbacks.VMInit != NULL)
1398 {
1399 ARG (JNIEnv *, jni_env);
1400 env->callbacks.VMInit (env, jni_env, event_thread);
1401 }
1402 break;
1403
1404 case JVMTI_EVENT_VM_DEATH:
1405 if (env->callbacks.VMDeath != NULL)
1406 {
1407 ARG (JNIEnv *, jni_env);
1408 env->callbacks.VMDeath (env, jni_env);
1409 }
1410 break;
1411
1412 case JVMTI_EVENT_THREAD_START:
1413 if (env->callbacks.ThreadStart != NULL)
1414 {
1415 ARG (JNIEnv *, jni_env);
1416 env->callbacks.ThreadStart (env, jni_env, event_thread);
1417 }
1418 break;
1419
1420 case JVMTI_EVENT_THREAD_END:
1421 if (env->callbacks.ThreadEnd != NULL)
1422 {
1423 ARG (JNIEnv *, jni_env);
1424 env->callbacks.ThreadEnd (env, jni_env, event_thread);
1425 }
1426 break;
1427
1428 case JVMTI_EVENT_CLASS_FILE_LOAD_HOOK:
1429 if (env->callbacks.ClassFileLoadHook != NULL)
1430 {
1431 ARG (JNIEnv *, jni_env);
1432 ARG (jclass, class_being_redefined);
1433 ARG (jobject, loader);
1434 ARG (const char *, name);
1435 ARG (jobject, protection_domain);
1436 ARG (jint, class_data_len);
1437 ARG (const unsigned char *, class_data);
1438 ARG (jint *, new_class_data_len);
1439 ARG (unsigned char **, new_class_data);
1440 env->callbacks.ClassFileLoadHook (env, jni_env,
1441 class_being_redefined, loader,
1442 name, protection_domain,
1443 class_data_len, class_data,
1444 new_class_data_len,
1445 new_class_data);
1446 }
1447 break;
1448
1449 case JVMTI_EVENT_CLASS_LOAD:
1450 if (env->callbacks.ClassLoad != NULL)
1451 {
1452 ARG (JNIEnv *, jni_env);
1453 ARG (jclass, klass);
1454 env->callbacks.ClassLoad (env, jni_env, event_thread, klass);
1455 }
1456 break;
1457
1458 case JVMTI_EVENT_CLASS_PREPARE:
1459 if (env->callbacks.ClassPrepare != NULL)
1460 {
1461 ARG (JNIEnv *, jni_env);
1462 ARG (jclass, klass);
1463 env->callbacks.ClassPrepare (env, jni_env, event_thread, klass);
1464 }
1465 break;
1466
1467 case JVMTI_EVENT_VM_START:
1468 if (env->callbacks.VMStart != NULL)
1469 {
1470 ARG (JNIEnv *, jni_env);
1471 env->callbacks.VMStart (env, jni_env);
1472 }
1473 break;
1474
1475 case JVMTI_EVENT_EXCEPTION:
1476 if (env->callbacks.Exception != NULL)
1477 {
1478 ARG (JNIEnv *, jni_env);
1479 ARG (jmethodID, method);
1480 ARG (jlocation, location);
1481 ARG (jobject, exception);
1482 ARG (jmethodID, catch_method);
1483 ARG (jlocation, catch_location);
1484 env->callbacks.Exception (env, jni_env, event_thread, method,
1485 location, exception, catch_method,
1486 catch_location);
1487 }
1488 break;
1489
1490 case JVMTI_EVENT_EXCEPTION_CATCH:
1491 if (env->callbacks.ExceptionCatch != NULL)
1492 {
1493 ARG (JNIEnv *, jni_env);
1494 ARG (jmethodID, method);
1495 ARG (jlocation, location);
1496 ARG (jobject, exception);
1497 env->callbacks.ExceptionCatch (env, jni_env, event_thread, method,
1498 location, exception);
1499 }
1500 break;
1501
1502 case JVMTI_EVENT_SINGLE_STEP:
1503 if (env->callbacks.SingleStep != NULL)
1504 {
1505 ARG (JNIEnv *, jni_env);
1506 ARG (jmethodID, method);
1507 ARG (jlocation, location);
1508 env->callbacks.SingleStep (env, jni_env, event_thread, method,
1509 location);
1510 }
1511 break;
1512
1513 case JVMTI_EVENT_FRAME_POP:
1514 if (env->callbacks.FramePop != NULL)
1515 {
1516 ARG (JNIEnv *, jni_env);
1517 ARG (jmethodID, method);
1518 GET_BOOLEAN_ARG (was_popped_by_exception);
1519 env->callbacks.FramePop (env, jni_env, event_thread, method,
1520 was_popped_by_exception);
1521 }
1522 break;
1523
1524 case JVMTI_EVENT_BREAKPOINT:
1525 if (env->callbacks.Breakpoint != NULL)
1526 {
1527 ARG (JNIEnv *, jni_env);
1528 ARG (jmethodID, method);
1529 ARG (jlocation, location);
1530 env->callbacks.Breakpoint (env, jni_env, event_thread, method,
1531 location);
1532 }
1533 break;
1534
1535 case JVMTI_EVENT_FIELD_ACCESS:
1536 if (env->callbacks.FieldAccess != NULL)
1537 {
1538 ARG (JNIEnv *, jni_env);
1539 ARG (jmethodID, method);
1540 ARG (jlocation, location);
1541 ARG (jclass, field_class);
1542 ARG (jobject, object);
1543 ARG (jfieldID, field);
1544 env->callbacks.FieldAccess (env, jni_env, event_thread, method,
1545 location, field_class, object, field);
1546 }
1547 break;
1548
1549 case JVMTI_EVENT_FIELD_MODIFICATION:
1550 if (env->callbacks.FieldModification != NULL)
1551 {
1552 ARG (JNIEnv *, jni_env);
1553 ARG (jmethodID, method);
1554 ARG (jlocation, location);
1555 ARG (jclass, field_class);
1556 ARG (jobject, object);
1557 ARG (jfieldID, field);
1558 GET_CHAR_ARG (signature_type);
1559 ARG (jvalue, new_value);
1560 env->callbacks.FieldModification (env, jni_env, event_thread, method,
1561 location, field_class, object,
1562 field, signature_type, new_value);
1563 }
1564 break;
1565
1566 case JVMTI_EVENT_METHOD_ENTRY:
1567 if (env->callbacks.MethodEntry != NULL)
1568 {
1569 ARG (JNIEnv *, jni_env);
1570 ARG (jmethodID, method);
1571 env->callbacks.MethodEntry (env, jni_env, event_thread, method);
1572 }
1573 break;
1574
1575 case JVMTI_EVENT_METHOD_EXIT:
1576 if (env->callbacks.MethodExit != NULL)
1577 {
1578 ARG (JNIEnv *, jni_env);
1579 ARG (jmethodID, method);
1580 GET_BOOLEAN_ARG (was_popped_by_exception);
1581 ARG (jvalue, return_value);
1582 env->callbacks.MethodExit (env, jni_env, event_thread, method,
1583 was_popped_by_exception, return_value);
1584 }
1585 break;
1586
1587 case JVMTI_EVENT_NATIVE_METHOD_BIND:
1588 if (env->callbacks.NativeMethodBind != NULL)
1589 {
1590 ARG (JNIEnv *, jni_env);
1591 ARG (jmethodID, method);
1592 ARG (void *, address);
1593 ARG (void **, new_address_ptr);
1594 env->callbacks.NativeMethodBind (env, jni_env, event_thread, method,
1595 address, new_address_ptr);
1596 }
1597 break;
1598
1599 case JVMTI_EVENT_COMPILED_METHOD_LOAD:
1600 if (env->callbacks.CompiledMethodLoad != NULL)
1601 {
1602 ARG (jmethodID, method);
1603 ARG (jint, code_size);
1604 ARG (const void *, code_addr);
1605 ARG (jint, map_length);
1606 ARG (const jvmtiAddrLocationMap *, map);
1607 ARG (const void *, compile_info);
1608 env->callbacks.CompiledMethodLoad (env, method, code_size, code_addr,
1609 map_length, map, compile_info);
1610 }
1611 break;
1612
1613 case JVMTI_EVENT_COMPILED_METHOD_UNLOAD:
1614 if (env->callbacks.CompiledMethodUnload != NULL)
1615 {
1616 ARG (jmethodID, method);
1617 ARG (const void *, code_addr);
1618 env->callbacks.CompiledMethodUnload (env, method, code_addr);
1619 }
1620 break;
1621
1622 case JVMTI_EVENT_DYNAMIC_CODE_GENERATED:
1623 if (env->callbacks.DynamicCodeGenerated != NULL)
1624 {
1625 ARG (const char *, name);
1626 ARG (const void *, address);
1627 ARG (jint, length);
1628 env->callbacks.DynamicCodeGenerated (env, name, address, length);
1629 }
1630 break;
1631
1632 case JVMTI_EVENT_DATA_DUMP_REQUEST:
1633 if (env->callbacks.DataDumpRequest != NULL)
1634 {
1635 env->callbacks.DataDumpRequest (env);
1636 }
1637 break;
1638
1639 case JVMTI_EVENT_MONITOR_WAIT:
1640 if (env->callbacks.MonitorWait != NULL)
1641 {
1642 ARG (JNIEnv *, jni_env);
1643 ARG (jobject, object);
1644 ARG (jlong, timeout);
1645 env->callbacks.MonitorWait (env, jni_env, event_thread, object,
1646 timeout);
1647 }
1648 break;
1649
1650 case JVMTI_EVENT_MONITOR_WAITED:
1651 if (env->callbacks.MonitorWaited != NULL)
1652 {
1653 ARG (JNIEnv *, jni_env);
1654 ARG (jobject, object);
1655 GET_BOOLEAN_ARG (timed_out);
1656 env->callbacks.MonitorWaited (env, jni_env, event_thread, object,
1657 timed_out);
1658 }
1659 break;
1660
1661 case JVMTI_EVENT_MONITOR_CONTENDED_ENTER:
1662 if (env->callbacks.MonitorContendedEnter != NULL)
1663 {
1664 ARG (JNIEnv *, jni_env);
1665 ARG (jobject, object);
1666 env->callbacks.MonitorContendedEnter (env, jni_env, event_thread,
1667 object);
1668 }
1669 break;
1670
1671 case JVMTI_EVENT_MONITOR_CONTENDED_ENTERED:
1672 if (env->callbacks.MonitorContendedEntered != NULL)
1673 {
1674 ARG (JNIEnv *, jni_env);
1675 ARG (jobject, object);
1676 env->callbacks.MonitorContendedEntered (env, jni_env, event_thread,
1677 object);
1678 }
1679 break;
1680
1681 case JVMTI_EVENT_GARBAGE_COLLECTION_START:
1682 if (env->callbacks.GarbageCollectionStart != NULL)
1683 {
1684 env->callbacks.GarbageCollectionStart (env);
1685 }
1686 break;
1687
1688 case JVMTI_EVENT_GARBAGE_COLLECTION_FINISH:
1689 if (env->callbacks.GarbageCollectionFinish != NULL)
1690 {
1691 env->callbacks.GarbageCollectionFinish (env);
1692 }
1693 break;
1694
1695 case JVMTI_EVENT_OBJECT_FREE:
1696 if (env->callbacks.ObjectFree != NULL)
1697 {
1698 ARG (jlong, tag);
1699 env->callbacks.ObjectFree (env, tag);
1700 }
1701 break;
1702
1703 case JVMTI_EVENT_VM_OBJECT_ALLOC:
1704 if (env->callbacks.VMObjectAlloc != NULL)
1705 {
1706 ARG (JNIEnv *, jni_env);
1707 ARG (jobject, object);
1708 ARG (jclass, object_class);
1709 ARG (jlong, size);
1710 env->callbacks.VMObjectAlloc (env, jni_env, event_thread,
1711 object, object_class, size);
1712 }
1713 break;
1714
1715 default:
1716 fprintf (stderr, "libgcj: post of unknown JVMTI event (%d)\n",
1717 (int) type);
1718 break;
1719 }
1720 va_end (args);
1721 #undef ARG
1722 #undef GET_BOOLEAN_ARG
1723 #undef GET_CHAR_ARG
1724 }
1725
1726 /* Post an event to requesting JVMTI environments
1727 *
1728 * This function should not be called without consulting the
1729 * JVMTI_REQUESTED_EVENT macro first (for speed). It does no real
1730 * harm (other than kill speed), since this function will still
1731 * only send the event if it was properly requested by an environment.
1732 */
1733 void
1734 _Jv_JVMTI_PostEvent (jvmtiEvent type, jthread event_thread, ...)
1735 {
1736 va_list args;
1737 va_start (args, event_thread);
1738
1739 JvSynchronize dummy (_envListLock);
1740 struct jvmti_env_list *e;
1741 FOREACH_ENVIRONMENT (e)
1742 {
1743 /* Events are only posted if the event was explicitly enabled,
1744 it has a registered event handler, and the event thread
1745 matches (either globally or restricted to a specific thread).
1746 Here we check all but the event handler, which will be handled
1747 by post_event. */
1748 if (e->env->enabled[EVENT_INDEX(type)]
1749 && (e->env->thread[EVENT_INDEX(type)] == NULL
1750 || e->env->thread[EVENT_INDEX(type)] == event_thread))
1751 {
1752 post_event (e->env, type, event_thread, args);
1753 }
1754 }
1755
1756 va_end (args);
1757 }
This page took 0.110241 seconds and 6 git commands to generate.