30 #include "classfile/vmSymbols.hpp"
31 #include "jvmtifiles/jvmtiEnv.hpp"
32 #include "logging/log.hpp"
33 #include "memory/allocation.inline.hpp"
34 #include "memory/resourceArea.hpp"
35 #include "memory/universe.hpp"
36 #include "oops/access.inline.hpp"
37 #include "oops/arrayOop.inline.hpp"
38 #include "oops/constantPool.inline.hpp"
39 #include "oops/instanceMirrorKlass.hpp"
40 #include "oops/objArrayKlass.hpp"
41 #include "oops/objArrayOop.inline.hpp"
42 #include "oops/oop.inline.hpp"
43 #include "oops/typeArrayOop.inline.hpp"
44 #include "prims/jvmtiEventController.hpp"
45 #include "prims/jvmtiEventController.inline.hpp"
46 #include "prims/jvmtiExport.hpp"
47 #include "prims/jvmtiImpl.hpp"
48 #include "prims/jvmtiTagMap.hpp"
49 #include "runtime/biasedLocking.hpp"
50 #include "runtime/frame.inline.hpp"
51 #include "runtime/handles.inline.hpp"
52 #include "runtime/javaCalls.hpp"
53 #include "runtime/jniHandles.inline.hpp"
54 #include "runtime/mutex.hpp"
55 #include "runtime/mutexLocker.hpp"
56 #include "runtime/reflectionUtils.hpp"
57 #include "runtime/thread.inline.hpp"
58 #include "runtime/threadSMR.hpp"
59 #include "runtime/vframe.hpp"
60 #include "runtime/vmThread.hpp"
61 #include "runtime/vmOperations.hpp"
62 #include "utilities/macros.hpp"
63 #if INCLUDE_ZGC
64 #include "gc/z/zGlobals.hpp"
65 #endif
66
67 // JvmtiTagHashmapEntry
68 //
69 // Each entry encapsulates a reference to the tagged object
1471 // array callback
1472 if (is_array &&
1473 callbacks()->array_primitive_value_callback != NULL &&
1474 obj->is_typeArray()) {
1475 jint res = invoke_array_primitive_value_callback(
1476 callbacks()->array_primitive_value_callback,
1477 &wrapper,
1478 obj,
1479 (void*)user_data() );
1480 if (check_flags_for_abort(res)) return;
1481 }
1482 };
1483
1484
1485 // Deprecated function to iterate over all objects in the heap
1486 void JvmtiTagMap::iterate_over_heap(jvmtiHeapObjectFilter object_filter,
1487 Klass* klass,
1488 jvmtiHeapObjectCallback heap_object_callback,
1489 const void* user_data)
1490 {
1491 MutexLocker ml(Heap_lock);
1492 IterateOverHeapObjectClosure blk(this,
1493 klass,
1494 object_filter,
1495 heap_object_callback,
1496 user_data);
1497 VM_HeapIterateOperation op(&blk);
1498 VMThread::execute(&op);
1499 }
1500
1501
1502 // Iterates over all objects in the heap
1503 void JvmtiTagMap::iterate_through_heap(jint heap_filter,
1504 Klass* klass,
1505 const jvmtiHeapCallbacks* callbacks,
1506 const void* user_data)
1507 {
1508 MutexLocker ml(Heap_lock);
1509 IterateThroughHeapObjectClosure blk(this,
1510 klass,
1511 heap_filter,
1512 callbacks,
1513 user_data);
1514 VM_HeapIterateOperation op(&blk);
1515 VMThread::execute(&op);
1516 }
1517
1518 // support class for get_objects_with_tags
1519
1520 class TagObjectCollector : public JvmtiTagHashmapEntryClosure {
1521 private:
1522 JvmtiEnv* _env;
1523 jlong* _tags;
1524 jint _tag_count;
1525
1526 GrowableArray<jobject>* _object_results; // collected objects (JNI weak refs)
1527 GrowableArray<uint64_t>* _tag_results; // collected tags
3243 if (is_following_references()) {
3244
3245 // visit each object until all reachable objects have been
3246 // visited or the callback asked to terminate the iteration.
3247 while (!visit_stack()->is_empty()) {
3248 oop o = visit_stack()->pop();
3249 if (!ObjectMarker::visited(o)) {
3250 if (!visit(o)) {
3251 break;
3252 }
3253 }
3254 }
3255 }
3256 }
3257
3258 // iterate over all objects that are reachable from a set of roots
3259 void JvmtiTagMap::iterate_over_reachable_objects(jvmtiHeapRootCallback heap_root_callback,
3260 jvmtiStackReferenceCallback stack_ref_callback,
3261 jvmtiObjectReferenceCallback object_ref_callback,
3262 const void* user_data) {
3263 MutexLocker ml(Heap_lock);
3264 BasicHeapWalkContext context(heap_root_callback, stack_ref_callback, object_ref_callback);
3265 VM_HeapWalkOperation op(this, Handle(), context, user_data);
3266 VMThread::execute(&op);
3267 }
3268
3269 // iterate over all objects that are reachable from a given object
3270 void JvmtiTagMap::iterate_over_objects_reachable_from_object(jobject object,
3271 jvmtiObjectReferenceCallback object_ref_callback,
3272 const void* user_data) {
3273 oop obj = JNIHandles::resolve(object);
3274 Handle initial_object(Thread::current(), obj);
3275
3276 MutexLocker ml(Heap_lock);
3277 BasicHeapWalkContext context(NULL, NULL, object_ref_callback);
3278 VM_HeapWalkOperation op(this, initial_object, context, user_data);
3279 VMThread::execute(&op);
3280 }
3281
3282 // follow references from an initial object or the GC roots
3283 void JvmtiTagMap::follow_references(jint heap_filter,
3284 Klass* klass,
3285 jobject object,
3286 const jvmtiHeapCallbacks* callbacks,
3287 const void* user_data)
3288 {
3289 oop obj = JNIHandles::resolve(object);
3290 Handle initial_object(Thread::current(), obj);
3291
3292 MutexLocker ml(Heap_lock);
3293 AdvancedHeapWalkContext context(heap_filter, klass, callbacks);
3294 VM_HeapWalkOperation op(this, initial_object, context, user_data);
3295 VMThread::execute(&op);
3296 }
3297
3298
3299 void JvmtiTagMap::weak_oops_do(BoolObjectClosure* is_alive, OopClosure* f) {
3300 // No locks during VM bring-up (0 threads) and no safepoints after main
3301 // thread creation and before VMThread creation (1 thread); initial GC
3302 // verification can happen in that window which gets to here.
3303 assert(Threads::number_of_threads() <= 1 ||
3304 SafepointSynchronize::is_at_safepoint(),
3305 "must be executed at a safepoint");
3306 if (JvmtiEnv::environments_might_exist()) {
3307 JvmtiEnvIterator it;
3308 for (JvmtiEnvBase* env = it.first(); env != NULL; env = it.next(env)) {
3309 JvmtiTagMap* tag_map = env->tag_map_acquire();
3310 if (tag_map != NULL && !tag_map->is_empty()) {
3311 tag_map->do_weak_oops(is_alive, f);
|
30 #include "classfile/vmSymbols.hpp"
31 #include "jvmtifiles/jvmtiEnv.hpp"
32 #include "logging/log.hpp"
33 #include "memory/allocation.inline.hpp"
34 #include "memory/resourceArea.hpp"
35 #include "memory/universe.hpp"
36 #include "oops/access.inline.hpp"
37 #include "oops/arrayOop.inline.hpp"
38 #include "oops/constantPool.inline.hpp"
39 #include "oops/instanceMirrorKlass.hpp"
40 #include "oops/objArrayKlass.hpp"
41 #include "oops/objArrayOop.inline.hpp"
42 #include "oops/oop.inline.hpp"
43 #include "oops/typeArrayOop.inline.hpp"
44 #include "prims/jvmtiEventController.hpp"
45 #include "prims/jvmtiEventController.inline.hpp"
46 #include "prims/jvmtiExport.hpp"
47 #include "prims/jvmtiImpl.hpp"
48 #include "prims/jvmtiTagMap.hpp"
49 #include "runtime/biasedLocking.hpp"
50 #include "runtime/deoptimization.hpp"
51 #include "runtime/frame.inline.hpp"
52 #include "runtime/handles.inline.hpp"
53 #include "runtime/javaCalls.hpp"
54 #include "runtime/jniHandles.inline.hpp"
55 #include "runtime/mutex.hpp"
56 #include "runtime/mutexLocker.hpp"
57 #include "runtime/reflectionUtils.hpp"
58 #include "runtime/thread.inline.hpp"
59 #include "runtime/threadSMR.hpp"
60 #include "runtime/vframe.hpp"
61 #include "runtime/vmThread.hpp"
62 #include "runtime/vmOperations.hpp"
63 #include "utilities/macros.hpp"
64 #if INCLUDE_ZGC
65 #include "gc/z/zGlobals.hpp"
66 #endif
67
68 // JvmtiTagHashmapEntry
69 //
70 // Each entry encapsulates a reference to the tagged object
1472 // array callback
1473 if (is_array &&
1474 callbacks()->array_primitive_value_callback != NULL &&
1475 obj->is_typeArray()) {
1476 jint res = invoke_array_primitive_value_callback(
1477 callbacks()->array_primitive_value_callback,
1478 &wrapper,
1479 obj,
1480 (void*)user_data() );
1481 if (check_flags_for_abort(res)) return;
1482 }
1483 };
1484
1485
1486 // Deprecated function to iterate over all objects in the heap
1487 void JvmtiTagMap::iterate_over_heap(jvmtiHeapObjectFilter object_filter,
1488 Klass* klass,
1489 jvmtiHeapObjectCallback heap_object_callback,
1490 const void* user_data)
1491 {
1492 // EA based optimizations on tagged objects are already reverted.
1493 EscapeBarrier eb(JavaThread::current(),
1494 object_filter == JVMTI_HEAP_OBJECT_UNTAGGED || object_filter == JVMTI_HEAP_OBJECT_EITHER);
1495 eb.deoptimize_objects_all_threads();
1496 MutexLocker ml(Heap_lock);
1497 IterateOverHeapObjectClosure blk(this,
1498 klass,
1499 object_filter,
1500 heap_object_callback,
1501 user_data);
1502 VM_HeapIterateOperation op(&blk);
1503 VMThread::execute(&op);
1504 }
1505
1506
1507 // Iterates over all objects in the heap
1508 void JvmtiTagMap::iterate_through_heap(jint heap_filter,
1509 Klass* klass,
1510 const jvmtiHeapCallbacks* callbacks,
1511 const void* user_data)
1512 {
1513 // EA based optimizations on tagged objects are already reverted.
1514 EscapeBarrier eb(JavaThread::current(), !(heap_filter & JVMTI_HEAP_FILTER_UNTAGGED));
1515 eb.deoptimize_objects_all_threads();
1516 MutexLocker ml(Heap_lock);
1517 IterateThroughHeapObjectClosure blk(this,
1518 klass,
1519 heap_filter,
1520 callbacks,
1521 user_data);
1522 VM_HeapIterateOperation op(&blk);
1523 VMThread::execute(&op);
1524 }
1525
1526 // support class for get_objects_with_tags
1527
1528 class TagObjectCollector : public JvmtiTagHashmapEntryClosure {
1529 private:
1530 JvmtiEnv* _env;
1531 jlong* _tags;
1532 jint _tag_count;
1533
1534 GrowableArray<jobject>* _object_results; // collected objects (JNI weak refs)
1535 GrowableArray<uint64_t>* _tag_results; // collected tags
3251 if (is_following_references()) {
3252
3253 // visit each object until all reachable objects have been
3254 // visited or the callback asked to terminate the iteration.
3255 while (!visit_stack()->is_empty()) {
3256 oop o = visit_stack()->pop();
3257 if (!ObjectMarker::visited(o)) {
3258 if (!visit(o)) {
3259 break;
3260 }
3261 }
3262 }
3263 }
3264 }
3265
3266 // iterate over all objects that are reachable from a set of roots
3267 void JvmtiTagMap::iterate_over_reachable_objects(jvmtiHeapRootCallback heap_root_callback,
3268 jvmtiStackReferenceCallback stack_ref_callback,
3269 jvmtiObjectReferenceCallback object_ref_callback,
3270 const void* user_data) {
3271 JavaThread* jt = JavaThread::current();
3272 EscapeBarrier eb(jt, true);
3273 eb.deoptimize_objects_all_threads();
3274 MutexLocker ml(Heap_lock);
3275 BasicHeapWalkContext context(heap_root_callback, stack_ref_callback, object_ref_callback);
3276 VM_HeapWalkOperation op(this, Handle(), context, user_data);
3277 VMThread::execute(&op);
3278 }
3279
3280 // iterate over all objects that are reachable from a given object
3281 void JvmtiTagMap::iterate_over_objects_reachable_from_object(jobject object,
3282 jvmtiObjectReferenceCallback object_ref_callback,
3283 const void* user_data) {
3284 oop obj = JNIHandles::resolve(object);
3285 Handle initial_object(Thread::current(), obj);
3286
3287 MutexLocker ml(Heap_lock);
3288 BasicHeapWalkContext context(NULL, NULL, object_ref_callback);
3289 VM_HeapWalkOperation op(this, initial_object, context, user_data);
3290 VMThread::execute(&op);
3291 }
3292
3293 // follow references from an initial object or the GC roots
3294 void JvmtiTagMap::follow_references(jint heap_filter,
3295 Klass* klass,
3296 jobject object,
3297 const jvmtiHeapCallbacks* callbacks,
3298 const void* user_data)
3299 {
3300 oop obj = JNIHandles::resolve(object);
3301 JavaThread* jt = JavaThread::current();
3302 Handle initial_object(jt, obj);
3303 // EA based optimizations that are tagged or reachable from initial_object are already reverted.
3304 EscapeBarrier eb(jt,
3305 initial_object.is_null() && !(heap_filter & JVMTI_HEAP_FILTER_UNTAGGED));
3306 eb.deoptimize_objects_all_threads();
3307 MutexLocker ml(Heap_lock);
3308 AdvancedHeapWalkContext context(heap_filter, klass, callbacks);
3309 VM_HeapWalkOperation op(this, initial_object, context, user_data);
3310 VMThread::execute(&op);
3311 }
3312
3313
3314 void JvmtiTagMap::weak_oops_do(BoolObjectClosure* is_alive, OopClosure* f) {
3315 // No locks during VM bring-up (0 threads) and no safepoints after main
3316 // thread creation and before VMThread creation (1 thread); initial GC
3317 // verification can happen in that window which gets to here.
3318 assert(Threads::number_of_threads() <= 1 ||
3319 SafepointSynchronize::is_at_safepoint(),
3320 "must be executed at a safepoint");
3321 if (JvmtiEnv::environments_might_exist()) {
3322 JvmtiEnvIterator it;
3323 for (JvmtiEnvBase* env = it.first(); env != NULL; env = it.next(env)) {
3324 JvmtiTagMap* tag_map = env->tag_map_acquire();
3325 if (tag_map != NULL && !tag_map->is_empty()) {
3326 tag_map->do_weak_oops(is_alive, f);
|