/*@brief: switch out old pcb (p_pcb_old), run the new pcb (gp_current_process) *@param: p_pcb_old, the old pcb that was in RUN *@return: RTX_OK upon success * RTX_ERR upon failure *PRE: p_pcb_old and gp_current_process are pointing to valid PCBs. *POST: if gp_current_process was NULL, then it gets set to pcbs[0]. * No other effect on other global variables. */ int process_switch(PCB *p_pcb_old) { PROC_STATE_E state; state = gp_current_process->m_state; if (state == NEW) { if (gp_current_process != p_pcb_old && p_pcb_old->m_state != NEW) { p_pcb_old->m_state = RDY; p_pcb_old->mp_sp = (U32 *) __get_MSP(); } gp_current_process->m_state = RUN; __set_MSP((U32) gp_current_process->mp_sp); __rte(); // pop exception stack frame from the stack for a new processes } /* The following will only execute if the if block above is FALSE */ if (gp_current_process != p_pcb_old) { if (state == RDY){ p_pcb_old->m_state = RDY; p_pcb_old->mp_sp = (U32 *) __get_MSP(); // save the old process's sp gp_current_process->m_state = RUN; __set_MSP((U32) gp_current_process->mp_sp); //switch to the new proc's stack } else { gp_current_process = p_pcb_old; // revert back to the old proc on error return RTX_ERR; } } return RTX_OK; }
int context_switch(PCB* p_pcb_old) { PROC_STATE_E state; state = gp_current_process->m_state; if (state == NEW) { if (gp_current_process != p_pcb_old && p_pcb_old->m_state != NEW) { if (p_pcb_old->m_state != BLOCKED_ON_RECEIVE && p_pcb_old->m_state != BLOCKED_ON_MEMORY) { p_pcb_old->m_state = READY; } p_pcb_old->mp_sp = (U32*) __get_MSP(); } gp_current_process->m_state = RUN; __set_MSP((U32) gp_current_process->mp_sp); __rte(); // pop exception stack frame from the stack for a new processes } if (gp_current_process != p_pcb_old) { if (state == READY){ if (p_pcb_old->m_state != BLOCKED_ON_MEMORY && p_pcb_old->m_state != BLOCKED_ON_RECEIVE) { p_pcb_old->m_state = READY; } p_pcb_old->mp_sp = (U32*) __get_MSP(); // save the old process's sp gp_current_process->m_state = RUN; __set_MSP((U32) gp_current_process->mp_sp); //switch to the new proc's stack } else { gp_current_process = p_pcb_old; // revert back to the old proc on error return RTX_ERR; } } return RTX_OK; }
/** * @brief release_processor(). * @return -1 on error and zero on success * POST: gp_current_process gets updated */ int k_release_processor(void) { volatile int pid; volatile proc_state_t state; pcb_t * p_pcb_old = NULL; pid = scheduler(); if (gp_current_process == NULL) { return -1; } p_pcb_old = gp_current_process; if (pid == 1) { gp_current_process = &pcb1; } else if (pid ==2){ gp_current_process = &pcb2; } else { return -1; } state = gp_current_process->m_state; if (state == NEW) { if (p_pcb_old->m_state != NEW) { p_pcb_old->m_state = RDY; p_pcb_old->mp_sp = (uint32_t *) __get_MSP(); } gp_current_process->m_state = RUN; __set_MSP((uint32_t) gp_current_process->mp_sp); __rte(); // pop exception stack frame from the stack for new processes } else if (state == RDY){ p_pcb_old->m_state = RDY; p_pcb_old->mp_sp = (uint32_t *) __get_MSP(); // save the old process's sp gp_current_process->m_state = RUN; __set_MSP((uint32_t) gp_current_process->mp_sp); //switch to the new proc's stack } else { gp_current_process = p_pcb_old; // revert back to the old proc on error return -1; } return 0; }
/*@brief: switch out old pcb (p_pcb_old), run the new pcb (gp_current_process) *@param: p_pcb_old, the old pcb that was in RUN *@return: RTX_OK upon success * RTX_ERR upon failure *PRE: p_pcb_old and gp_current_process are pointing to valid PCBs. *POST: if gp_current_process was NULL, then it gets set to pcbs[0]. * No other effect on other global variables. */ int process_switch(PCB *p_pcb_old) { PROC_STATE_E state; #ifdef DEBUG_0 //printf("switching from process %d to process %d\n\r", p_pcb_old->m_pid, gp_current_process->m_pid); #endif /* ! DEBUG_0 */ state = gp_current_process->m_state; if (state == NEW) { if (gp_current_process != p_pcb_old && p_pcb_old->m_state != NEW) { p_pcb_old->mp_sp = (U32 *) __get_MSP(); if (p_pcb_old->m_state != BLK && p_pcb_old->m_state != BLK_RCV) { p_pcb_old->m_state = RDY; pq_push(ready_queue, p_pcb_old); } } gp_current_process->m_state = RUN; __set_MSP((U32) gp_current_process->mp_sp); __rte(); // pop exception stack frame from the stack for a new processes } /* The following will only execute if the if block above is FALSE */ if (gp_current_process != p_pcb_old) { if (state == RDY){ p_pcb_old->mp_sp = (U32 *) __get_MSP(); // save the old process's sp if (p_pcb_old->m_state != BLK && p_pcb_old->m_state != BLK_RCV) { p_pcb_old->m_state = RDY; pq_push(ready_queue, p_pcb_old); } gp_current_process->m_state = RUN; __set_MSP((U32) gp_current_process->mp_sp); //switch to the new proc's stack } else { gp_current_process = p_pcb_old; // revert back to the old proc on error return RTX_ERR; } } return RTX_OK; }