如何在 Linux 中使用 ps、kill 和 nice 管理进程
介绍
与任何现代计算机一样,Linux 服务器运行多个应用程序。这些被称为和管理为单独的流程。
虽然 Linux 将处理进程生命周期中的低级、幕后管理——即启动、关闭、内存分配等——您将需要一种与操作系统交互的方式来管理它们更高的水平。
在本指南中,您将了解流程管理的一些基本方面。为此,Linux 提供了许多标准的内置工具。
您将在 Ubuntu 20.04 环境中探索这些想法,但任何现代 Linux 发行版都将以类似的方式运行。
第 1 步 – 如何在 Linux 中查看正在运行的进程
您可以使用 top
命令查看服务器上运行的所有进程:
- top
Outputtop - 15:14:40 up 46 min, 1 user, load average: 0.00, 0.01, 0.05
Tasks: 56 total, 1 running, 55 sleeping, 0 stopped, 0 zombie
Cpu(s): 0.0%us, 0.0%sy, 0.0%ni,100.0%id, 0.0%wa, 0.0%hi, 0.0%si, 0.0%st
Mem: 1019600k total, 316576k used, 703024k free, 7652k buffers
Swap: 0k total, 0k used, 0k free, 258976k cached
PID USER PR NI VIRT RES SHR S %CPU %MEM TIME+ COMMAND
1 root 20 0 24188 2120 1300 S 0.0 0.2 0:00.56 init
2 root 20 0 0 0 0 S 0.0 0.0 0:00.00 kthreadd
3 root 20 0 0 0 0 S 0.0 0.0 0:00.07 ksoftirqd/0
6 root RT 0 0 0 0 S 0.0 0.0 0:00.00 migration/0
7 root RT 0 0 0 0 S 0.0 0.0 0:00.03 watchdog/0
8 root 0 -20 0 0 0 S 0.0 0.0 0:00.00 cpuset
9 root 0 -20 0 0 0 S 0.0 0.0 0:00.00 khelper
10 root 20 0 0 0 0 S 0.0 0.0 0:00.00 kdevtmpfs
前几行输出提供了系统统计信息,例如 CPU/内存负载和正在运行的任务总数。
您可以看到有 1 个正在运行的进程和 55 个被认为睡眠的进程,因为它们没有主动使用 CPU 周期。
显示输出的其余部分显示正在运行的进程及其使用情况统计信息。默认情况下,top
会自动按 CPU 使用率对这些进程进行排序,因此您可以首先看到最繁忙的进程。 top
将继续在您的 shell 中运行,直到您使用标准组合键 Ctrl+C
停止它以退出正在运行的进程。这将发送一个 kill
信号,指示进程在能够停止时优雅地停止。
top
的改进版本,称为 htop
,在大多数包存储库中都可用。在 Ubuntu 20.04 上,您可以使用 apt
安装它:
- sudo apt install htop
之后,htop
命令将可用:
- htop
Output Mem[||||||||||| 49/995MB] Load average: 0.00 0.03 0.05
CPU[ 0.0%] Tasks: 21, 3 thr; 1 running
Swp[ 0/0MB] Uptime: 00:58:11
PID USER PRI NI VIRT RES SHR S CPU% MEM% TIME+ Command
1259 root 20 0 25660 1880 1368 R 0.0 0.2 0:00.06 htop
1 root 20 0 24188 2120 1300 S 0.0 0.2 0:00.56 /sbin/init
311 root 20 0 17224 636 440 S 0.0 0.1 0:00.07 upstart-udev-brid
314 root 20 0 21592 1280 760 S 0.0 0.1 0:00.06 /sbin/udevd --dae
389 messagebu 20 0 23808 688 444 S 0.0 0.1 0:00.01 dbus-daemon --sys
407 syslog 20 0 243M 1404 1080 S 0.0 0.1 0:00.02 rsyslogd -c5
408 syslog 20 0 243M 1404 1080 S 0.0 0.1 0:00.00 rsyslogd -c5
409 syslog 20 0 243M 1404 1080 S 0.0 0.1 0:00.00 rsyslogd -c5
406 syslog 20 0 243M 1404 1080 S 0.0 0.1 0:00.04 rsyslogd -c5
553 root 20 0 15180 400 204 S 0.0 0.0 0:00.01 upstart-socket-br
htop
提供更好的多 CPU 线程可视化、更好地了解现代终端中的颜色支持、更多排序选项等功能。与 top
不同,它并不总是默认安装,但可以被视为替代品。您可以像使用 top
一样按 Ctrl+C
退出 htop
。您还可以了解有关如何使用 top 和 htop 的更多信息。
在下一节中,您将了解如何使用工具来查询特定进程。
第 2 步 – 如何使用 ps 列出进程
top
和 htop
提供了一个仪表板界面来查看类似于图形任务管理器的正在运行的进程。仪表板界面可以提供概览,但通常不会直接返回可操作的输出。为此,Linux 提供了另一个名为 ps
的标准命令来查询正在运行的进程。
不带任何参数运行 ps
提供的信息非常少:
- ps
Output PID TTY TIME CMD
1017 pts/0 00:00:00 bash
1262 pts/0 00:00:00 ps
此输出显示与当前用户和终端会话关联的所有进程。如果您当前仅在此终端中运行 bash
shell 和此 ps
命令,那么这是有意义的。
要更全面地了解此系统上的进程,您可以运行 ps aux
:
- ps aux
OutputUSER PID %CPU %MEM VSZ RSS TTY STAT START TIME COMMAND
root 1 0.0 0.2 24188 2120 ? Ss 14:28 0:00 /sbin/init
root 2 0.0 0.0 0 0 ? S 14:28 0:00 [kthreadd]
root 3 0.0 0.0 0 0 ? S 14:28 0:00 [ksoftirqd/0]
root 6 0.0 0.0 0 0 ? S 14:28 0:00 [migration/0]
root 7 0.0 0.0 0 0 ? S 14:28 0:00 [watchdog/0]
root 8 0.0 0.0 0 0 ? S< 14:28 0:00 [cpuset]
root 9 0.0 0.0 0 0 ? S< 14:28 0:00 [khelper]
…
这些选项告诉 ps
以更易于阅读的格式显示所有用户拥有的进程(不管他们的终端关联)。
通过使用管道,您可以使用 grep
在 ps aux
的输出中进行搜索,以返回特定进程的名称。如果您认为它已经崩溃,或者如果您出于某种原因需要停止它,这将很有用。
- ps aux | grep bash
Outputsammy 41664 0.7 0.0 34162880 2528 s000 S 1:35pm 0:00.04 -bash
sammy 41748 0.0 0.0 34122844 828 s000 S+ 1:35pm 0:00.00 grep bash
这将返回您刚刚运行的 grep
进程,以及当前正在运行的 bash
shell。它还返回它们的总内存和 CPU 使用率、它们运行了多长时间,以及在上面突出显示的输出中,它们的进程 ID。在 Linux 和类 Unix 系统中,每个进程都分配有一个进程 ID 或 PID。这就是操作系统识别和跟踪进程的方式。
获取进程 PID 的快速方法是使用 pgrep
命令:
- pgrep bash
Output1017
启动时产生的第一个进程称为 init,其 PID 为“1”。
- pgrep init
Output1
然后,该进程负责在系统上生成所有其他进程。后面的进程被赋予更大的 PID 编号。
一个进程的父级是负责产生它的进程。父进程有一个 PPID,您可以在许多进程管理应用程序的列标题中看到它,包括 top
、htop
和 ps
。
用户和操作系统之间关于进程的任何通信都涉及在操作期间的某个时刻在进程名称和 PID 之间进行转换。这就是为什么这些实用程序总是在其输出中包含 PID。在下一节中,您将学习如何使用 PID 向正在运行的进程发送停止、恢复或其他信号。
第 3 步 – 如何在 Linux 中发送进程信号
Linux 中的所有进程都响应信号。信号是一种操作系统级别的方式,它告诉程序终止或修改它们的行为。
向程序传递信号的最常见方式是使用 kill
命令。如您所料,此实用程序的默认功能是尝试终止进程:
- kill PID_of_target_process
这会将 TERM 信号发送到进程。 TERM 信号告诉进程请终止。这样可以让程序进行清理操作并顺利退出。
如果程序运行不正常并且在给出 TERM 信号时没有退出,您可以通过传递 KILL
信号来升级信号:
- kill -KILL PID_of_target_process
这是一个特殊的信号,不会发送给程序。
相反,它被提供给操作系统内核,从而关闭进程。这用于绕过忽略发送给它们的信号的程序。
每个信号都有一个关联的数字,可以代替名称传递。例如,您可以传递“-15”而不是“-TERM”,传递“-9”而不是“-KILL”。
信号不仅用于关闭程序。它们也可用于执行其他操作。
例如,许多设计为在后台持续运行的进程(有时称为“守护进程”)将在获得 HUP
或 hang-up 时自动重启信号。Apache 网络服务器通常以这种方式运行。
- sudo kill -HUP pid_of_apache
上述命令将导致 Apache 重新加载其配置文件并恢复提供内容。
注意:像这样的许多后台进程都是通过系统 服务 管理的,它提供了一个额外的界面来与它们交互,通常最好重新启动服务本身而不是发送 HUP
直接向一个正在运行的进程发出信号。如果您查看各种服务的配置文件,您可能会发现各种 service restart
挂钩旨在执行此操作——向特定进程发送信号——同时还提供日志和其他报告。
您可以使用 -l
标志列出所有可能通过 kill
发送的信号:
- kill -l
Output1) SIGHUP 2) SIGINT 3) SIGQUIT 4) SIGILL 5) SIGTRAP
6) SIGABRT 7) SIGBUS 8) SIGFPE 9) SIGKILL 10) SIGUSR1
11) SIGSEGV 12) SIGUSR2 13) SIGPIPE 14) SIGALRM 15) SIGTERM
虽然发送信号的传统方式是通过使用 PID,但也有使用常规进程名称执行此操作的方法。
pkill
命令的工作方式几乎与 kill
完全相同,但它对进程名称进行操作:
- pkill -9 ping
上面的命令等效于:
- kill -9 `pgrep ping`
如果你想向某个进程的每个实例发送一个信号,你可以使用 killall
命令:
- killall firefox
上面的命令会将 TERM 信号发送到计算机上运行的每个 firefox
实例。
第 4 步 – 如何调整流程优先级
通常,您会想要调整在服务器环境中赋予哪些进程优先权。
某些流程可能被认为对您的情况至关重要,而其他流程可能会在有剩余资源时执行。
Linux 通过一个叫做 niceness 的值来控制优先级。
高优先级任务被认为不太好,因为它们也不共享资源。另一方面,低优先级进程很好,因为它们坚持只占用最少的资源。
当您在文章开头运行 top
时,有一列标记为 NI。这是该过程的 nice 值:
- top
[secondary_label Output]
Tasks: 56 total, 1 running, 55 sleeping, 0 stopped, 0 zombie
Cpu(s): 0.0%us, 0.3%sy, 0.0%ni, 99.7%id, 0.0%wa, 0.0%hi, 0.0%si, 0.0%st
Mem: 1019600k total, 324496k used, 695104k free, 8512k buffers
Swap: 0k total, 0k used, 0k free, 264812k cached
PID USER PR NI VIRT RES SHR S %CPU %MEM TIME+ COMMAND
1635 root 20 0 17300 1200 920 R 0.3 0.1 0:00.01 top
1 root 20 0 24188 2120 1300 S 0.0 0.2 0:00.56 init
2 root 20 0 0 0 0 S 0.0 0.0 0:00.00 kthreadd
3 root 20 0 0 0 0 S 0.0 0.0 0:00.11 ksoftirqd/0
Nice 值的范围在 -19/-20(最高优先级)和 19/20(最低优先级)之间,具体取决于系统。
要运行具有特定 nice 值的程序,可以使用 nice
命令:
- nice -n 15 command_to_execute
这仅在开始新程序时有效。
要更改已在执行的程序的 nice 值,您可以使用名为 renice
的工具:
- renice 0 PID_to_prioritize
结论
进程管理是 Linux 的基本组成部分,几乎在所有情况下都有用。即使您没有执行任何实际的系统管理,能够追踪卡住的进程并小心处理它们也非常有帮助。
接下来,您可能想学习如何使用 netstat
和 du
来监控其他服务器资源。