Как известно, команда kill, несмотря на своё “кровожадное” название, предназначена всего лишь для того, чтобы посылать процессам “нужные” сигналы. Частными случаями этих сигналов являются сигналы завершения (которые, тем не менее, используется чаще всех — видимо, поэтому команда и получила такое “убийственное” название). Обычно мы используем её в виде kill -SIGNAL PID, где PID — идентификатор процесса.
Но есть и другие способы эффективно “кильнуть” процесс — по имени, по части имени, просто показав на него курсором, и т.д. Рассмотрим несколько из них.
1. Команда Kill: работаем по PID’у
Все нижеописанные команды kill посылают сигнал TERM процессам. Можно использовать как имя, так и номера сигналов. Предварительно нужно найти соответствующий процессу pid и указать его в качестве аргумента.
$ kill -TERM pid $ kill -SIGTERM pid $ kill -15 pid
Пример: прибьём-ка firefox.
$ ps -ef | grep firefox 1986 ? Sl 7:22 /usr/lib/firefox-3.5.3/firefox $ kill -9 1986
2. Команда killall: “…позови меня тихо по имени…”
Вместо PID можно указать имя процесса. Если есть более одного процесса с таким именем, все они будут “обработаны”.
Пример: и снова прибьём firefox
$ killall -9 firefox
3. Команда pkill: Сигналим по части имени
Вы можете послать сигнал любому процессу по имени или части его. И для этого не нужно знать PID процесса для посылки сигнала.
Пример: Послать SIGTERM всем процессам со строкой “sample” в имени.
$ pkill sample
Перед посылкой сигнала, лучше проверить, какие процессы “попадут под раздачу” с помощью команды pgrep -l, которая отобразит все process ID и имена, подпадающие под критерий.
В этом примере все процессы созданы таким образом, что пишут сигналы в signal-log, сообщая попутно свой PID.
$ pgrep -l sample 12406 sample-server.p 12425 sample-server.p 12430 sample-garbagec $ pkill -USR1 sample $ cat signal-log Name: ./sample-server.pl Pid: 12406 Signal Received: USR1 Name: ./sample-server.pl Pid: 12425 Signal Received: USR1 Name: ./sample-garbagecollector.pl Pid: 12430 Signal Received: USR1 Note: The part of name which you specify should be in the character within the first 15 character of the process name.
Ещё одна полезная функция у pkill — возможность отправить сигнал группе процессов по имени пользователя (UID). Например, можно легко остановить все процессы zabbix (как агента, так и сервера, а также всё, ими порождённое), потому что они работают от пользователя zabbix:
observer:~ # pgrep -l -U zabbix 617 rstats 622 netcat 846 rstats 849 netcat 1494 sh 1495 fping 1566 checkurl 1568 checkurl 1569 time 1570 wget 1571 storage_DS4000 1574 cat 1575 awk 1576 grep 1577 grep 21651 zabbix_agentd 21652 zabbix_agentd 21653 zabbix_agentd 21654 zabbix_agentd 21655 zabbix_agentd 21656 zabbix_agentd 21657 zabbix_agentd 21658 zabbix_agentd 27062 zabbix_server 27112 zabbix_server 27113 zabbix_server observer:~ # pkill -U zabbix observer:~ #
4. Команда xkill: “… не выпендривайся, покажи пальцем!”
Xkill — простейший путь завершить неправильно функционирующую программу. Когда вы хотите покончить с процессом, запустите xkill, и ваш мышиный курсор приобретёт зловещие очертания. Кликнув на окне приложения, вы завершите соответствующий процесс.
$ xkill Select the window whose client you wish to kill with button 1.... xkill: killing creator of resource 0x1200003
Надо сказать, что, естественно, программа в состоянии работать только с процессами, имеющими окна в XWindow. Так что завершить, например, hald, вы, при всём желании, не сможете.
я бы еще добавил, что соответствия номеров и названий сигналов хоть по большей части и похожи в разных системах, но в POSIX регламентируются только названия, а номера в каждой системе свои, поэтому лучше посылать сигналы, используя их имена, а в сложных случаях лучше консультироваться с signal(7) в Linux, signal(3) в FreeBSD и т.д.
А еще можно проверить существование процесса с помощью
kill -0
вместоps ax|grep pid|grep -v grep
(это работает только в Linux)Пусть пока эта информация поживёт в комментах, попозже добавлю.
Вот скрипт, если нет killall
#!/bin/sh
SIG=
case $1 in
-*) SIG=$1 ; shift ;;
esac
[ X$1 = X ] &for i in $* ; do
PS=`ps -ax | egrep ‘\.[0-9][0-9] [^ ]*\”$’\|’\.[0-9][0-9] [^ ]*\” ‘| sed ‘s/^\([ 0-9]*\) .*/\1’/`
[ “X$PS” = X ] &echo $i: kill $SIG $PS
kill $SIG $PS
done
Скрипт не мой. Создал его su (ник у него такой) и называется он unp
Ага, “Мотороллер не мой, я просто разместил объяву…” 🙂
для полноты картины добавлю, что pkill/pgrep иногда не могут «найти» процесс по имени.
встречал такое только с проблемными (подвисшими) процессами. которые как раз и требуется «kill-нуть».
приходится с помощью ps смотреть номер процесса и отправлять сигнал классическим kill-ом.
Как правило, все манипуляции с процессами всё равно сводятся к связке “ps-grep-kill”.
А про зомби вообще разговор отдельный…
нет-нет, конечно не зомби.
вполне живой, но «заглючивший» процесс.
у меня на ноутбуке стоит gnome (чисто для «посмотреть», как же люди сосуществуют с этим de-монстрами).
после перезапуска сессии запускается в том числе и gnome-screensaver. который, после срабатывания и отключения экрана, уже не выходит из этого состояния.
есть несколько предположений, почему это так происходит, но не в этом суть моего поста.
суть в том, что даже сразу после перезапуска сессии этот самый gnome-screensaver ни pkill-ом, ни pgrep-ом не детектится.
> Как правило, все манипуляции с процессами всё равно сводятся к связке «ps-grep-kill»
не скажите, не скажите. pkill/pgrep — гораздо более удобное средство, нежели связка ps|grep|kill.
хотя бы потому, что не приходится на стадии «grep» отфильтровывать строчку про сам процесс grep.
Как раз unp (см. выше) и есть ps-grep-kill 🙂
Отличный мануал.
Зачем большую ps -ef | grep firefox , если гораздо быстрее pidof firefox ?
И согласен с bappoy лучше использовать имена kill -KILL firefox , тем более киллом можно и приостановить процесс например копирования kill -STOP nautilus и продолжить kill -CONT nautilus
упс. Вместо имен PID-ы. О чем-то задумался…
я обычно так убиваю
killall `pgrep something`
удобно очень, на мой взгляд
Для админов-любителей экспериментов под виндоус:
pskill.exe -t \\* explorer.exe
pskill.exe -t \\* nosmoke.com
😉
Сомневаюсь, что nosmoke.com может выступать в качестве родительского процесса. 🙂
Расшифрую, почему “Для админов-любителей”:
pskill.exe -снять задачу(и)
-t -и все порождённые ей процессы
\\* -на всех компьютерах в домене
explorer.exe -кого мочим (считай, GUI)
Несложно представить масштабы разрушений при бездумном запуске из под учётной записи администратора домена.
Ещё стоит заметить, что xkill не убивает приложение сигналом, он рвёт соединение с X-сервером. Если приложение над чем-то глубого задумалось, то после xkill оно чаще всего будет продолжать думать, только уже тайком от пользователя.
Спасибо, очень ценное замечание!