Відповіді:
kill -9
( SIGKILL ) завжди працює, якщо у вас є дозвіл на вбивство процесу. По суті, або процес повинен бути запущений вами, і не бути налаштованим або налаштованим, або ви повинні мати root. Є один виняток: навіть root не може надіслати фатальний сигнал PID 1 ( init
процес).
Однак kill -9
не гарантовано працювати негайно . Усі сигнали, включаючи SIGKILL, подаються асинхронно: ядро може зайняти час для їх доставки. Зазвичай подача сигналу займає максимум кілька мікросекунд, саме час, який потрібен цілі, щоб отримати відрізок часу. Однак якщо ціль заблокувала сигнал , сигнал буде в черзі, поки ціль не розблокує його.
Зазвичай процеси не можуть блокувати SIGKILL. Але код ядра може і процеси виконувати код ядра під час виклику системних викликів . Код ядра блокує всі сигнали, коли переривання системного виклику призведе до погано сформованої структури даних десь у ядрі, або, загалом, до порушення інваріанта ядра. Отже, якщо (через помилку чи неправильне проектування) системний виклик блокується на невизначений термін, фактично неможливо вбити спосіб. (Але процес буде вбито, якщо він коли-небудь завершить системний виклик.)
Процес, заблокований у системному дзвінку, знаходиться у режимі безперебійного сну . Команда ps
or top
(на більшості уніцій) показує її у стані D
( я думаю, що спочатку для " d isk").
Класичним випадком тривалого безперебійного сну є процеси доступу до файлів через NFS, коли сервер не відповідає; сучасні реалізації, як правило, не накладають режиму безперебійного сну (наприклад, в Linux, intr
опція кріплення дозволяє сигналу перервати доступ до файлів NFS).
Іноді ви можете бачити записи, позначені Z
(або H
під Linux, я не знаю, що це відмінність) у вихідному ps
чи top
вихідному. Це технічно не процеси, це процеси зомбі, які є не що інше, як запис у таблиці процесів, що зберігається навколо, щоб батьківський процес міг повідомити про смерть своєї дитини. Вони відійдуть, коли батьківський процес зверне увагу (або помре).
man 5 nfs
: "Параметр intr
/ nointr
mount припинено після ядра 2.6.25. Тільки SIGKILL може перервати очікувані операції NFS на цих ядрах, і якщо зазначено, цей параметр монтажу ігнорується, щоб забезпечити зворотну сумісність зі старими ядрами."
sshfs
процес (і так само, як і з будь-якою іншою файловою системою FUSE: ви завжди можете примусово відключити цей спосіб).
Колись процес існує і його не можна вбити через:
top
ньому сигналізується Ztop
ній сигналізується Д.Це здається, що у вас може бути процес зомбі . Це нешкідливо: єдиний ресурс, який споживає процес зомбі, - це запис у таблиці процесів. Він піде, коли батьківський процес вмирає або реагує на смерть своєї дитини.
Ви можете побачити, чи є процес зомбі, скориставшись top
цією командою:
ps aux | awk '$8=="Z" {print $2}'
ps
. Хто може бути впевнений, що обов'язкове поле завжди буде 8-м, з усіма реалізаціями ps
в усіх Unices?
Перевірте свої /var/log/kern.log
та /var/log/dmesg
(або їх еквіваленти) наявність будь-яких підказок. На мій досвід, це сталося зі мною лише тоді, коли раптово перепало мережеве з'єднання кріплення NFS або вийшов з ладу драйвер пристрою. Це може статися, якщо жорсткий диск також вийде з ладу, я вважаю.
Ви можете використовувати, lsof
щоб побачити, які файли пристроїв відкрив процес.
kill -9
зазвичай не працювали, навіть очікуючи 60 хвилин. Єдиним рішенням було перезавантаження.
Якщо відповіді @ Maciej та @ Gilles не вирішують вашу проблему, і ви не розпізнаєте процес (а на запитання, що це з вашим дистрибутивом, не знайдете відповідей). Перевірте наявність у Rootkit та інших ознак, якими ви володіли . Руткіт більш ніж здатний запобігти вам убити процес. Насправді багато хто здатний заважати вам їх бачити. Але якщо вони забудуть змінити 1 невелику програму, вони можуть бути помічені (наприклад, вони змінили top
, але ні htop
). Швидше за все, це не так, але краще безпечно, ніж шкода.
Вбити насправді означає надіслати сигнал. Є кілька сигналів, які ви можете надіслати. kill -9 - це спеціальний сигнал.
При надсиланні сигналу програма займається цим. якщо не ядро займається цим. тож ви можете захопити сигнал у вашій програмі.
Але я сказав, що вбити -9 було особливим. Він особливий тим, що програма не отримує його. воно прямує до ядра, яке тоді справді вбиває додаток при першій можливій нагоді. іншими словами вбиває його мертвим
kill -15 посилає сигнал SIGTERM, який означає SIGNAL TERMINATE, інакше кажучи, повідомляє програмі вийти. Це дружній спосіб сказати програмі, що час відключення. але якщо додаток не відповідає kill -9 вб'є його.
якщо kill -9 не працює, це, ймовірно, означає, що ваше ядро не працює. перезавантаження в порядку. Я не можу згадати, що коли-небудь траплялося.
По-перше, перевірте, чи це процес Zombie (що дуже можливо):
ps -Al
Ви побачите щось на кшталт:
0 Z 1000 24589 1 0 80 0 - 0 exit ? 00:00:00 soffice.bin <defunct>
(Зверніть увагу на "Z" зліва)
Якщо 5-й стовпець не 1, значить, він має батьківський процес. Спробуйте вбити ідентифікатор батьківського процесу .
Якщо його PPID = 1, НЕ Вбивайте його !! , подумайте, які інші пристрої чи процеси можуть бути пов’язані з цим.
Наприклад, якщо ви використовували змонтований пристрій або самбу, спробуйте його відключити. Це може випустити процес зомбі.
ПРИМІТКА . Якщо ps -Al
(або top
) відображається "D" замість "Z", це може бути пов'язано з віддаленим кріпленням (наприклад, NFS). На мій досвід, перезавантаження - це єдиний спосіб поїхати туди, але ви можете перевірити інші відповіді, які висвітлюють цю справу більш детально.
Як уже згадували інші, процес безперебійного сну неможливо вбити негайно (або, в деяких випадках, зовсім). Варто зазначити, що для вирішення цієї проблеми в певних сценаріях було додано інший стан процесу, TASK_KILLABLE, особливо загальний випадок, коли процес очікується на NFS. Дивіться http://lwn.net/Articles/288056/
На жаль, я не вірю, що це використовується в будь-якому місці ядра, крім NFS.
ls
процесу доступу до sshfs
версії, коли віддалений сервер виявився недоступним. Чи є рішення для FUSE або sshfs, яке я можу використовувати в майбутньому, щоб уникнути подібних ситуацій? 2.6.30 ядро
Зробив невеликий сценарій, який мені дуже допоміг подивитися!
Ви можете використовувати його для вбивства будь-якого процесу із заданим іменем на його шляху (зверніть увагу на це !!) Або ви можете вбити будь-який процес певного користувача за допомогою параметра "-u ім'я користувача".
#!/bin/bash
if [ "$1" == "-u" ] ; then\n
PID=`grep "$2" /etc/passwd | cut -d ":" -f3`
processes=`ps aux | grep "$PID" | egrep -v "PID|ps \-au|killbyname|grep" | awk '{ print $2}'`
echo "############# Killing all processes of user: $2 ############################"
else
echo "############# Killing processes by name: $1 ############################"
processes=`ps aux | grep "$1" | egrep -v "killbyname|grep" | awk '{ print $2}' `
fi
for process in $processes ; do
# "command" stores the entire commandline of the process that will be killed
#it may be useful to show it but in some cases it is counter-productive
#command=`ps aux | grep $process | egrep -v "grep" | awk '{ print $2 }'`
echo "Killing process: $process"
echo ""
kill -9 $process
done
Бувають випадки, коли навіть якщо ви надіслаєте процес kill -9, цей pid зупиняється, але процес перезапускається автоматично (наприклад, якщо ви спробуєте його gnome-panel
, він перезапуститься): чи може це бути тут?
з тут спочатку :
перевірте, чи щось показує страйк
strace -p <PID>
спробуйте приєднатися до процесу за допомогою gdb
gdb <path to binary> <PID>
якщо процес взаємодіяв із пристроєм, який ви можете відключити, видаліть модуль ядра або фізично відключіть / відключіть вилку від мережі ... тоді спробуйте це.
У мене було таке питання. Це була програма, яку я запустив strace
і перервав Ctrl
+ C
. Він опинився у T
(простеженому чи зупиненому) стані. Я не знаю, як саме це сталося, але це було не під силу SIGKILL
.
Якщо коротко розповісти, мені вдалося вбити це за допомогою gdb
:
gdb -p <PID>
> kill
Kill the program being debugged? (y or n) y
> quit
Виходячи із підказки з відповіді gilles, у мене був процес, позначений "Z" вгорі ( <defunct>
в ps), який використовував системні ресурси, у нього навіть був відкритий порт, який був LISTEN'ing, і ви можете підключитися до цього порту. Це було після виконання kill -9
на ньому. Його батько був "1" (тобто init
), тому теоретично його слід просто повторити і зникнути. Але це не було, воно стирчало, хоч і не бігало, і "не вмирало"
Тож у моєму випадку це було зомбі, але все-таки споживало ресурси ... FWIW.
І це не було вбивством жодної кількості kill -9
російських
І його батько був, init
але його не збирали (прибирали). Тобто init
народила зомбі.
І перезавантажувати проблему не потрібно було. Хоча перезавантаження "спрацювало б" навколо проблеми / пришвидшило її вимкнення. Просто не витончена, що все-таки було можливо.
І це був LISTEN-порт, який належить до зомбі-процесу (і кілька інших портів, схожий на статус CLOSE_WAIT, підключили localhost до localhost). І це навіть прийняло зв’язки. Навіть як зомбі. Я думаю, що не збирався очищати порти, але вхідні з'єднання все ще були додані до відставання порту прослуховування TCP, хоча вони не мали шансу прийняти.
Багато з перерахованого вище в різних місцях міжвузлів заявляються як "неможливі".
Виявляється, у мене в ній була внутрішня нитка, яка виконувала "системний виклик" (в даному випадку ioctl), щоб повернути на це потрібно кілька годин (така очікувана поведінка). Мабуть, система не може вбити процес «до кінця», поки він не повернеться з ioctl
виклику, здогадуйтесь, що він переходить у землю ядра. Через декілька годин він повернувся, все прояснилося, і розетки автоматично закривалися тощо, як очікувалося. Ось який час нудить у смертному карі! Ядро терпляче чекало, щоб його вбити.
Отже, щоб відповісти на ОП, іноді доводиться чекати. Довгий час. Тоді вбивство нарешті відбудеться.
Також перевірте dmesg, щоб побачити, чи не було паніки з ядром (тобто помилка ядра).