我们可以使用键盘或 pkill 命令、kill 命令和 killall 命令向进程发送各种信号。
使用键盘发送信号
在 Bash Shell 下,我们可以使用键盘发送信号,如下表所示。
kill 命令发送信号
大多数主流的 Shell,包括 Bash,都有内置的 kill 命令。Linux 系统中,也有 kill 命令,即 /bin/kill。如果使用 /bin/kill,则系统可能会激活一些额外的选项,比如,杀掉不是你自己的进程,或指定进程名作为参数,类似于 pgrep 和 pkill 命令。不过两种 kill 命令默认都是发送 SIGTERM 信号。
当准备杀掉一个进程或一连串的进程时,我们的常识是从尝试发送最安全的信号开始,即 SIGTERM 信号。以这种方式,关心正常停止运行的程序,当它收到 SIGTERM 信号时,有机会按照已经设计好的流程执行,比如,清理和关闭打开的文件。
如果你发送一个 SIGKILL 信号到进程,你将消除进程先清理而后关闭的机会,而这可能会导致不幸的结果。但如果一个有序地终结不管用,那么发送 SIGINT 或 SIGKILL 信号就可能是唯一的方法了。例如,当一个前台进程使用 Ctrl+C 组合键杀不掉时,那最好就使用命令“kill -9 PID” 了。
在前面的学习中我们已经了解,kill 命令可以发送多种信号到进程。特别有用的信号包括:
- SIGHUP (1)
- SIGINT (2)
- SIGKILL (9)
- SIGCONT (18)
- SIGSTOP (19)
在 Bash Shell 中,信号名或信号值都可作为 kill 命令的选项,而作业号或进程号则作为 kill 命令的参数。
实例 1
发送 SIGKILL 信号到 PID 是 123 的进程。
kill -9 123
或是:
kill -KILL 123
也可以是:
kill -SIGKILL 123
实例 2
使用 kill 命令终结一个作业。
#将 sleep 命令放在后台执行,休眠 30 秒
[linuxyz.cn]$ sleep 30 &
[1] 20551
#列出当前 Shell 下所有作业的信息
[linuxyz.cn]$ jobs -l
[1]+ 20551 Running sleep 30 &
#终结作业 1
[linuxyz.cn]$ kill %1
[1]+ 20551 Terminated sleep 30
#查看当前 Shell 下的作业的信息
[linuxyz.cn]$ jobs -l
killall 命令发送信号
killall 命令会发送信号到运行任何指定命令的所有进程。所以,当一个进程启动了多个实例时,使用 killall 命令来杀掉这些进程会更方便些。
注意:在生产环境中,若没有经验,使用 killall 命令之前请先测试该命令,因为在一些商业 Unix 系统中,它可能不像所期望的那样工作。
如果没有指定信号名,killall 命令会默认发送 SIGTERM 信号。例如,使用 killall 命令杀掉所有 firefox 进程:
killall firefox
发送 KILL 信号到 firefox 的进程:
killall -s SIGKILL firefox
pkill 命令发送信号
使用 pkill 命令,可以通过指定进程名、用户名、组名、终端、UID、EUID 和 GID 等属性来杀掉相应的进程。pkill 命令默认也是发送SIGTERM 信号到进程。
实例 1
使用 pkill 命令杀掉所有用户的 firefox 进程。
pkill firefox
实例 2
强制杀掉用户 mozhiyan 的 firefox 进程。
pkill -KILL -u mozhiyan firefox
实例 3
让 sshd 守护进程重新加载它的配置文件。
pkill -HUP sshd