hotspot/src/share/vm/gc_implementation/shared/concurrentGCThread.cpp
changeset 24094 5dbf1f44de18
parent 22758 c6b6abb73544
child 25477 7dad9f95fd31
equal deleted inserted replaced
24093:095cc0a63ed9 24094:5dbf1f44de18
    35 
    35 
    36 // CopyrightVersion 1.2
    36 // CopyrightVersion 1.2
    37 
    37 
    38 int  ConcurrentGCThread::_CGC_flag            = CGC_nil;
    38 int  ConcurrentGCThread::_CGC_flag            = CGC_nil;
    39 
    39 
    40 SuspendibleThreadSet ConcurrentGCThread::_sts;
       
    41 
       
    42 ConcurrentGCThread::ConcurrentGCThread() :
    40 ConcurrentGCThread::ConcurrentGCThread() :
    43   _should_terminate(false), _has_terminated(false) {
    41   _should_terminate(false), _has_terminated(false) {
    44   _sts.initialize();
       
    45 };
    42 };
    46 
       
    47 void ConcurrentGCThread::safepoint_synchronize() {
       
    48   _sts.suspend_all();
       
    49 }
       
    50 
       
    51 void ConcurrentGCThread::safepoint_desynchronize() {
       
    52   _sts.resume_all();
       
    53 }
       
    54 
    43 
    55 void ConcurrentGCThread::create_and_start() {
    44 void ConcurrentGCThread::create_and_start() {
    56   if (os::create_thread(this, os::cgc_thread)) {
    45   if (os::create_thread(this, os::cgc_thread)) {
    57     // XXX: need to set this to low priority
    46     // XXX: need to set this to low priority
    58     // unless "aggressive mode" set; priority
    47     // unless "aggressive mode" set; priority
    88     Terminator_lock->notify();
    77     Terminator_lock->notify();
    89   }
    78   }
    90 
    79 
    91   // Thread destructor usually does this..
    80   // Thread destructor usually does this..
    92   ThreadLocalStorage::set_thread(NULL);
    81   ThreadLocalStorage::set_thread(NULL);
    93 }
       
    94 
       
    95 
       
    96 void SuspendibleThreadSet::initialize_work() {
       
    97   MutexLocker x(STS_init_lock);
       
    98   if (!_initialized) {
       
    99     _m             = new Monitor(Mutex::leaf,
       
   100                                  "SuspendibleThreadSetLock", true);
       
   101     _async         = 0;
       
   102     _async_stop    = false;
       
   103     _async_stopped = 0;
       
   104     _initialized   = true;
       
   105   }
       
   106 }
       
   107 
       
   108 void SuspendibleThreadSet::join() {
       
   109   initialize();
       
   110   MutexLockerEx x(_m, Mutex::_no_safepoint_check_flag);
       
   111   while (_async_stop) _m->wait(Mutex::_no_safepoint_check_flag);
       
   112   _async++;
       
   113   assert(_async > 0, "Huh.");
       
   114 }
       
   115 
       
   116 void SuspendibleThreadSet::leave() {
       
   117   assert(_initialized, "Must be initialized.");
       
   118   MutexLockerEx x(_m, Mutex::_no_safepoint_check_flag);
       
   119   _async--;
       
   120   assert(_async >= 0, "Huh.");
       
   121   if (_async_stop) _m->notify_all();
       
   122 }
       
   123 
       
   124 void SuspendibleThreadSet::yield(const char* id) {
       
   125   assert(_initialized, "Must be initialized.");
       
   126   if (_async_stop) {
       
   127     MutexLockerEx x(_m, Mutex::_no_safepoint_check_flag);
       
   128     if (_async_stop) {
       
   129       _async_stopped++;
       
   130       assert(_async_stopped > 0, "Huh.");
       
   131       if (_async_stopped == _async) {
       
   132         if (ConcGCYieldTimeout > 0) {
       
   133           double now = os::elapsedTime();
       
   134           guarantee((now - _suspend_all_start) * 1000.0 <
       
   135                     (double)ConcGCYieldTimeout,
       
   136                     "Long delay; whodunit?");
       
   137         }
       
   138       }
       
   139       _m->notify_all();
       
   140       while (_async_stop) _m->wait(Mutex::_no_safepoint_check_flag);
       
   141       _async_stopped--;
       
   142       assert(_async >= 0, "Huh");
       
   143       _m->notify_all();
       
   144     }
       
   145   }
       
   146 }
       
   147 
       
   148 void SuspendibleThreadSet::suspend_all() {
       
   149   initialize();  // If necessary.
       
   150   if (ConcGCYieldTimeout > 0) {
       
   151     _suspend_all_start = os::elapsedTime();
       
   152   }
       
   153   MutexLockerEx x(_m, Mutex::_no_safepoint_check_flag);
       
   154   assert(!_async_stop, "Only one at a time.");
       
   155   _async_stop = true;
       
   156   while (_async_stopped < _async) _m->wait(Mutex::_no_safepoint_check_flag);
       
   157 }
       
   158 
       
   159 void SuspendibleThreadSet::resume_all() {
       
   160   assert(_initialized, "Must be initialized.");
       
   161   MutexLockerEx x(_m, Mutex::_no_safepoint_check_flag);
       
   162   assert(_async_stopped == _async, "Huh.");
       
   163   _async_stop = false;
       
   164   _m->notify_all();
       
   165 }
    82 }
   166 
    83 
   167 static void _sltLoop(JavaThread* thread, TRAPS) {
    84 static void _sltLoop(JavaThread* thread, TRAPS) {
   168   SurrogateLockerThread* slt = (SurrogateLockerThread*)thread;
    85   SurrogateLockerThread* slt = (SurrogateLockerThread*)thread;
   169   slt->loop();
    86   slt->loop();
   281       _monitor.notify();
   198       _monitor.notify();
   282     }
   199     }
   283   }
   200   }
   284   assert(!_monitor.owned_by_self(), "Should unlock before exit.");
   201   assert(!_monitor.owned_by_self(), "Should unlock before exit.");
   285 }
   202 }
   286 
       
   287 
       
   288 // ===== STS Access From Outside CGCT =====
       
   289 
       
   290 void ConcurrentGCThread::stsYield(const char* id) {
       
   291   assert( Thread::current()->is_ConcurrentGC_thread(),
       
   292           "only a conc GC thread can call this" );
       
   293   _sts.yield(id);
       
   294 }
       
   295 
       
   296 bool ConcurrentGCThread::stsShouldYield() {
       
   297   assert( Thread::current()->is_ConcurrentGC_thread(),
       
   298           "only a conc GC thread can call this" );
       
   299   return _sts.should_yield();
       
   300 }
       
   301 
       
   302 void ConcurrentGCThread::stsJoin() {
       
   303   assert( Thread::current()->is_ConcurrentGC_thread(),
       
   304           "only a conc GC thread can call this" );
       
   305   _sts.join();
       
   306 }
       
   307 
       
   308 void ConcurrentGCThread::stsLeave() {
       
   309   assert( Thread::current()->is_ConcurrentGC_thread(),
       
   310           "only a conc GC thread can call this" );
       
   311   _sts.leave();
       
   312 }