if (VM.VerifyAssertions) VM.assert(isActive);
if (VM.VerifyAssertions) VM._assert(isActive);
  public void run() {    //  make sure Opt compiler does not compile this method    //  references stored in registers by the opt compiler will not be relocated by GC    VM_Magic.pragmaNoOptCompile();        while (true)      {	// suspend this thread: it will resume when scheduled by VM_Handshake.initiateCollection()	//	VM_Scheduler.collectorMutex.lock();	VM_Thread.getCurrentThread().yield(VM_Scheduler.collectorQueue, VM_Scheduler.collectorMutex);		// When we wake up here, we have been tapped on the shoulder to perform the next collection		VM_Processor p = VM_Processor.getCurrentProcessor();	p.disableThreadSwitching(); // block mutators		double startTime;	if (TIME_PAUSES) startTime = VM_Time.now();		p.localEpoch = VM_Scheduler.globalEpoch;		if (VM.VerifyAssertions) VM.assert(isActive);		if (trace) VM_Scheduler.trace("VM_RCCollectorThread", "starting collection");		VM_Allocator.collect();     // PERFORM GARBAGE COLLECTION TASKS		if (trace) VM_Scheduler.trace("VM_RCCollectorThread", "finished collection");		if (TIME_PAUSES) {	  double pauseTime = VM_Time.now() - startTime;	  if (VM_Scheduler.numProcessors > 1 && p.id != VM_Scheduler.numProcessors) {	    pauseTimeTotal += pauseTime;	    if (pauseTime > pauseTimeMax) pauseTimeMax = pauseTime;	    pauseCount++;	  }	  else {	    collectTimeTotal += pauseTime;	    if (pauseTime > collectTimeMax) collectTimeMax = pauseTime;	    collectCount++;	  }	  if (PRINT_PAUSES) {	    VM.sysWrite("||||  Pause time for CPU ");  VM.sysWrite(p.id, false);	    VM.sysWrite(" epoch ");  		         VM.sysWrite(p.localEpoch, false);	    VM.sysWrite(": ");  			 VM.sysWrite((int)(pauseTime*1000000.0), false);	    VM.sysWrite(" usec\n");	  }	}		// wake up the collector thread on next processor (if there is any)	// and yield so that mutator can run on this processor	//	if (p.id == VM_Scheduler.numProcessors)   // this proc is the last proc	  {	    collectionCount += 1;	    while (!VM_Scheduler.gcWaitQueue.isEmpty()) {	      VM_Thread t = VM_Scheduler.gcWaitQueue.dequeue();	      if (t.processorAffinity != null)		t.processorAffinity.scheduleThread(t); // should this be transferThread???	      else {		t.dump();		VM.assert(false);	      }	    }	    collect.notifyCompletion();        // notify mutators waiting on previous handshake object	    collect = new VM_RCHandshake();    // replace handshake with new one for next collection	    VM_Allocator.gcInProgress = false;	    if (trace) VM_Scheduler.trace("VM_RCCollectorThread", "ending last gc ");	  }	else 	  {	    VM_Scheduler.collectorMutex.lock();	    VM_Scheduler.processors[p.id + 1].scheduleThread(VM_Scheduler.collectorQueue.dequeue(p.id + 1));	    VM_Scheduler.collectorMutex.unlock();	    if (trace) VM_Scheduler.trace("VM_RCCollectorThread", "woke up the next proc");	  }		VM_Processor.getCurrentProcessor().enableThreadSwitching();  // resume normal scheduling      }      }  // run