int32_t OSSim::eventResume(Pid_t cpid, Pid_t pid) { LOG("OSSim::resume(%d,%d)", cpid, pid); ProcessId *proc = ProcessId::getProcessId(pid); if( proc == 0 ) { LOG("OSSim::resume(%d,%d) non existing process???", cpid, pid); return 0; } // Decrement the suspend counter proc->decSuspendedCounter(); // If process is in SuspendedState if(proc->getState()==SuspendedState) { // If the suspend count is not positive if(proc->getSuspendedCounter()<=0) { // Make the process runnable proc->setState(InvalidState); cpus.makeRunnable(proc); } return 1; } else { I(0); LOG("OSSim::resume(%d,%d) OOO suspend/resume (%d)", cpid, pid, proc->getSuspendedCounter()); } return 0; }
int32_t OSSim::eventSuspend(Pid_t cpid, Pid_t pid) { LOG("OSSim::suspend(%d) Received from pid %d",pid,cpid); ProcessId *proc = ProcessId::getProcessId(pid); if( proc == 0 ) { LOG("OSSim::suspend(%d) non existing process???", pid); return 0; } // Increment the suspend counter proc->incSuspendedCounter(); // Check if process already suspended if(proc->getState()==SuspendedState) { I(0); LOG("OSSim::suspend(%d) already suspended (recursive=%d)" , pid, proc->getSuspendedCounter()); return 0; } // The process should be ready or running I((proc->getState()==ReadyState)||(proc->getState()==RunningState)); // Need to suspend only if suspended counter is positive if(proc->getSuspendedCounter()>0) { // The process is no longer runnable cpus.makeNonRunnable(proc); // Set the state to SuspendedState proc->setState(SuspendedState); } else { I(0); LOG("OSSim::suspend(%d,%d) OOO suspend/resume (%d)", cpid, pid, proc->getSuspendedCounter()); } return 1; }
Pid_t OSSim::contextSwitch(CPU_t cpu, Pid_t nPid) { // This is the process we displaced to run the target process Pid_t oldPid=-1; ProcessId *newProc = ProcessId::getProcessId(nPid); I(newProc); GProcessor *newCore=cpus.getProcessor(cpu); I(newCore); // Get the cpu where the target process is already running CPU_t runCpu=(newProc->getState()==RunningState)?newProc->getCPU():-1; // If already running on the target processor, do nothing if(runCpu==cpu) return -1; // If target core has no available flows, make one if(!newCore->availableFlows()) { oldPid=newCore->findVictimPid(); ProcessId *oldProc=ProcessId::getProcessId(oldPid); cpus.switchOut(cpu, oldProc); } // Is the target process already running on another cpu? if(runCpu!=-1) { // Get another process to run on original cpu ProcessId *repProc=ProcessId::queueGet(runCpu); // Get the target process out of old core cpus.switchOut(runCpu, newProc); // Get the replacement process (if any) into the old core if(repProc) cpus.switchIn(runCpu,repProc); // Get the target process in the target cpu cpus.switchIn(cpu, newProc); } else { // If new process not ready, make it ready if(newProc->getState()!=ReadyState) { // Make it prefer the target cpu newProc->setCPU(cpu); // Make it ready newProc->setState(InvalidState); cpus.makeRunnable(newProc); // The target cpu is prefered by the target process, and // the target cpu has available flows. Thus, the target // process should be now running on the target cpu I(newProc->getCPU()==cpu); I(newProc->getState()==RunningState); } else { // The new process is already ready, just switch it in cpus.switchIn(cpu,newProc); } } return oldPid; }
void OSSim::eventWait(Pid_t cpid) { // All the threads have already finished if(cpid<0) return; LOG("OSSim::wait (cpid %d)", cpid); ProcessId *proc = ProcessId::getProcessId(cpid); if(proc->getNChilds()==0) { // No child pending return; } // Should be still running I(proc->getState()==RunningState); // Make it non-runnable cpus.makeNonRunnable(proc); // Set state to WaitingState proc->setState(WaitingState); }
void OSSim::tryWakeupParent(Pid_t cpid) { ProcessId *proc = ProcessId::getProcessId(cpid); I(proc); Pid_t ppid = proc->getPPid(); if (ppid < 0) return; ProcessId *pproc = ProcessId::getProcessId(ppid); // Does the parent process still exist? if(pproc == 0) return; if(pproc->getState()==WaitingState) { LOG("Waiting pid(%d) is awaked (child %d call)",ppid,cpid); pproc->setState(InvalidState); cpus.makeRunnable(pproc); } }