Por que não posso matar um processo SIGSTOP'd com um SIGTERM e onde está o sinal pendente armazenado?

21

Estou usando o Debian stretch (systemd). Eu estava executando o daemon rsyslog em primeiro plano usando %código% e eu fiz um Ctrl + Z para pará-lo. O estado do processo foi alterado para /usr/sbin/rsyslogd -n (interrompido, encadeado). Eu emiti vários comandos Tl para o processo e o estado do processo era o mesmo: kill -15 <pid> . Uma vez que eu fiz um Tl , ele morreu. Eu tenho 3 perguntas.

  • Por que o processo fg -ed não está respondendo a SIGSTOP ? Por que o kernel mantém no mesmo estado?
  • Por que foi morto no momento em que recebeu o sinal SIGTERM ?
  • Se foi por causa do sinal SIGCONT anterior, onde foi mantido até o processo ser retomado?
por nohup 27.07.2016 / 16:07

2 respostas

36

SIGSTOP e SIGKILL são dois sinais que não podem ser capturados e manipulados por um processo. SIGTSTP é como SIGSTOP , exceto que pode ser capturado e manipulado.

Os sinais SIGSTOP e SIGTSTP interrompem um processo, pronto para SIGCONT . Quando você envia esse processo a SIGTERM , o processo não está em execução e, portanto, não pode executar o código para sair.

(Há também SIGTTIN e SIGTTOU , que são sinais gerados pela camada TTY quando uma tarefa em segundo plano tenta ler ou gravar no terminal. Eles podem ser capturados, mas irão parar (suspender) o processo, apenas como SIGTSTP . Mas agora vou ignorar esses dois para o restante desta resposta.)

A sua Ctrl Z envia ao processo um SIGTSTP , que parece não ser tratado de maneira especial por rsyslogd , então simplesmente suspende o processo pendente SIGCONT ou SIGKILL .

A solução aqui também é enviar SIGCONT após seu SIGTERM para que o processo possa receber e manipular o sinal.

Exemplo:

sleep 999 &

# Assume we got PID 456 for this process
kill -TSTP 456    # Suspend the process (nicely)
kill -TERM 456    # Terminate the process (nicely). Nothing happens
kill -CONT 456    # Continue the process so it can exit cleanly

A documentação para a Biblioteca GNU C explica isso muito bem , Eu acho (meu destaque):

While a process is stopped, no more signals can be delivered to it until it is continued, except SIGKILL signals and (obviously) SIGCONT signals. The signals are marked as pending, but not delivered until the process is continued. The SIGKILL signal always causes termination of the process and can’t be blocked, handled or ignored. You can ignore SIGCONT, but it always causes the process to be continued anyway if it is stopped. Sending a SIGCONT signal to a process causes any pending stop signals for that process to be discarded. Likewise, any pending SIGCONT signals for a process are discarded when it receives a stop signal

    
por 27.07.2016 / 16:31
9

SIGTERM é como qualquer outro sinal em que pode ser capturado por um processo. Receber o sinal apenas fará o processo saltar para uma rotina especial de manipulador de sinal. Para SIGTERM , a ação padrão será encerrar o processo, mas, por exemplo, um editor pode querer capturar o sinal para salvar uma cópia de rascunho de qualquer arquivo aberto antes de morrer. Se o processo for interrompido, ele não poderá executar o manipulador de sinal, mas o sinal permanecerá pendente até que o processo continue. Note que o número dos sinais enviados geralmente não será salvo.

Em teoria, o sistema pode saber se o processo tem um manipulador de sinal instalado para SIGTERM e finalizá-lo imediatamente, caso contrário. Mas (de acordo com o comentário de Gilles), o POSIX exige que o sinal seja pendurado até que o processo seja continuado via SIGCONT .

    
por 27.07.2016 / 16:23