/**
@brief This function handles a system call request coming from a process running in User Mode.
@return Void.
*/
HIDDEN void syscallUserMode()
{
	/* [Case 1] A privileged system call has been raised */
	if (SYSBP_Old->a1 > 0 && SYSBP_Old->a1 < 9)
	{
		/* Save SYS/BP Old Area into PgmTrap Old Area */
		saveCurrentState(SYSBP_Old, PGMTRAP_Old);

		/* Set program trap cause to RI (Reserved Instruction) */
		PGMTRAP_Old->CP15_Cause = CAUSE_EXCCODE_SET(PGMTRAP_Old->CP15_Cause, EXC_RESERVEDINSTR);

		/* Call the trap handler in order to trigger the PgmTrap exception response */
		pgmTrapHandler();
	}
	/* [Case 2] A non privileged system call has been raised */
	else
		/* Distinguish whether SYS5 has been invoked or not */
		checkSYS5(SYSBK_EXCEPTION, SYSBP_Old);
}
Exemple #2
0
void sysBpHandler(){
	
	int cause;
	int mode;
	
	//1-dovremmo salvare lo stato del registro
	
	//2-boh -> il tipo dice per evitare loop syscall :/
	currentProcess->p_s.cpsr += //qualcosa;
	
	//3-prendiamo il mode
	mode= ((sysBp_old->cpsr & STATUS_SYS_MODE) >> 0x3); //forse funziona -> STATUS_SYS_MODE in uarmConst.h
	
	//4-cause interrupt
	cause=getCAUSE();
	
	if(cause == EXC_SYSCALL){ //caso system call
		
		//controlla se è in user mode
		if(mode==TRUE){ //è definito da qualche parte il true?
			
			//controllo se è una delle 11 syscall
			if((sysBp_old->reg_a0 >= 1) && (sysBp_old->reg_a0 <= SYSCALL_MAX)){ //SYSCALL_MAX sta in const.h
			
				sysBp_old->CP15_Cause = setCAUSE(); //siamo sicuri non ci vadano parametri?
				
				//salva il sysbp old in pgmtrap old
				
				pgmTrapHandler();
				
			}
			else{
				//ERRORE!!! FACCIAMO UN ALTRA VOLTA!!!
			}
		}
		else{//caso kernel mode
			
			int ret;
			
			/* Salva i parametri delle SYSCALL */
			U32 argv1 = sysBp_old->a2;
			U32 argv2 = sysBp_old->a3;
			U32 argv3 = sysBp_old->a4;
			
			
			
			/* Gestisce ogni singola SYSCALL */
			switch(sysBp_old->a1)
			{
				case CREATEPROCESS:
					//currentProcess->p_state.reg_v0 = createProcess((state_t *) arg1);
					break;
					
				case TERMINATEPROCESS:
					//ris = terminateProcess((int) arg1);
					//if(currentProcess != NULL) currentProcess->p_state.reg_v0 = ris;
					break;
					
				case SEMOP:
					semaphoreOperation((int *) argv1, (int) argv2);
					break;
				
				case SPECSYSHDL:
					
					break;
					
				case SPECTLBHDL:
					
					break;
					
				case SPECPGMTHDL:
					
					break;
					
					
				case EXITTRAP:
					
					break;
					
				case GETCPUTIME:
					//currentProcess->p_state.reg_v0 = getCPUTime();
					break;
					
				case WAITCLOCK:
					//waitClock();
					break;
					
				case IODEVOP:
					
					break;
					
				case GETPID:
					currentProcess->p_state.reg_v0 = getPid();
					break;
					
				
				/*
					
				case WAITIO:
					currentProcess->p_state.reg_v0 = waitIO((int) arg1, (int) arg2, (int) arg3);
					break;
					
				case GETPPID:
					currentProcess->p_state.reg_v0 = getPpid();
					break;
					
				case SPECTLBVECT:
					specTLBvect((state_t *) arg1, (state_t *)arg2);
					break;
					
				case SPECPGMVECT:
					specPGMvect((state_t *) arg1, (state_t *)arg2);
					break;
					
				case SPECSYSVECT:
					specSYSvect((state_t *) arg1, (state_t *)arg2);
					break;
					
				 */
					
				default:
					/* Se non è già stata eseguita la SYS12, viene terminato il processo corrente */
					if(currentProcess->ExStVec[ESV_SYSBP] == 0)
					{
						int ris;
						
						ris = terminateProcess(-1);
						if(currentProcess != NULL) currentProcess->p_state.reg_v0 = ris;
					}
					/* Altrimenti viene salvata la SysBP Old Area all'interno del processo corrente */
					else
					{
						saveCurrentState(sysBp_old, currentProcess->sysbpState_old);
						LDST(currentProcess->sysbpState_new);
					}
			}
			
			scheduler();
			
		}
	}
	else{ //caso breakpoint
	
 
	}
}