src/share/vm/memory/gcLocker.cpp

Print this page




 105   while ((needs_gc() && is_jni_active()) || _doing_gc) {
 106     JNICritical_lock->wait();
 107   }
 108   thread->enter_critical();
 109   _jni_lock_count++;
 110   increment_debug_jni_lock_count();
 111 }
 112 
 113 void GC_locker::jni_unlock(JavaThread* thread) {
 114   assert(thread->in_last_critical(), "should be exiting critical region");
 115   MutexLocker mu(JNICritical_lock);
 116   _jni_lock_count--;
 117   decrement_debug_jni_lock_count();
 118   thread->exit_critical();
 119   if (needs_gc() && !is_jni_active()) {
 120     // We're the last thread out. Cause a GC to occur.
 121     // GC will also check is_active, so this check is not
 122     // strictly needed. It's added here to make it clear that
 123     // the GC will NOT be performed if any other caller
 124     // of GC_locker::lock() still needs GC locked.
 125     if (!is_active()) {
 126       _doing_gc = true;
 127       {
 128         // Must give up the lock while at a safepoint
 129         MutexUnlocker munlock(JNICritical_lock);
 130         if (PrintJNIGCStalls && PrintGCDetails) {
 131           ResourceMark rm; // JavaThread::name() allocates to convert to UTF8
 132           gclog_or_tty->print_cr("%.3f: Thread \"%s\" is performing GC after exiting critical section, %d locked",
 133                                  gclog_or_tty->time_stamp().seconds(), Thread::current()->name(), _jni_lock_count);
 134         }
 135         Universe::heap()->collect(GCCause::_gc_locker);
 136       }
 137       _doing_gc = false;
 138     }
 139 
 140     _needs_gc = false;
 141     JNICritical_lock->notify_all();
 142   }
 143 }
 144 
 145 // Implementation of No_GC_Verifier




 105   while ((needs_gc() && is_jni_active()) || _doing_gc) {
 106     JNICritical_lock->wait();
 107   }
 108   thread->enter_critical();
 109   _jni_lock_count++;
 110   increment_debug_jni_lock_count();
 111 }
 112 
 113 void GC_locker::jni_unlock(JavaThread* thread) {
 114   assert(thread->in_last_critical(), "should be exiting critical region");
 115   MutexLocker mu(JNICritical_lock);
 116   _jni_lock_count--;
 117   decrement_debug_jni_lock_count();
 118   thread->exit_critical();
 119   if (needs_gc() && !is_jni_active()) {
 120     // We're the last thread out. Cause a GC to occur.
 121     // GC will also check is_active, so this check is not
 122     // strictly needed. It's added here to make it clear that
 123     // the GC will NOT be performed if any other caller
 124     // of GC_locker::lock() still needs GC locked.
 125     if (!is_active_internal()) {
 126       _doing_gc = true;
 127       {
 128         // Must give up the lock while at a safepoint
 129         MutexUnlocker munlock(JNICritical_lock);
 130         if (PrintJNIGCStalls && PrintGCDetails) {
 131           ResourceMark rm; // JavaThread::name() allocates to convert to UTF8
 132           gclog_or_tty->print_cr("%.3f: Thread \"%s\" is performing GC after exiting critical section, %d locked",
 133                                  gclog_or_tty->time_stamp().seconds(), Thread::current()->name(), _jni_lock_count);
 134         }
 135         Universe::heap()->collect(GCCause::_gc_locker);
 136       }
 137       _doing_gc = false;
 138     }
 139 
 140     _needs_gc = false;
 141     JNICritical_lock->notify_all();
 142   }
 143 }
 144 
 145 // Implementation of No_GC_Verifier