Por que processo / programa se torna zumbi?

13

Se o script estiver rodando bem a partir da linha de comando, então, por que o mesmo script se torna zumbi depois de rodar pelo cron e como você vai solucioná-lo?

Aqui segue exemplo real:

[root@abc ~]# ps ax | grep Z
23880 ?        Zs     0:00 [checkloadadv.sh] <defunct>
23926 pts/0    S+     0:00 grep Z
[root@abc ~]# strace -p 23880
attach: ptrace(PTRACE_ATTACH, ...): Operation not permitted
[root@abc ~]# pstree | grep  checkload
init-+-crond---crond-+-checkloadadv.sh
[root@abc ~]# bash /usr/bin/checkloadadv.sh
System Load is OK : 0.05
    
por Rahul Patil 20.12.2013 / 08:30

2 respostas

21

Comozumbisreais,umprocessodezumbisnãopodesermorto,porquejáestámorto.

Comoissoacontece

QuandonoLinux/Unixumprocessomorre/terminatodasasinformaçõesdoprocessosãoremovidasdamemóriadosistema,somenteodescritordeprocessopermanece.OprocessoentranoestadoZ(zumbi).Seuprocessopairecebeumsinaldokernel:SIGCHLD,issosignificaqueumdeseusprocessosfilhossai,éinterrompidoourecomeçadepoisdeserinterrompido(nonossocaso,simplesmentesai).

Oprocessopaiagoraprecisaexecutarowait()syscallparalerostatusdesaídaeoutrasinformaçõesdeseuprocessofilho.Entãoodescritoréremovidodamemóriaeoprocessonãoémaisumzumbi.

Seoprocessopainuncachamarowait()syscall,odescritordoprocessozumbificaránamemóriaeconsumirácérebros.Normalmentevocênãovêprocessoszumbis,porqueoprocedimentoacimalevamenostempo.

Oamanhecerdosmortos

Cadadescritordeprocessoprecisadeumaquantidademuitopequenadememória,entãoalgunszumbisnãosãomuitoperigosos(comonavidareal).Umproblemaéquecadaprocessozumbimantémseuiddeprocesso,eumsistemaoperacionalLinux/Unixpossuiumnúmerolimitadodepid's.Seumsoftwareprogramadoindevidamentegerarmuitosprocessoszumbis,podeacontecerqueosprocessosnãopossammaisseriniciadosporquenãohámaisidentificaçõesdeprocessodisponíveis.

Então,seelesestãoemgruposenormes,elessãomuitoperigosos(comoemmuitosfilmesédemonstradomuitobem)

Comopodemosnosdefendercontraumahordadezumbis?

Umtironacabeçafuncionaria,maseunãoseiocomandoparaisso(oSIGKILLnãofuncionaporqueoprocessojáestámorto).

Bem,vocêpodeenviarSIGCHLDviakillparaoprocessopai,masquandoeleignoraessesinal,edepois?Suaúnicaopçãoémataroprocessopaiequeoprocessodeinicialização"adota" o zumbi. O Init chama periodicamente o wait() syscall para limpar seus filhos zumbis.

No seu caso

No seu caso, você tem que enviar SIGCHLD para o processo de crond:

root@host:~# strace -p $(pgrep cron)
Process 1180 attached - interrupt to quit

Então, a partir de outro terminal:

root@host:~$ kill -17 $(pgrep cron)

A saída é:

restart_syscall(<... resuming interrupted call ...>) = ? ERESTART_RESTARTBLOCK (To be restarted)
--- SIGCHLD (Child exited) @ 0 (0) ---
wait4(-1, 0x7fff51be39dc, WNOHANG, NULL) = -1 ECHILD (No child processes) <-- Here it happens
rt_sigreturn(0xffffffffffffffff)        = -1 EINTR (Interrupted system call)
stat("/etc/localtime", {st_mode=S_IFREG|0644, st_size=1892, ...}) = 0
rt_sigprocmask(SIG_BLOCK, [CHLD], [], 8) = 0
rt_sigaction(SIGCHLD, NULL, {0x403170, [CHLD], SA_RESTORER|SA_RESTART, 0x7fd6a7e9d4a0}, 8) = 0
rt_sigprocmask(SIG_SETMASK, [], NULL, 8) = 0
nanosleep({42, 0}, ^C <unfinished ...>
Process 1180 detached

Você vê que o wait4() syscall retorna -1 ECHILD, o que significa que nenhum processo filho está lá. Portanto, a conclusão é: o cron reage ao syscall do SIGCHLD e não deve forçar o apocalipse.

    
por 20.12.2013 / 09:31
-2

Se o encadeamento pai for morto antes de seu encadeamento filho, todo encadeamento filho se tornará um processo zumbi.

    
por 20.12.2013 / 09:09