Як я можу вбити процес <defunct>, батьком якого є init?


27

Передача періодично висить на моєму NAS. Якщо я надсилаю SIGTERM, він не зникає зі списку процесів, а <defunct>біля нього з’являється мітка. Якщо я надішлю SIGKILL, він все ще не зникає, і я не можу припинити батьків, тому що це батько init. Єдиний спосіб я можу позбутися процесу та перезапустити передачу - це перезавантажити.

Я усвідомлюю, що найкраще, що я можу зробити, - спробувати виправити передачу (і я пробував), але я новачок у складанні, і я хотів переконатися, що мої торренти закінчилися, перш ніж я розпочну з цим возитися.


3
Ніхто не констатує очевидне ... процес <defunct>, який належить "init", повинен бути неможливим! Це дуже дивна ситуація! Ти впевнений?
JoelFan

@JoelFan: Я просто шукав це, щоб переконатися, що я не забув щось важливе. Зомбі, які є дітьми, initповинні пройти досить швидко, оскільки initперіодично чекає на дітей, як одне з багатьох його загальних завдань ... - це <defunct>те саме, що зомбі?
Д.Шоулі

1
Nevermind ... <defunct>точно так само, як зомбі. initбуде чекати своїх дітей, тому це ніколи не повинно відбуватися теоретично. Цікаво , що станеться , якщо ви відправити SIGCHLDв init?
Д.Шоулі

@JoelFan: Так, я впевнений. Значення для PPID було 1 (init), тому SIGKILL процес неможливо.
Енді Е

Відповіді:


35

Ви не можете вбити <defunct>процес (також відомий як процес зомбі), оскільки він уже мертвий. Система зберігає зомбі-процеси для батьків, щоб збирати статус виходу. Якщо батько не збирає статус виходу, процес зомбі залишатиметься назавжди. Єдиний спосіб позбутися цих процесів зомбі - це вбивство батьків. Якщо батьків є init, ви можете лише перезавантажити.

Процеси зомбі майже не вимагають повторних результатів, тому немає ніяких витрат на продуктивність, що дозволяють їм затриматися. Хоча процес зомбі зазвичай означає, що в деяких ваших програмах є помилка. Ініт зазвичай повинен збирати всіх дітей. Якщо у Ініта є діти-зомбі, то в init є помилка (або щось інше, але помилка це є).

http://en.wikipedia.org/wiki/Zombie_process


9
initніколи не можуть мати дітей зомбі. З статті wikipedia: Коли процес втрачає свого батьківського, init стає його новим батьківським. Init періодично виконує виклик системи очікування, щоб отримати жодного зомбі з init як батьків. Однією з initобов'язків є пожинання сиріт та зомбі без батьків.
Д.Шоулі

14
@ D.Shawley: initхоча можуть бути помилки. У замінника init runitвиникла помилка, яка викликає цю проблему.
camh

2
Ініт може мати дітей, що не вмерли, можливо через помилку, але це може. Тому що я зараз дивлюсь на одного.
studgeek

Є ця програма, яку я вибіг з терміналу і перейшов у неіснуючий стан. Як пояснив @lesmana, коли я закрив термінал (батьківський), програма вийшла з чистого режиму.
mk ..

6

Кожен, хто намагається виправити вихідний код передачі C, повинен прочитати про трюк "подвійної вилки", щоб уникнути зомбі та обробників сигналів ... і як його можна використовувати як частину розумної варіативної функції нересту (див. Нерест в Unix ).

excerpt from: 
   "Spawning in Unix", http://lubutu.com/code/spawning-in-unix

Double fork
This trick lets you spawn processes whilst avoiding zombies, without 
installing any signal handler. The first process forks and waits for its 
child; the second process forks and immediately exits and is reaped;
the third process is adopted by init, and executes the desired program. 
All zombies accounted for, since init is always waiting.

if(fork() == 0) {
   if(fork() == 0) {
       execvp(file, argv);
       exit(EXIT_FAILURE);
   }
   exit(EXIT_SUCCESS);
}
wait(NULL);

1
Подвійна вилка перешкоджає процесам зомбі, змушуючи ядро ​​встановити його батьківське значення PID 1, яке повинно очищати зомбі. Здається, що передача вже це робить, оскільки її батько вже 1 процес.
Джандер

1
Тут є кілька проблем. №1: Тільки батько повинен дзвонити exit(3); діти повинні зателефонувати _exit(2)натомість (в іншому випадку ви отримуєте кілька спалахів stdio, серед інших питань). # 2: Це execvp(3)може скористатись, perror(3)якщо воно не вдасться. # 3: Ви повинні просто використовувати signal(SIGCHLD, SIG_IGN)замість цілого безладу.
Кевін
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.