//This function terminates a PCB void TerminateProcess(struct Process_Control_Block *PCB) { //check if PCB passed into, and terminate only if not NULL if (PCB != NULL) { //set PCB state PCB->ProcessState = PCB_STATE_TERMINATE; pcbTable->Terminated_Number += 1; //terminate if more than one runnable PCBs, otherwise halt if (PCBLiveNumber() >= 1) { //do more actions when terminating current PCB if (PCB == CurrentPCB()) { //if uniprocessor, start a new PCB if (ProcessorMode == Uniprocessor) { Dispatcher(); } //if multiprocessor, suspend itself else { OSSuspendCurrentProcess(); } } } else { HaltProcess(); } } }
bool PhysicsEngine::Init(double dGravity, double dTimeStep, double nMaxSubSteps){ timestep_ = dTimeStep; gravity_acc_ = dGravity; time_max_substeps_ = nMaxSubSteps; // Physics stuff // See http://bulletphysics.org/mediawiki-1.5.8/index.php/Hello_World std::shared_ptr<btCollisionDispatcher> Dispatcher( new btCollisionDispatcher(&collision_configuration_) ); bt_dispatcher_ = Dispatcher; std::shared_ptr<btDbvtBroadphase> Broadphase( new btDbvtBroadphase ); bt_broadphase_ = Broadphase; std::shared_ptr<btSequentialImpulseConstraintSolver> Solver( new btSequentialImpulseConstraintSolver ); bt_solver_ = Solver; std::shared_ptr<btDiscreteDynamicsWorld> DWorld( new btDiscreteDynamicsWorld(bt_dispatcher_.get(), bt_broadphase_.get(), bt_solver_.get(), &collision_configuration_) ); dynamics_world_ = DWorld; dynamics_world_->setGravity( btVector3(0, 0, gravity_acc_) ); dynamics_world_->setDebugDrawer( &debug_drawer_ ); dynamics_world_->getDebugDrawer()-> setDebugMode(btIDebugDraw::DBG_DrawWireframe + btIDebugDraw::DBG_FastWireframe + btIDebugDraw::DBG_DrawConstraints); vehicle_raycaster_ = new btDefaultVehicleRaycaster(dynamics_world_.get()); return true; }
void EditBoxCollection::SendKey(const char *key) { KeyInfo k; k.skey = shIsCtrl; strcpy(k.KeyName, key); Dispatcher(k); }
void makeCurrentToWaitingMegPCB(INT32 process_id, INT32 *error_ptr) { if(process_id == -1) { { makeWaitngMegPCBToS = current_PCB_PTR; addToWaitingMegPCBQ(makeWaitngMegPCBToS); *error_ptr = ERR_SUCCESS; Dispatcher(); } } }
//This function suspends a PCB void SuspendProcess(struct Process_Control_Block *PCB) { //check input PCB, suspend only if it's not NULL if (PCB != NULL) { //suspend only if there're other PCBs alive if (PCBLiveNumber() > 1) { //set PCB state PCB->ProcessState = PCB_STATE_SUSPEND; pcbTable->Suspended_Number += 1; //if suspend current PCB, start a new one if (PCB == CurrentPCB()) { Dispatcher(); } } } }
void os_suspend_process(INT32 process_id, INT32 *error_ptr) { if(process_id == -1) { if((timerHead == NULL && readyHead == NULL)) { *error_ptr = ERROR; printf("Suspend the Only Process.\n"); } else { makeSuspend = current_PCB_PTR; lockSuspend(); addToSuspendQ(makeSuspend); unlockSuspend(); *error_ptr = ERR_SUCCESS; Dispatcher(); } } else if(process_id != -1) { makeReadyToSuspend(process_id,error_ptr); if(*error_ptr != ERROR) { schedular_printer(SUSPEND); addToSuspendQ(makeSuspend); *error_ptr = ERR_SUCCESS; } } { makeWaitngMegPCBToSuspend(process_id,error_ptr); if(*error_ptr != ERROR) { schedular_printer(SUSPEND); makeWaitngMegPCBToS->p_meg_status = CHANGE; addToSuspendQ(makeWaitngMegPCBToS); change_waiting_meg_status(makeWaitngMegPCBToS->p_id); *error_ptr = ERR_SUCCESS; } } }
void rr::CallDispatcher() { Dispatcher(); }
bool blinkDashLight(Task*) { if (!Dispatcher().isEnabled()) { // Only send light if not enabled Frame dashMessage = { .id=VCU_ID, .body={BLINK_LIGHT}, .len=1}; CAN().write(dashMessage); }
bool requestPermanentUpdatesRight(Task*) { Dispatcher().requestRightMotorUpdates(); return false; }
// Request message from both motors void requestMotorHeartbeat(Task*) { Dispatcher().requestMotorHeartbeat(); }
void osInit(int argc, char *argv[]) { INT32 i; MEMORY_MAPPED_IO mmio; long a; long b; long* arg0=(long*)"test2a"; //default ruuning test long* arg1=(long*)test2a; long* arg2=(long*)10; long* arg3=& a; long* arg4=& b; // Demonstrates how calling arguments are passed thru to here printf( "Program called with %d arguments:", argc ); for ( i = 0; i < argc; i++ ) printf( " %s", argv[i] ); printf( "\n" ); printf( "Calling with argument 'sample' executes the sample program.\n" ); // Here we check if a second argument is present on the command line. // If so, run in multiprocessor mode if ( argc > 2 ){ printf("Simulation is running as a MultProcessor\n\n"); mmio.Mode = Z502SetProcessorNumber; mmio.Field1 = MAX_NUMBER_OF_PROCESSORS; mmio.Field2 = (long) 0; mmio.Field3 = (long) 0; mmio.Field4 = (long) 0; MEM_WRITE(Z502Processor, &mmio); // Set the number of processors } else { printf("Simulation is running as a UniProcessor\n"); printf("Add an 'M' to the command line to invoke multiprocessor operation.\n\n"); } // Setup so handlers will come to code in base.c TO_VECTOR[TO_VECTOR_INT_HANDLER_ADDR ] = (void *) InterruptHandler; TO_VECTOR[TO_VECTOR_FAULT_HANDLER_ADDR ] = (void *) FaultHandler; TO_VECTOR[TO_VECTOR_TRAP_HANDLER_ADDR ] = (void *) svc; if((argc > 1) && (strcmp(argv[1], "test1a") == 0)){ arg0=(long*)"test1a"; arg1=(long*)test1a; OSCreateProcess(arg0,arg1,arg2,arg3,arg4); Dispatcher(); } if((argc > 1) && (strcmp(argv[1], "test1b") == 0)){ arg0=(long*)"test1b"; arg1=(long*)test1b; OSCreateProcess(arg0,arg1,arg2,arg3,arg4); Dispatcher(); } if((argc > 1) && (strcmp(argv[1], "test1c") == 0)){ arg0=(long*)"test1c"; arg1=(long*)test1c; OSCreateProcess(arg0,arg1,arg2,arg3,arg4); Dispatcher(); } if((argc > 1) && (strcmp(argv[1], "test1d") == 0)){ arg0=(long*)"test1d"; arg1=(long*)test1d; OSCreateProcess(arg0,arg1,arg2,arg3,arg4); Dispatcher(); } if((argc > 1) && (strcmp(argv[1], "test1e") == 0)){ arg0=(long*)"test1e"; arg1=(long*)test1e; OSCreateProcess(arg0,arg1,arg2,arg3,arg4); Dispatcher(); } if((argc > 1) && (strcmp(argv[1], "test1f") == 0)){ arg0=(long*)"test1f"; arg1=(long*)test1f; OSCreateProcess(arg0,arg1,arg2,arg3,arg4); Dispatcher(); } if((argc > 1) && (strcmp(argv[1], "test1g") == 0)){ arg0=(long*)"test1g"; arg1=(long*)test1g; OSCreateProcess(arg0,arg1,arg2,arg3,arg4); Dispatcher(); } if((argc > 1) && (strcmp(argv[1], "test1h") == 0)){ arg0=(long*)"test1h"; arg1=(long*)test1h; OSCreateProcess(arg0,arg1,arg2,arg3,arg4); Dispatcher(); } if((argc > 1) && (strcmp(argv[1], "test1i") == 0)){ arg0=(long*)"test1i"; arg1=(long*)test1i; OSCreateProcess(arg0,arg1,arg2,arg3,arg4); Dispatcher(); } if((argc > 1) && (strcmp(argv[1], "test1j") == 0)){ arg0=(long*)"test1j"; arg1=(long*)test1j; OSCreateProcess(arg0,arg1,arg2,arg3,arg4); Dispatcher(); } if((argc > 1) && (strcmp(argv[1], "test1k") == 0)){ arg0=(long*)"test1k"; arg1=(long*)test1k; OSCreateProcess(arg0,arg1,arg2,arg3,arg4); Dispatcher(); } /*project2*/ if((argc > 1) && (strcmp(argv[1], "test2a") == 0)){ arg0=(long*)"test2a"; arg1=(long*)test2a; OSCreateProcess(arg0,arg1,arg2,arg3,arg4); Dispatcher(); } if((argc > 1) && (strcmp(argv[1], "test2b") == 0)){ arg0=(long*)"test2b"; arg1=(long*)test2b; OSCreateProcess(arg0,arg1,arg2,arg3,arg4); Dispatcher(); } if((argc > 1) && (strcmp(argv[1], "test2c") == 0)){ arg0=(long*)"test2c"; arg1=(long*)test2c; OSCreateProcess(arg0,arg1,arg2,arg3,arg4); Dispatcher(); } if((argc > 1) && (strcmp(argv[1], "test2d") == 0)){ arg0=(long*)"test2d"; arg1=(long*)test2d; OSCreateProcess(arg0,arg1,arg2,arg3,arg4); Dispatcher(); } if((argc > 1) && (strcmp(argv[1], "test2e") == 0)){ arg0=(long*)"test2e"; arg1=(long*)test2e; OSCreateProcess(arg0,arg1,arg2,arg3,arg4); Dispatcher(); } if((argc > 1) && (strcmp(argv[1], "test2f") == 0)){ arg0=(long*)"test2f"; arg1=(long*)test2f; OSCreateProcess(arg0,arg1,arg2,arg3,arg4); Dispatcher(); } if((argc > 1) && (strcmp(argv[1], "test2g") == 0)){ arg0=(long*)"test2g"; arg1=(long*)test2g; OSCreateProcess(arg0,arg1,arg2,arg3,arg4); Dispatcher(); } if((argc > 1) && (strcmp(argv[1], "test2h") == 0)){ arg0=(long*)"test2h"; arg1=(long*)test2h; OSCreateProcess(arg0,arg1,arg2,arg3,arg4); Dispatcher(); } else{ OSCreateProcess(arg0,arg1,arg2,arg3,arg4); Dispatcher(); } } // End of osInit
void svc(SYSTEM_CALL_DATA *SystemCallData) { short call_type; static short do_print = 10; short i; INT32 Time; int Status; void *PageTable; char* processName; MEMORY_MAPPED_IO mmio; call_type = (short) SystemCallData->SystemCallNumber; if (do_print > 0) { printf("SVC handler: %s\n", call_names[call_type]); for (i = 0; i < SystemCallData->NumberOfArguments - 1; i++) { //Value = (long)*SystemCallData->Argument[i]; printf("Arg %d: Contents = (Decimal) %8ld, (Hex) %8lX\n", i, (unsigned long) SystemCallData->Argument[i], (unsigned long) SystemCallData->Argument[i]); } do_print--; } // printf((char *) SystemCallData->Argument[i]); switch (call_type) { //get time service call case SYSNUM_GET_TIME_OF_DAY: mmio.Mode = Z502ReturnValue; mmio.Field1 = mmio.Field2 = mmio.Field3 = 0; MEM_READ(Z502Clock, &mmio); *(long *) SystemCallData->Argument[0] = mmio.Field1; break; //system sleep call case SYSNUM_SLEEP: mmio.Mode = Z502ReturnValue; mmio.Field1 = mmio.Field2 = mmio.Field3 = 0; MEM_READ(Z502Clock, &mmio); Time = (long) SystemCallData->Argument[0]; pcb = FindCurrent(runningProcessPid); pcb->wakeUpTimer = Time; EnTimerQueue(&pcb_timer_queue, pcb); //start timer headPCB = GetHead(&pcb_timer_queue)->data; if (pcb == headPCB) { mmio.Mode = Z502Start; mmio.Field1 = (long) SystemCallData->Argument[0]; mmio.Field2 = mmio.Field3 = 0; MEM_WRITE(Z502Timer, &mmio); } Dispatcher(); break; //system create process case SYSNUM_CREATE_PROCESS: if ((long) SystemCallData->Argument[2] < 0) { *SystemCallData->Argument[4] = ERR_BAD_PARAM; } else { PageTable = (void *) calloc(2, NUMBER_VIRTUAL_PAGES); mmio.Mode = Z502InitializeContext; mmio.Field1 = 0; mmio.Field2 = (long) SystemCallData->Argument[1]; mmio.Field3 = (long) PageTable; MEM_WRITE(Z502Context, &mmio); pcb = OSCreateProcess((char*) SystemCallData->Argument[0], (long) mmio.Field1, (long) SystemCallData->Argument[2], (long) SystemCallData->Argument[3], (long) SystemCallData->Argument[4]); if (pcb != NULL) { EnQueue(&pcb_ready_queue, (void*) pcb); *SystemCallData->Argument[3] = pcb->pid; *SystemCallData->Argument[4] = ERR_SUCCESS; } else { *SystemCallData->Argument[4] = ERR_BAD_PARAM; } } break; //system get process id case SYSNUM_GET_PROCESS_ID: processName = (char*) SystemCallData->Argument[0]; if (strlen(processName) == 0) { *SystemCallData->Argument[1] = runningProcessPid; *SystemCallData->Argument[2] = ERR_SUCCESS; } else { pcb = FindPCBByName(processName); } if (pcb != NULL) { *SystemCallData->Argument[1] = pcb->pid; *SystemCallData->Argument[2] = ERR_SUCCESS; } else { *SystemCallData->Argument[2] = ERR_BAD_PARAM; } break; case SYSNUM_PHYSICAL_DISK_READ: do { mmio.Mode = Z502Status; mmio.Field1 = (long) SystemCallData->Argument[0]; mmio.Field2 = mmio.Field3 = 0; MEM_READ(Z502Disk, &mmio); CALL(WasteTime()); } while (mmio.Field2 != DEVICE_FREE); pcb = FindCurrent(runningProcessPid); if (pcb != NULL) { pcb->diskID = (int) SystemCallData->Argument[0]; pcb->sectorID = (int) SystemCallData->Argument[1]; pcb->memoryBuffer = (void*) SystemCallData->Argument[2]; EnQueue(&(pcb_disk_queue[pcb->diskID]), (void*) pcb); } mmio.Mode = Z502DiskRead; mmio.Field1 = (long) SystemCallData->Argument[0]; mmio.Field2 = (long) SystemCallData->Argument[1]; mmio.Field3 = (long) SystemCallData->Argument[2]; mmio.Field4 = 0; MEM_READ(Z502Disk, &mmio); do { mmio.Mode = Z502Status; mmio.Field1 = (long) SystemCallData->Argument[0]; mmio.Field2 = mmio.Field3 = 0; MEM_READ(Z502Disk, &mmio); CALL(WasteTime()); } while (mmio.Field2 != DEVICE_FREE); Dispatcher(); break; case SYSNUM_PHYSICAL_DISK_WRITE: do { mmio.Mode = Z502Status; mmio.Field1 = (long) SystemCallData->Argument[0]; mmio.Field2 = mmio.Field3 = 0; MEM_READ(Z502Disk, &mmio); CALL(WasteTime()); } while (mmio.Field2 != DEVICE_FREE); pcb = FindCurrent(runningProcessPid); if (pcb != NULL) { pcb->diskID = (int) SystemCallData->Argument[0]; pcb->sectorID = (int) SystemCallData->Argument[1]; pcb->memoryBuffer = (void*) SystemCallData->Argument[2]; EnQueue(&(pcb_disk_queue[pcb->diskID]), (void*) pcb); } mmio.Mode = Z502DiskWrite; mmio.Field1 = (long) SystemCallData->Argument[0]; mmio.Field2 = (long) SystemCallData->Argument[1]; mmio.Field3 = (long) SystemCallData->Argument[2]; MEM_WRITE(Z502Disk, &mmio); // mmio.Mode = Z502Action; // mmio.Field1 = mmio.Field2 = mmio.Field3 = 0; // MEM_WRITE(Z502Idle, &mmio); do { mmio.Mode = Z502Status; mmio.Field1 = (long) SystemCallData->Argument[0]; mmio.Field2 = mmio.Field3 = 0; MEM_READ(Z502Disk, &mmio); CALL(WasteTime()); } while (mmio.Field2 != DEVICE_FREE); Dispatcher(); break; //system terminate call case SYSNUM_TERMINATE_PROCESS: //If ProcessID = -1, then terminate self if ((long) SystemCallData->Argument[0] == -1) { pcb = FindCurrent(runningProcessPid); if (pcb != NULL) { // ReleasePCB(); // RemovePCB(&pcb_ready_queue,(void*)pcb); // RemovePCB(&pcb_timer_queue,(void*)pcb); // *SystemCallData->Argument[1] = ERR_SUCCESS; if (pcb_ready_queue.size == 0 && pcb_timer_queue.size == 0) { mmio.Mode = Z502ReturnValue; mmio.Field1 = mmio.Field2 = mmio.Field3 = mmio.Field4 = 0; MEM_WRITE(Z502Halt, &mmio); *SystemCallData->Argument[1] = ERR_SUCCESS; } else { Dispatcher(); } } else { ReleasePCB(); mmio.Mode = Z502ReturnValue; mmio.Field1 = mmio.Field2 = mmio.Field3 = mmio.Field4 = 0; MEM_WRITE(Z502Halt, &mmio); *SystemCallData->Argument[1] = ERR_SUCCESS; } } else if ((long) SystemCallData->Argument[0] == -2) { // terminite all halt ReleasePCB(); mmio.Mode = Z502ReturnValue; mmio.Field1 = mmio.Field2 = mmio.Field3 = mmio.Field4 = 0; MEM_WRITE(Z502Halt, &mmio); *SystemCallData->Argument[1] = ERR_SUCCESS; // pcb = FindCurrent(runningProcessPid); // RemovePCB(&pcb_ready_queue, (void*) pcb); // RemovePCB(&pcb_timer_queue, (void*) pcb); // RemovePCB(&pcb_ready_queue, (void*) pcb->childProcesses); // RemovePCB(&pcb_timer_queue, (void*) pcb->childProcesses); } else { pcb = FindPCBByPID(SystemCallData->Argument[0]); RemovePCB(&pcb_ready_queue, (void*) pcb); *SystemCallData->Argument[1] = ERR_SUCCESS; } break; defaut: printf("ERROR! call_type not recognized!\n"); printf("Call_type is %i\n", call_type); } } // End of svc
void osInit(int argc, char *argv[]) { void *PageTable = (void *) calloc(2, VIRTUAL_MEM_PAGES); INT32 i; MEMORY_MAPPED_IO mmio; //init Queues initPCBTable(); initTimerQueue(); initReadyQueue(); initMessageTable(); // Demonstrates how calling arguments are passed thru to here printf( "Program called with %d arguments:", argc ); for ( i = 0; i < argc; i++ ) printf( " %s", argv[i] ); printf( "\n" ); printf( "Calling with argument 'sample' executes the sample program.\n" ); // Here we check if a second argument is present on the command line. // If so, run in multiprocessor mode if ( argc > 2 ){ printf("Simulation is running as a MultProcessor\n\n"); mmio.Mode = Z502SetProcessorNumber; mmio.Field1 = MAX_NUMBER_OF_PROCESSORS; mmio.Field2 = (long) 0; mmio.Field3 = (long) 0; mmio.Field4 = (long) 0; MEM_WRITE(Z502Processor, &mmio); // Set the number of processors } else { printf("Simulation is running as a UniProcessor\n"); printf("Add an 'M' to the command line to invoke multiprocessor operation.\n\n"); } // Setup so handlers will come to code in base.c TO_VECTOR[TO_VECTOR_INT_HANDLER_ADDR ] = (void *) InterruptHandler; TO_VECTOR[TO_VECTOR_FAULT_HANDLER_ADDR ] = (void *) FaultHandler; TO_VECTOR[TO_VECTOR_TRAP_HANDLER_ADDR ] = (void *) svc; // Determine if the switch was set, and if so go to demo routine. PageTable = (void *) calloc(2, VIRTUAL_MEM_PAGES); if ((argc > 1) && (strcmp(argv[1], "sample") == 0)) { mmio.Mode = Z502InitializeContext; mmio.Field1 = 0; mmio.Field2 = (long) SampleCode; mmio.Field3 = (long) PageTable; MEM_WRITE(Z502Context, &mmio); // Start of Make Context Sequence mmio.Mode = Z502StartContext; // Field1 contains the value of the context returned in the last call mmio.Field2 = START_NEW_CONTEXT_AND_SUSPEND; MEM_WRITE(Z502Context, &mmio); // Start up the context } // End of handler for sample code - This routine should never return here /****************************Parse Input******************************/ long *TestToRun; switch (argc){ case 2: TestToRun = TestParser(argv[1]); ProcessorMode = Uniprocessor; break; case 3: TestToRun = TestParser(argv[1]); ProcessorMode = Multiprocessor; break; default: TestToRun = test1c; ProcessorMode = Uniprocessor; break; } /********************************************************************/ long ErrorReturned; long newPID; struct Process_Control_Block *newPCB = OSCreateProcess((long*)"test1", TestToRun, (long*)3, (long*)&newPID, (long*)&ErrorReturned); if (newPCB != NULL) { enPCBTable(newPCB); enReadyQueue(newPCB); } Dispatcher(); } // End of osInit
void svc(SYSTEM_CALL_DATA *SystemCallData) { short call_type; static short do_print = 10; short i; //for hardware interface MEMORY_MAPPED_IO mmio; //for GET_TIME_OF_DAY INT32 Temp_Clock; //for SLEEP long Sleep_Time; struct Process_Control_Block *sleepPCB; //for RESTART_PROCESS long PID_restart; struct Process_Control_Block *restartPCB; struct Process_Control_Block *recreatedPCB; //for CREATE_PROCESS struct Process_Control_Block *newPCB; //for TERMINATE_PROCESS long termPID; struct Process_Control_Block *termPCB; //for GET_PROCESS_ID int ReturnedPID; char* ProcessName; struct Process_Control_Block *PCBbyProcessName; //for SUSPEND_PROCESS int suspendPID; struct Process_Control_Block *suspendPCB; //for RESUME_PROCESS int resumePID; struct Process_Control_Block *resumePCB; //for CHANGE_PRIORITY int changePrioPID; struct Process_Control_Block *changePrioPCB; int newPriority; //for SEND_MESSAGE long TargetPID; char *MessageBuffer; long SendLength; struct Message *MessageCreated; long *ErrorReturned_SendMessage; //for RECEIVE_MESSAGE long SourcePID; char *ReceiveBuffer; long ReceiveLength; long *ActualSendLength; long *ActualSourcePID; long *ErrorReturned_ReceiveMessage; struct Process_Control_Block *Mess_PCB; call_type = (short) SystemCallData->SystemCallNumber; if (do_print > 0) { printf("SVC handler: %s\n", call_names[call_type]); for (i = 0; i < SystemCallData->NumberOfArguments - 1; i++) { //Value = (long)*SystemCallData->Argument[i]; printf("Arg %d: Contents = (Decimal) %8ld, (Hex) %8lX\n", i, (unsigned long) SystemCallData->Argument[i], (unsigned long) SystemCallData->Argument[i]); } do_print--; } switch (call_type) { //get and return current system time case SYSNUM_GET_TIME_OF_DAY: mmio.Mode = Z502ReturnValue; mmio.Field1 = mmio.Field2 = mmio.Field3 = 0; MEM_READ(Z502Clock, &mmio); Temp_Clock = mmio.Field1; *SystemCallData->Argument[0] = Temp_Clock; break; //create a new PCB and put it into pcb table and ready queue case SYSNUM_CREATE_PROCESS: //create a new PCB newPCB = OSCreateProcess(SystemCallData->Argument[0], SystemCallData->Argument[1], SystemCallData->Argument[2], SystemCallData->Argument[3], SystemCallData->Argument[4]); //if create successfully, put it into PCB table and ready queue if (newPCB != NULL) { SchedularPrinter("Create", newPCB->ProcessID);//print states enPCBTable(newPCB); enReadyQueue(newPCB); } break; //return PID regarding process name case SYSNUM_GET_PROCESS_ID: ProcessName = (char*)SystemCallData->Argument[0]; //if no input process name, return the current running PID if (strcmp(ProcessName, "") == 0) { PCBbyProcessName = CurrentPCB(); *SystemCallData->Argument[1] = PCBbyProcessName->ProcessID; *SystemCallData->Argument[2] = ERR_SUCCESS; } //find the PCB in PCB table and return PID if found else { PCBbyProcessName = findPCBbyProcessName(ProcessName); //if found, return PID if (PCBbyProcessName != NULL) { ReturnedPID = PCBbyProcessName->ProcessID; *SystemCallData->Argument[1] = ReturnedPID; *SystemCallData->Argument[2] = ERR_SUCCESS; } //if not found, return error else { *SystemCallData->Argument[2] = ERR_BAD_PARAM; } } break; //if a PCB wanna sleep, put itself into timer queue and start //a new PCB case SYSNUM_SLEEP: //print states SchedularPrinter("Sleep", CurrentPID()); //Calculate WakeUpTime for PCB Sleep_Time = (long)SystemCallData->Argument[0]; sleepPCB = CurrentPCB(); sleepPCB->WakeUpTime = CurrentTime() + Sleep_Time; //Put current running PCB into timer queue and reset time lockTimer(); enTimerQueue(sleepPCB); if (sleepPCB == timerQueue->First_Element->PCB){ SetTimer(Sleep_Time); } unlockTimer(); //in uniprocessor, start a new PCB //in multiprocessor, only suspend itself if (ProcessorMode == Uniprocessor) { //first PCB in Ready Queue starts Dispatcher(); } else { OSSuspendCurrentProcess(); } break; //restart a PCB by terminate itself and created a new PCB with everything the same except PID case SYSNUM_RESTART_PROCESS: //initial return error *SystemCallData->Argument[2] = ERR_BAD_PARAM; PID_restart = (long)SystemCallData->Argument[0]; //if not restart itself if (PID_restart != CurrentPID()){ //find restarted PCB restartPCB = findPCBbyProcessID(PID_restart); //if PCB found, terminate itself and create a new one if (restartPCB != NULL){ TerminateProcess(restartPCB); recreatedPCB = OSCreateProcess(restartPCB->ProcessName, restartPCB->TestToRun, restartPCB->Priority, SystemCallData->Argument[1], SystemCallData->Argument[2]); //if create successfully, put it into PCB table and ready queue if (recreatedPCB != NULL) { *SystemCallData->Argument[2] = ERR_SUCCESS; SchedularPrinter("Create", recreatedPCB->ProcessID);//print states enPCBTable(recreatedPCB); enReadyQueue(recreatedPCB); SchedularPrinter("Restart", restartPCB->ProcessID); } } else{ *SystemCallData->Argument[2] = ERR_BAD_PARAM; } } else{ *SystemCallData->Argument[2] = ERR_BAD_PARAM; } break; //terminate a process case SYSNUM_TERMINATE_PROCESS: termPID = (long)SystemCallData->Argument[0]; //if PID = -1, terminate current running PCB if (termPID == -1) { if (PCBLiveNumber() > 1) { *SystemCallData->Argument[1] = ERR_SUCCESS; //print states SchedularPrinter("Terminate", termPID); //terminate current PCB TerminateProcess(CurrentPCB()); } else { *SystemCallData->Argument[1] = ERR_SUCCESS; HaltProcess(); } } //if PID = -2, terminate OS if (termPID == -2) { *SystemCallData->Argument[1] = ERR_SUCCESS; HaltProcess(); } //if PID positive, terminate specified PID else { termPCB = findPCBbyProcessID((long)SystemCallData->Argument[0]); //if PCB found, terminate it if (termPCB != NULL) { *SystemCallData->Argument[1] = ERR_SUCCESS; //if more than one PCB alive, simply terminate it if (PCBLiveNumber() > 1) { //print states SchedularPrinter("Terminate", termPID); //terminate specified PCB TerminateProcess(termPCB); } //if last alive PCB, terminate OS else { HaltProcess(); } } else { *SystemCallData->Argument[1] = ERR_BAD_PARAM; } } break; //suspend a PCB, which can be resumed case SYSNUM_SUSPEND_PROCESS: suspendPID = (int)SystemCallData->Argument[0]; //if PID = -1, suspend current running PCB if (suspendPID == -1) { //if more than one PCB alive, suspend it if (PCBLiveNumber() > 1) { *SystemCallData->Argument[1] = ERR_SUCCESS; //print states SchedularPrinter("Suspend", suspendPID); //Suspend Current Process SuspendProcess(CurrentPCB()); } //if last one PCB alive, return error else { *SystemCallData->Argument[1] = ERR_BAD_PARAM; } } //if PID positive, suspend specified PCB else { suspendPCB = findPCBbyProcessID((int)suspendPID); //if PCB found if (suspendPCB != NULL) { //if more than one PCB alive, suspend it if (suspendPCB->ProcessState == PCB_STATE_LIVE && PCBLiveNumber() > 1) { *SystemCallData->Argument[1] = ERR_SUCCESS; //print states SchedularPrinter("Suspend", suspendPID); //Suspend specified process SuspendProcess(suspendPCB); } //if last one PCB alive, return error else { *SystemCallData->Argument[1] = ERR_BAD_PARAM; } } else { *SystemCallData->Argument[1] = ERR_BAD_PARAM; } } break; //resumes a previously suspended PCB case SYSNUM_RESUME_PROCESS: resumePID = (int)SystemCallData->Argument[0]; resumePCB = findPCBbyProcessID(resumePID); //if PCB found if (resumePCB != NULL) { //if PCB is previously suspended if (resumePCB->ProcessState == PCB_STATE_SUSPEND) { *SystemCallData->Argument[1] = ERR_SUCCESS; //print states SchedularPrinter("Resume", resumePID); //Resume specified process ResumeProcess(resumePCB); } else { *SystemCallData->Argument[1] = ERR_BAD_PARAM; } } else { *SystemCallData->Argument[1] = ERR_BAD_PARAM; } break; //change the priority of a PCB case SYSNUM_CHANGE_PRIORITY: changePrioPID = (int)SystemCallData->Argument[0]; changePrioPCB = findPCBbyProcessID((int)changePrioPID); newPriority = (int)SystemCallData->Argument[1]; //if legal priority if (newPriority<=40 && newPriority>=0) { if (changePrioPCB != NULL) { *SystemCallData->Argument[2] = ERR_SUCCESS; //print states printf("Before changing Priority\n"); SchedularPrinter("ChangePrio", changePrioPID); //if PCB in ready queue, change order in ready queue if (changePrioPCB->ProcessLocation == PCB_LOCATION_READY_QUEUE && newPriority != changePrioPCB->Priority) { changePrioPCB = deCertainPCBFromReadyQueue(changePrioPID); changePrioPCB->Priority = newPriority; enReadyQueue(changePrioPCB); } else { changePrioPCB->Priority = newPriority; } //print states printf("After changing Priority\n"); SchedularPrinter("ChangePrio", changePrioPID); } else { *SystemCallData->Argument[2] = ERR_BAD_PARAM; } } else { *SystemCallData->Argument[2] = ERR_BAD_PARAM; } break; //PCB stores a message in message table case SYSNUM_SEND_MESSAGE: TargetPID = (long)SystemCallData->Argument[0]; MessageBuffer = (char*)SystemCallData->Argument[1]; SendLength = (long)SystemCallData->Argument[2]; ErrorReturned_SendMessage = SystemCallData->Argument[3]; //create a message MessageCreated = CreateMessage(TargetPID, MessageBuffer, SendLength, ErrorReturned_SendMessage); //if successfully create a message, put it into message table if (MessageCreated != NULL) { SchedularPrinter("SendMsg", TargetPID); enMessageTable(MessageCreated); } break; //retrive a message in message table case SYSNUM_RECEIVE_MESSAGE: SourcePID = (long)SystemCallData->Argument[0]; ReceiveBuffer = (char*)SystemCallData->Argument[1]; ReceiveLength = (long)SystemCallData->Argument[2]; ActualSendLength = SystemCallData->Argument[3]; ActualSourcePID = SystemCallData->Argument[4]; ErrorReturned_ReceiveMessage = SystemCallData->Argument[5]; Mess_PCB = CurrentPCB(); Mess_PCB->ProcessState = PCB_STATE_MSG_SUSPEND; pcbTable->Msg_Suspended_Number += 1; //PCB kept suspended by sleep until find a message while (findMessage(SourcePID, ReceiveBuffer, ReceiveLength, ActualSendLength, ActualSourcePID, ErrorReturned_ReceiveMessage) == 0) { Mess_PCB->WakeUpTime = CurrentTime() + 10; //Put current running PCB into timer queue and reset time enTimerQueue(Mess_PCB); if (Mess_PCB == timerQueue->First_Element->PCB) { SetTimer(10); } //first PCB in Ready Queue starts Dispatcher(); } Mess_PCB->ProcessState = PCB_STATE_LIVE; pcbTable->Msg_Suspended_Number -= 1; SchedularPrinter("ReceiveMsg", CurrentPID()); break; default: printf("ERROR! call_type not recognized!\n"); printf("Call_type is - %i\n", call_type); } } // End of svc
void rr::on_StepSim_clicked() { if(CheckQValueBeforeStart()) Dispatcher(); }
/************************************************************************ INTERRUPT_HANDLER When the Z502 gets a hardware interrupt, it transfers control to this routine in the OS. ************************************************************************/ void InterruptHandler(void) { INT32 DeviceID; INT32 Status; INT32 ErrorState; INT32 CurrentTime; INT32 diskID; QueuePtr node; MEMORY_MAPPED_IO mmio; // Enables communication with hardware PCB* nextPcb; QueuePtr TEMPnode; QueuePtr TempDnode; static BOOL remove_this_in_your_code = TRUE; /** TEMP **/ static INT32 how_many_interrupt_entries = 0; /** TEMP **/ // Get cause of interrupt mmio.Mode = Z502GetInterruptInfo; mmio.Field1 = mmio.Field2 = mmio.Field3 = 0; MEM_READ(Z502InterruptDevice, &mmio); DeviceID = mmio.Field1; //diskid Status = mmio.Field2; ErrorState = mmio.Field4; mmio.Mode = Z502ReturnValue; mmio.Field1 = mmio.Field2 = mmio.Field3 = mmio.Field4 = 0; MEM_READ(Z502Clock, &mmio); CurrentTime = mmio.Field1; if (ErrorState == ERR_SUCCESS) { switch (DeviceID) { case TIMER_INTERRUPT : node = DeQueue(&pcb_timer_queue); if(node == NULL){ Dispatcher(); } else{ PCB* pcb = (PCB*) node->data; if (pcb != NULL) { EnQueue(&(pcb_ready_queue), (void*) pcb); } TEMPnode = GetHead(&pcb_timer_queue); if (TEMPnode != NULL) { nextPcb = TEMPnode->data; if (nextPcb->wakeUpTimer > CurrentTime) { mmio.Mode = Z502Start; mmio.Field1 = (long) (nextPcb->wakeUpTimer - CurrentTime); mmio.Field2 = mmio.Field3 = 0; MEM_WRITE(Z502Timer, &mmio); } else { node = DeQueue(&pcb_timer_queue); EnQueue(&pcb_ready_queue, (void*) node->data); } } } break; case DISK_INTERRUPT_DISK0 : case DISK_INTERRUPT_DISK1 : case DISK_INTERRUPT_DISK2 : case DISK_INTERRUPT_DISK3 : case DISK_INTERRUPT_DISK4 : case DISK_INTERRUPT_DISK5 : case DISK_INTERRUPT_DISK6 : case DISK_INTERRUPT_DISK7 : diskID = DeviceID - DISK_INTERRUPT; TempDnode = DeQueue(&pcb_disk_queue[diskID]); PCB* diskPCB = (PCB*) TempDnode->data; if (diskPCB != NULL) { EnQueue(&pcb_ready_queue, diskPCB); printf(""); } break; default: break; } } // if (ErrorState == ERR_BAD_PARAM) { // printf("Illegal disk ID or Illegal sector"); // } else if (ErrorState == ERR_NO_PREVIOUS_WRITE) { // printf("Reading form no previously written sector"); // } else if (ErrorState == ERR_DISK_IN_USE) { // printf("Disk in use"); // } // Clear out this device - we're done with it mmio.Mode = Z502ClearInterruptStatus; mmio.Field1 = DeviceID; mmio.Field2 = mmio.Field3 = mmio.Field4 = 0; MEM_WRITE(Z502InterruptDevice, &mmio); } // End of InterruptHandler
// Handle messages as fast as possible void dispatchPointer(Task*) { Dispatcher().dispatch(); }
INT32 os_create_process(char *name, void *test_name, INT32 initial_prriority,INT32 *pid_ptr,INT32 *p_error_prt, INT32 status) { S_PCB *PCB_PTR = NULL; if(initial_prriority == ILLEGAL) { *p_error_prt = ERR_BAD_PARAM; return -1; } if(readyHead != NULL) { S_PCB *temp =readyHead; while(temp != NULL) { if(strcmp(temp->p_name, name) == 0) { printf("same name error"); (*p_error_prt) = ERR_BAD_PARAM; return -1; } else { temp = temp->next; } } } if(timerHead != NULL) { S_PCB *temp =timerHead; while(temp != NULL) { if(strcmp(temp->p_name, name) == 0) { printf("same name error"); (*p_error_prt) = ERR_BAD_PARAM; return -1; } else { temp = temp->next; } }} //check total pid (*p_error_prt) = ERR_BAD_PARAM; PCB_PTR = (S_PCB*)(malloc(sizeof(S_PCB))); PCB_PTR-> p_time = 0; PCB_PTR->p_status = status; PCB_PTR->p_position = CREATE; PCB_PTR->p_id = PCBSTRARTID; (*pid_ptr) = PCBSTRARTID; PCBSTRARTID++; PCB_PTR->p_time = 0; PCB_PTR->p_priority = initial_prriority; strcpy(PCB_PTR->p_name, name); if(PCBSTRARTID >MAXPROCESS) { *p_error_prt = TOOMUCHPROCESSES; return -1; } make_context(PCB_PTR, test_name); if(status == RUN) { addToReadyQ(PCB_PTR); Dispatcher(); } else { addToReadyQ(PCB_PTR); *p_error_prt = ERR_SUCCESS; } return 0; }
// Check for faults at 10Hz void checkFaults(Task*) { Dispatcher().handleFaultPins(); }
void svc( SYSTEM_CALL_DATA *SystemCallData ) { short call_type; static short do_print = 10; short i; INT32 Time; static long SleepTimer; INT32 atLock = -1; call_type = (short)SystemCallData->SystemCallNumber; if ( do_print > 0 ) { printf( "SVC handler: %s\n", call_names[call_type]); for (i = 0; i < SystemCallData->NumberOfArguments - 1; i++ ){ //Value = (long)*SystemCallData->Argument[i]; printf( "Arg %d: Contents = (Decimal) %8ld, (Hex) %8lX\n", i, (unsigned long )SystemCallData->Argument[i], (unsigned long )SystemCallData->Argument[i]); } do_print--; } switch (call_type){ //get time service call case SYSNUM_GET_TIME_OF_DAY: //This value is found in syscalls.h CALL(MEM_READ( Z502ClockStatus, &Time )); *SystemCallData->Argument[0] = Time; break; //terminate system call case SYSNUM_TERMINATE_PROCESS: CALL(MEM_READ( Z502ClockStatus, &Time )); if(SystemCallData->Argument[0] == -1) { if(current_PCB_PTR->p_id==0) { CALL(Z502Halt()); break; } else if(timerHead != NULL) { if(Time>TimerStatusTime) { start_timer(5); CALL(Dispatcher()); break; } else CALL(Dispatcher()); break; } else{ CALL(Dispatcher()); break;} break; } else if(SystemCallData->Argument[0] == -2) { *SystemCallData->Argument[1] = ERR_SUCCESS; CALL(Z502Halt()); break; } else { S_PCB *temp = readyHead; S_PCB *prev = NULL; while(temp != NULL) { if(temp->p_id ==SystemCallData->Argument[0]) { if(temp->next == NULL) { *SystemCallData->Argument[1] = ERR_SUCCESS; break; } else { *SystemCallData->Argument[1] = ERR_SUCCESS; prev->next = temp->next; break; } } else { prev = temp; temp = temp->next; *SystemCallData->Argument[1] = ERR_SUCCESS; break; } } if(temp == NULL) { *SystemCallData->Argument[1] = CANNOTTERMINATE ; } } break; case SYSNUM_SLEEP: //overTimeModify(); schedular_printer(SLEEP); SleepTimer = SystemCallData->Argument[0]; CALL(MEM_READ( Z502ClockStatus, &Time )); current_PCB_PTR->p_time = Time + SleepTimer; lockTimer(); CALL(addToTimerQ(current_PCB_PTR)); unlockTimer(); if(Time<(timerHead->p_time)) //compare the wake time with current time { CALL(start_timer(SleepTimer)); CALL(Dispatcher()); } else{ //if wake time is smaller than now, it need wake up immedately CALL(start_timer(5)); CALL(Dispatcher()); } break; case SYSNUM_CREATE_PROCESS: os_create_process(SystemCallData->Argument[0], SystemCallData->Argument[1],SystemCallData->Argument[2],SystemCallData->Argument[3],SystemCallData->Argument[4],NOTRUN); break; case SYSNUM_GET_PROCESS_ID: os_get_process_id(SystemCallData->Argument[0], SystemCallData->Argument[1],SystemCallData->Argument[2]); break; case SYSNUM_SUSPEND_PROCESS: os_suspend_process(SystemCallData->Argument[0], SystemCallData->Argument[1]); break; case SYSNUM_RESUME_PROCESS: os_resume_process(SystemCallData->Argument[0], SystemCallData->Argument[1]); break; case SYSNUM_CHANGE_PRIORITY: os_change_priority(SystemCallData->Argument[0], SystemCallData->Argument[1],SystemCallData->Argument[2]); break; case SYSNUM_SEND_MESSAGE: os_send_message(SystemCallData->Argument[0], SystemCallData->Argument[1],SystemCallData->Argument[2],SystemCallData->Argument[3]); break; case SYSNUM_RECEIVE_MESSAGE: os_receive_message(SystemCallData->Argument[0], SystemCallData->Argument[1],SystemCallData->Argument[2],SystemCallData->Argument[3],SystemCallData->Argument[4],SystemCallData->Argument[5]); break; default: printf( "ERROR! Call type not reconginzed!\n"); printf( "Call_type is - %i\n", call_type); } }
void svc(SYSTEM_CALL_DATA *SystemCallData) { MEMORY_MAPPED_IO mmio; short call_type; static short do_print = 10; INT32 Time; INT32 Status; short i; long* arg0=SystemCallData->Argument[0]; long* arg1=SystemCallData->Argument[1]; long* arg2=SystemCallData->Argument[2]; long* arg3=SystemCallData->Argument[3]; long* arg4=SystemCallData->Argument[4]; long *arg5=SystemCallData->Argument[5]; call_type = (short) SystemCallData->SystemCallNumber; if (do_print > 0) { printf("SVC handler: %s\n", call_names[call_type]); for (i = 0; i < SystemCallData->NumberOfArguments - 1; i++) { printf("Arg %d: Contents = (Decimal) %8ld, (Hex) %8lX\n", i, (unsigned long) SystemCallData->Argument[i], (unsigned long) SystemCallData->Argument[i]); } do_print--; } switch (call_type) { // Get time service call case SYSNUM_GET_TIME_OF_DAY: mmio.Mode = Z502ReturnValue; mmio.Field1 = mmio.Field2 = mmio.Field3 = 0; MEM_READ(Z502Clock, &mmio);//hardware call Time = mmio.Field1; (SystemCallData->Argument[0])=(long*)&Time; //statePrinter(call_type,arg0, arg1, arg2, arg3, arg4); break; // get the Timer start and generate idle. case SYSNUM_SLEEP: startTimer(arg0); //statePrinter(call_type,arg0, arg1, arg2, arg3, arg4); Dispatcher();//call dispatcher break; // create process case SYSNUM_CREATE_PROCESS: OSCreateProcess(arg0,arg1,arg2,arg3,arg4); //statePrinter(call_type,arg0, arg1, arg2, arg3, arg4); break; // get process id case SYSNUM_GET_PROCESS_ID: getProcessID(arg0,arg1,arg2); //statePrinter(call_type,arg0, arg1, arg2, arg3, arg4); break; // suspend process case SYSNUM_SUSPEND_PROCESS: suspendProcess(arg0, arg1); //statePrinter(call_type,arg0, arg1, arg2, arg3, arg4); break; // resume the process case SYSNUM_RESUME_PROCESS: resumeProcess(arg0, arg1); //statePrinter(call_type,arg0, arg1, arg2, arg3, arg4); break; // change priority; case SYSNUM_CHANGE_PRIORITY: changePriority(arg0,arg1,arg2); //statePrinter(call_type,arg0, arg1, arg2, arg3, arg4); break; // terminate system call case SYSNUM_TERMINATE_PROCESS: terminateSysProcess(arg0,arg1); break; case SYSNUM_SEND_MESSAGE: Send_message(arg0, arg1, arg2, arg3); break; case SYSNUM_RECEIVE_MESSAGE: ReceiveMessage(arg0, arg1, arg2, arg3, arg4, arg5); break; case SYSNUM_DISK_WRITE: DiskWrite(arg0, arg1, arg2); break; case SYSNUM_DISK_READ: DiskRead(arg0, arg1, arg2); break; case SYSNUM_DEFINE_SHARED_AREA: DefineSharedArea(arg0, arg1, arg2,arg3,arg4); break; default: printf( "ERROR! call_type not recognized!\n" ); printf( "Call_type is - %i\n", call_type); } } // End of svc