2013-08-05 15 views
5

mia comprensione è come segue:In che modo le chiamate di sistema vengono interrotte dal segnale?

la chiamata di sistema di bloccaggio normalmente mettere il processo in stato 'TASK_INTERRUPTIBLE' in modo tale che quando un segnale viene consegnato, il kernel pone il processo in stato di 'TASK_RUNNING'. E il processo verrà programmato per essere eseguito quando si verifica il successivo tick del timer, in modo che il syscall venga interrotto.

Ma ho fatto un piccolo test, non è riuscito. Ho creato un processo usermode, che ha chiamato sleep(). E ho cambiato lo stato del processo in TASK_RUNNING nel kernel, ma sleep() non è stato affatto interrotto e il processo stava ancora dormendo.

Quindi ho provato wake_up_process (processo), non è riuscito.

Quindi ho provato set_tsk_thread_flag (processo, TIF_SIGPENDING), non è riuscito.

Quindi ho provato set_tsk_thread_flag (processo, TIF_SIGPENDING) e wake_up_process (processo), riuscito !! sleep() è stato interrotto e il processo ha iniziato a funzionare.

Quindi non è così semplice. Qualcuno sa esattamente come le chiamate di sistema vengono interrotte dal segnale?

+0

Se si chiama semplicemente "wake_up_process()", il processo si riattiva, controlla per vedere cosa succede e scopre che non c'era motivo di riattivare, quindi torna immediatamente in stato di stop. Se imposti il ​​flag senza svegliare il processo, allora non si attiva, quindi non controlla la flag. Devi fare entrambe le cose. – caf

risposta

2

Check out __send_signal da signal.c. Chiede complete_signal vicino alla fine, che alla fine chiama questa piccola funzione:

void signal_wake_up_state(struct task_struct *t, unsigned int state) 
{ 
     set_tsk_thread_flag(t, TIF_SIGPENDING); 
     /* 
     * TASK_WAKEKILL also means wake it up in the stopped/traced/killable 
     * case. We don't check t->state here because there is a race with it 
     * executing another processor and just now entering stopped state. 
     * By using wake_up_state, we ensure the process will wake up and 
     * handle its death signal. 
     */ 
     if (!wake_up_state(t, state | TASK_INTERRUPTIBLE)) 
       kick_process(t); 
} 

E questo è come lo fai. Si noti che non è sufficiente impostare il flag del thread: è necessario utilizzare una funzione di attivazione per assicurarsi che il processo sia pianificato.

+0

, ho provato wake_up_process() senza impostare il flag del thread, anche questo non è riuscito. Quindi voglio quando e in che modo le chiamate di sistema vengono interrotte dal segnale? – goodjesse

+0

... si imposta il flag del filo, quindi si riattiva il processo. Manca uno di questi due passaggi e non funzionerà. Cosa non è chiaro a riguardo? – nneonneo

Problemi correlati