src/share/vm/services/memBaseline.cpp

Print this page

        

@@ -21,13 +21,16 @@
  * questions.
  *
  */
 #include "precompiled.hpp"
 #include "memory/allocation.hpp"
+#include "runtime/safepoint.hpp"
+#include "runtime/thread.hpp"
 #include "services/memBaseline.hpp"
 #include "services/memTracker.hpp"
 
+
 MemType2Name MemBaseline::MemType2NameMap[NUMBER_OF_MEMORY_TYPE] = {
   {mtJavaHeap,   "Java Heap"},
   {mtClass,      "Class"},
   {mtThreadStack,"Thread Stack"},
   {mtThread,     "Thread"},

@@ -148,10 +151,19 @@
   _malloc_data[index].overwrite_counter(0);
 
   return true;
 }
 
+// check if there is a safepoint in progress, if so, block the thread
+// for the safepoint
+void MemBaseline::check_safepoint(JavaThread* thr) {
+  if (SafepointSynchronize::is_synchronizing()) {
+    // grab and drop the SR_lock to honor the safepoint protocol
+    MutexLocker ml(thr->SR_lock());
+  }
+}
+
 // baseline mmap'd memory records, generate overall summary and summaries by
 // memory types
 bool MemBaseline::baseline_vm_summary(const MemPointerArray* vm_records) {
   MemPointerArrayIteratorImpl vm_itr((MemPointerArray*)vm_records);
   VMMemRegion* vm_ptr = (VMMemRegion*)vm_itr.current();

@@ -343,21 +355,32 @@
   return true;
 }
 
 // baseline a snapshot. If summary_only = false, memory usages aggregated by
 // callsites are also baselined.
+// The method call can be lengthy, especially when detail tracking info is
+// requested. So the method checks for safepoint explicitly.
 bool MemBaseline::baseline(MemSnapshot& snapshot, bool summary_only) {
-  MutexLockerEx snapshot_locker(snapshot._lock, true);
+  Thread* THREAD = Thread::current();
+  assert(THREAD->is_Java_thread(), "must be a JavaThread");
+  MutexLocker snapshot_locker(snapshot._lock);
   reset();
-  _baselined = baseline_malloc_summary(snapshot._alloc_ptrs) &&
-               baseline_vm_summary(snapshot._vm_ptrs);
+  _baselined = baseline_malloc_summary(snapshot._alloc_ptrs);
+  if (_baselined) {
+    check_safepoint((JavaThread*)THREAD);
+    _baselined = baseline_vm_summary(snapshot._vm_ptrs);
+  }
   _number_of_classes = snapshot.number_of_classes();
 
   if (!summary_only && MemTracker::track_callsite() && _baselined) {
-    _baselined =  baseline_malloc_details(snapshot._alloc_ptrs) &&
-      baseline_vm_details(snapshot._vm_ptrs);
+    check_safepoint((JavaThread*)THREAD);
+    _baselined =  baseline_malloc_details(snapshot._alloc_ptrs);
+    if (_baselined) {
+      check_safepoint((JavaThread*)THREAD);
+      _baselined =  baseline_vm_details(snapshot._vm_ptrs);
   }
+  }
   return _baselined;
 }
 
 
 int MemBaseline::flag2index(MEMFLAGS flag) const {