changeset 26183:bbe259d3c8bc

8055098: WB API should be extended to provide information about size and age of object. Summary: Extend the WhiteBox API to provide information about the size and age of objects. Further add a mechanism to trigger a young GC. Reviewed-by: tschatzl, sjohanss Contributed-by: Leonid Mesnik <leonid.mesnik@oracle.com>
author tschatzl
date Thu, 21 Aug 2014 16:44:41 +0200
parents 89f44df5b438
children b21502379d4a
files hotspot/src/share/vm/gc_implementation/g1/g1CollectedHeap.cpp hotspot/src/share/vm/gc_implementation/parallelScavenge/vmPSOperations.cpp hotspot/src/share/vm/gc_interface/gcCause.cpp hotspot/src/share/vm/gc_interface/gcCause.hpp hotspot/src/share/vm/memory/genCollectedHeap.cpp hotspot/src/share/vm/prims/whitebox.cpp hotspot/test/testlibrary/whitebox/sun/hotspot/WhiteBox.java
diffstat 7 files changed, 52 insertions(+), 9 deletions(-) [+]
line wrap: on
line diff
--- a/hotspot/src/share/vm/gc_implementation/g1/g1CollectedHeap.cpp	Wed Aug 20 15:04:39 2014 +0200
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1CollectedHeap.cpp	Thu Aug 21 16:44:41 2014 +0200
@@ -2516,7 +2516,7 @@
         }
       }
     } else {
-      if (cause == GCCause::_gc_locker
+      if (cause == GCCause::_gc_locker || cause == GCCause::_wb_young_gc
           DEBUG_ONLY(|| cause == GCCause::_scavenge_alot)) {
 
         // Schedule a standard evacuation pause. We're setting word_size
--- a/hotspot/src/share/vm/gc_implementation/parallelScavenge/vmPSOperations.cpp	Wed Aug 20 15:04:39 2014 +0200
+++ b/hotspot/src/share/vm/gc_implementation/parallelScavenge/vmPSOperations.cpp	Thu Aug 21 16:44:41 2014 +0200
@@ -70,7 +70,7 @@
     "must be a ParallelScavengeHeap");
 
   GCCauseSetter gccs(heap, _gc_cause);
-  if (_gc_cause == GCCause::_gc_locker
+  if (_gc_cause == GCCause::_gc_locker || _gc_cause == GCCause::_wb_young_gc
       DEBUG_ONLY(|| _gc_cause == GCCause::_scavenge_alot)) {
     // If (and only if) the scavenge fails, this will invoke a full gc.
     heap->invoke_scavenge();
--- a/hotspot/src/share/vm/gc_interface/gcCause.cpp	Wed Aug 20 15:04:39 2014 +0200
+++ b/hotspot/src/share/vm/gc_interface/gcCause.cpp	Thu Aug 21 16:44:41 2014 +0200
@@ -51,6 +51,9 @@
     case _heap_dump:
       return "Heap Dump Initiated GC";
 
+    case _wb_young_gc:
+      return "WhiteBox Initiated Young GC";
+
     case _no_gc:
       return "No GC";
 
--- a/hotspot/src/share/vm/gc_interface/gcCause.hpp	Wed Aug 20 15:04:39 2014 +0200
+++ b/hotspot/src/share/vm/gc_interface/gcCause.hpp	Thu Aug 21 16:44:41 2014 +0200
@@ -46,6 +46,7 @@
     _gc_locker,
     _heap_inspection,
     _heap_dump,
+    _wb_young_gc,
 
     /* implementation independent, but reserved for GC use */
     _no_gc,
--- a/hotspot/src/share/vm/memory/genCollectedHeap.cpp	Wed Aug 20 15:04:39 2014 +0200
+++ b/hotspot/src/share/vm/memory/genCollectedHeap.cpp	Thu Aug 21 16:44:41 2014 +0200
@@ -708,15 +708,18 @@
 #else  // INCLUDE_ALL_GCS
     ShouldNotReachHere();
 #endif // INCLUDE_ALL_GCS
+  } else if (cause == GCCause::_wb_young_gc) {
+    // minor collection for WhiteBox API
+    collect(cause, 0);
   } else {
 #ifdef ASSERT
-    if (cause == GCCause::_scavenge_alot) {
-      // minor collection only
-      collect(cause, 0);
-    } else {
-      // Stop-the-world full collection
-      collect(cause, n_gens() - 1);
-    }
+  if (cause == GCCause::_scavenge_alot) {
+    // minor collection only
+    collect(cause, 0);
+  } else {
+    // Stop-the-world full collection
+    collect(cause, n_gens() - 1);
+  }
 #else
     // Stop-the-world full collection
     collect(cause, n_gens() - 1);
--- a/hotspot/src/share/vm/prims/whitebox.cpp	Wed Aug 20 15:04:39 2014 +0200
+++ b/hotspot/src/share/vm/prims/whitebox.cpp	Thu Aug 21 16:44:41 2014 +0200
@@ -47,6 +47,7 @@
 #include "utilities/exceptions.hpp"
 
 #if INCLUDE_ALL_GCS
+#include "gc_implementation/parallelScavenge/parallelScavengeHeap.inline.hpp"
 #include "gc_implementation/g1/concurrentMark.hpp"
 #include "gc_implementation/g1/g1CollectedHeap.inline.hpp"
 #include "gc_implementation/g1/heapRegionRemSet.hpp"
@@ -227,6 +228,30 @@
                                         (size_t) magnitude, (size_t) iterations);
 WB_END
 
+WB_ENTRY(jboolean, WB_isObjectInOldGen(JNIEnv* env, jobject o, jobject obj))
+  oop p = JNIHandles::resolve(obj);
+#if INCLUDE_ALL_GCS
+  if (UseG1GC) {
+    G1CollectedHeap* g1 = G1CollectedHeap::heap();
+    const HeapRegion* hr = g1->heap_region_containing(p);
+    if (hr == NULL) {
+      return false;
+    }
+    return !(hr->is_young());
+  } else if (UseParallelGC) {
+    ParallelScavengeHeap* psh = ParallelScavengeHeap::heap();
+    return !psh->is_in_young(p);
+  }
+#endif // INCLUDE_ALL_GCS
+  GenCollectedHeap* gch = GenCollectedHeap::heap();
+  return !gch->is_in_young(p);
+WB_END
+
+WB_ENTRY(jlong, WB_GetObjectSize(JNIEnv* env, jobject o, jobject obj))
+  oop p = JNIHandles::resolve(obj);
+  return p->size() * HeapWordSize;
+WB_END
+
 #if INCLUDE_ALL_GCS
 WB_ENTRY(jboolean, WB_G1IsHumongous(JNIEnv* env, jobject o, jobject obj))
   G1CollectedHeap* g1 = G1CollectedHeap::heap();
@@ -690,6 +715,9 @@
   Universe::heap()->collect(GCCause::_last_ditch_collection);
 WB_END
 
+WB_ENTRY(void, WB_YoungGC(JNIEnv* env, jobject o))
+  Universe::heap()->collect(GCCause::_wb_young_gc);
+WB_END
 
 WB_ENTRY(void, WB_ReadReservedMemory(JNIEnv* env, jobject o))
   // static+volatile in order to force the read to happen
@@ -841,6 +869,8 @@
 
 static JNINativeMethod methods[] = {
   {CC"getObjectAddress",   CC"(Ljava/lang/Object;)J", (void*)&WB_GetObjectAddress  },
+  {CC"getObjectSize",      CC"(Ljava/lang/Object;)J", (void*)&WB_GetObjectSize     },
+  {CC"isObjectInOldGen",   CC"(Ljava/lang/Object;)Z", (void*)&WB_isObjectInOldGen  },
   {CC"getHeapOopSize",     CC"()I",                   (void*)&WB_GetHeapOopSize    },
   {CC"isClassAlive0",      CC"(Ljava/lang/String;)Z", (void*)&WB_IsClassAlive      },
   {CC"parseCommandLine",
@@ -919,6 +949,7 @@
                                                       (void*)&WB_GetStringVMFlag},
   {CC"isInStringTable",    CC"(Ljava/lang/String;)Z", (void*)&WB_IsInStringTable  },
   {CC"fullGC",   CC"()V",                             (void*)&WB_FullGC },
+  {CC"youngGC",  CC"()V",                             (void*)&WB_YoungGC },
   {CC"readReservedMemory", CC"()V",                   (void*)&WB_ReadReservedMemory },
   {CC"allocateMetaspace",
      CC"(Ljava/lang/ClassLoader;J)J",                 (void*)&WB_AllocateMetaspace },
--- a/hotspot/test/testlibrary/whitebox/sun/hotspot/WhiteBox.java	Wed Aug 20 15:04:39 2014 +0200
+++ b/hotspot/test/testlibrary/whitebox/sun/hotspot/WhiteBox.java	Thu Aug 21 16:44:41 2014 +0200
@@ -73,6 +73,8 @@
   // Memory
   public native long getObjectAddress(Object o);
   public native int  getHeapOopSize();
+  public native boolean isObjectInOldGen(Object o);
+  public native long getObjectSize(Object o);
 
   // Runtime
   // Make sure class name is in the correct format
@@ -150,6 +152,9 @@
   public native long allocateMetaspace(ClassLoader classLoader, long size);
   public native void freeMetaspace(ClassLoader classLoader, long addr, long size);
 
+  // force Young GC
+  public native void youngGC();
+
   // force Full GC
   public native void fullGC();