Linux系统管理——TOP命令详解与性能分析

1、Top命令介绍

Linux系统中,Top命令主要用于实时运行系统的监控,包括Linux内核管理的进程或者线程的资源占用情况。

这个命令对所有正在运行的进程和系统负荷提供不断更新的概览信息,包括系统负载、CPU利用分布情况、内存使用、每个进程的内容使用情况等信息。

2、Top命令使用

Top的命令介绍如下

top -hv|-bcHiOSs -d secs -n max -u|U user -p pid -o fld -w [cols]

常用的Top指令有:

top:启动top命令
top -c:显示完整的命令行
top -b:以批处理模式显示程序信息
top -S:以累积模式显示程序信息
top -n 2:表示更新两次后终止更新显示
top -d 3:设置信息更新周期为3秒
top -p 139:显示进程号为139的进程信息,CPU、内存占用率等
top -n 10:显示更新十次后退出

除此之外,在top进程运行过程中,两个最重要的功能是查看帮助(h)和退出(qCtrl+C)。

3、Top信息详解

top展示界面由从上到下3部分组成

  1. 概览区域
  2. 表头
  3. 任务区域
  4. 还有一个输入/消息行,位于概览区域和表头之间。

image-20240516130346165

[root@VM-10-17-centos ~]# top
top - 13:04:25 up 729 days, 16:00, 1 user, load average: 0.06, 0.07, 0.06
Tasks: 121 total, 1 running, 120 sleeping, 0 stopped, 0 zombie
%Cpu(s): 0.5 us, 0.5 sy, 0.0 ni, 98.8 id, 0.2 wa, 0.0 hi, 0.0 si, 0.0 st
KiB Mem : 8008648 total, 176544 free, 6956268 used, 875836 buff/cache
KiB Swap: 0 total, 0 free, 0 used. 762252 avail Mem

PID USER PR NI VIRT RES SHR S %CPU %MEM TIME+ COMMAND
1323 root 20 0 50088 912 580 S 2.0 0.0 14955:27 rshim
23266 root 20 0 1133744 184572 10924 S 2.0 2.3 1969:13 YDService
18901 root 20 0 757596 17912 2572 S 1.0 0.2 1149:30 barad_agent
6383 mysql 20 0 7262308 5.9g 5216 S 0.3 77.1 3250:47 mysqld
18900 root 20 0 165044 9388 1872 S 0.3 0.1 72:34.96 barad_agent
27634 root 20 0 162116 2292 1600 R 0.3 0.0 0:00.37 top
29175 rabbitmq 20 0 2749496 140500 3936 S 0.3 1.8 2329:30 beam.smp
1 root 20 0 43716 3700 2184 S 0.0 0.0 93:28.64 systemd
2 root 20 0 0 0 0 S 0.0 0.0 0:37.44 kthreadd
4 root 0 -20 0 0 0 S 0.0 0.0 0:00.00 kworker/0:0H
6 root 20 0 0 0 0 S 0.0 0.0 12:27.19 ksoftirqd/0
7 root rt 0 0 0 0 S 0.0 0.0 6:14.58 migration/0
8 root 20 0 0 0 0 S 0.0 0.0 0:00.00 rcu_bh
9 root 20 0 0 0 0 S 0.0 0.0 522:15.48 rcu_sched
10 root 0 -20 0 0 0 S 0.0 0.0 0:00.00 lru-add-drain

3.1 概览区详解

top - 13:04:25 up 729 days, 16:00,  1 user,  load average: 0.06, 0.07, 0.06
  • 程序或者窗口的名称:top
  • 当前时间和系统的启动时间:13:04:25
  • 系统运行时间,未重启的时间,时间越长系统越稳定:up 729 days, 16:00 表示启动了729天又16小时整
  • 总共的用户数量:1 user
  • 过去1、5和15分钟的系统平均负载:load average: 0.06, 0.07, 0.06
    • 系统平均负载:单核CPU情况下,0.00 表示没有任何负荷,1.00表示刚好满负荷,超过1侧表示超负荷,理想值是0.7;
    • 多核CPU负载:CPU核数 * 理想值0.7 = 理想负荷,例如:4核CPU负载不超过2.8何表示没有出现高负载。
Tasks: 121 total,   1 running, 120 sleeping,   0 stopped,   0 zombie
%Cpu(s): 0.5 us, 0.5 sy, 0.0 ni, 98.8 id, 0.2 wa, 0.0 hi, 0.0 si, 0.0 st

这两行显示了任务数量和CPU状态

  • 第一行该信息对Task进行分类,包括running、sleeping、stopped、zombie四类,显示了系统中正在运行的任务的状态统计信息。上述信息具体拆开来说表示如下:

    • total:这里有121个任务总数;
    • running:其中有1个任务正在运行;
    • sleeping:120个任务正在睡眠;
    • stopped:0个任务已停止;
    • zombie:0个任务为僵尸进程。
  • 第二行显示CPU的状态百分比%Cpu(s): CPU使用率的统计信息。

    • us (user): 用户空间进程占用CPU的时间百分比(重要);
    • sy (system): 内核空间进程占用CPU的时间百分比(重要);
    • ni (nice): 用户进程以优先级调整过的占用CPU的时间百分比;
    • id (idle): CPU空闲的时间百分比(重要);
    • wa (IO-wait): CPU等待I/O操作的时间百分比;
    • hi (hardware interrupt): CPU处理硬件中断的时间百分比;
    • si (software interrupt): CPU处理软件中断的时间百分比;
    • st: 被虚拟化环境偷取的时间百分比(如果当前处于一个hypervisor下的vm,实际上hypervisor也是要消耗一部分CPU处理时间的)。
KiB Mem :  3994720 total,   525876 free,   595492 used,  2873352 buff/cache
KiB Swap: 2097148 total, 2096624 free, 524 used. 3114400 avail Mem

KiB Mem : 8008648 total, 176544 free, 6956268 used, 875836 buff/cache
KiB Swap: 0 total, 0 free, 0 used. 762252 avail Mem

这两行表示内存的使用情况

  • 第一行表示物理内存,分为total(物理内存总量)、 free(空闲内存总量)、 used(使用的物理内存总量)、 buff/cache(用作内核缓存的内存量)
  • 第二行表示虚拟内存,分为totalfreeusedavail(预计可用虚拟内存量)
提示:
1、默认单位是KiB,使用按键E可以切换任务区中的单位为MiB、GiB、TiB、PiB、EiB。
2、单位换算
KiB = kibibyte = 1024 bytes
MiB = mebibyte = 1024 KiB = 1,048,576 bytes
GiB = gibibyte = 1024 MiB = 1,073,741,824 bytes
TiB = tebibyte = 1024 GiB = 1,099,511,627,776 bytes
PiB = pebibyte = 1024 TiB = 1,125,899,906,842,624 bytes
EiB = exbibyte = 1024 PiB = 1,152,921,504,606,846,976 bytes

3.2 任务区

任务区是按照列的形式来显示的,并且有多个字段可以用来查看进程的状态信息。

  PID USER      PR  NI    VIRT    RES    SHR S  %CPU %MEM     TIME+ COMMAND               
1323 root 20 0 50088 912 580 S 2.0 0.0 14955:27 rshim
23266 root 20 0 1133744 184572 10924 S 2.0 2.3 1969:13 YDService
3.2.1 任务字段介绍

在top命令中按f按可以查看显示的列信息,按对应字母来开启/关闭列,大写字母表示开启,小写字母表示关闭。以下是是默显示列。

  • A: PID = (Process Id) 进程Id
  • E: USER = (User Name) 进程所有者的用户名
  • H: PR = (Priority) 优先级
  • I: NI = (Nice value) nice值。负值表示高优先级,正值表示低优先级
  • O: VIRT = (Virtual Image (kb)) 进程使用的虚拟内存总量,单位kb。VIRT=SWAP+RES
  • Q: RES = (Resident size (kb)) 进程使用的、未被换出的物理内存大小,单位kb。RES=CODE+DATA
  • T: SHR = (Shared Mem size (kb)) 共享内存大小,单位kb
  • W: S = (Process Status) 进程状态。D=不可中断的睡眠状态,R=运行,S=睡眠,T=跟踪/停止,Z=僵尸进程
  • K: %CPU = (CPU usage) 上次更新到现在的CPU时间占用百分比
  • N: %MEM = (Memory usage (RES)) 进程使用的物理内存百分比
  • M: TIME+ = (CPU Time, hundredths) 进程使用的CPU时间总计,单位1/100秒
  • X: COMMAND = (Command name/line) 命令名/命令行

更多的一些列介绍。

  • b: PPID = (Parent Process Pid) 父进程Id
  • c: RUSER = (Real user name)
  • d: UID = (User Id) 进程所有者的用户id
  • f: GROUP = (Group Name) 进程所有者的组名
  • g: TTY = (Controlling Tty) 启动进程的终端名。不是从终端启动的进程则显示为 ?
  • j: P = (Last used cpu (SMP)) 最后使用的CPU,仅在多CPU环境下有意义
  • p: SWAP = (Swapped size (kb)) 进程使用的虚拟内存中,被换出的大小,单位kb
  • l: TIME = (CPU Time) 进程使用的CPU时间总计,单位秒
  • r: CODE = (Code size (kb)) 可执行代码占用的物理内存大小,单位kb
  • s: DATA = (Data+Stack size (kb)) 可执行代码以外的部分(数据段+栈)占用的物理内存大小,单位kb
  • u: nFLT = (Page Fault count) 页面错误次数
  • v: nDRT = (Dirty Pages count) 最后一次写入到现在,被修改过的页面数
  • y: WCHAN = (Sleeping in Function) 若该进程在睡眠,则显示睡眠中的系统函数名
  • z: Flags = (Task Flags <sched.h>) 任务标志,参考 sched.h
提示:相关属性有很多,可以使用man top查看,这里先列举这些。
3.2.2 字段管理

我们输入top后,默认只显示一部分属性信息,我们可以自行管理想要的属性信息。

我们输入F或者f,进入字段管理功能,用于选择想要的字段信息

按键 功能
光标上下移动选择
空格d 切换
s 设置为排序依据字段
aw 在4种窗口中切换:1.默认,2.任务,3.内存,4.用户
Esc键q 退出当前窗口

4、交互命令详解

top的功能很多,基本能够查看进程的各种状态信息,其中还有一些交互式的命令,方便我们更好的查看系统状态。

在top主界面中,我们输入下面的命令
命令 功能
1 显示CPU详细信息,每核显示一行
h? 帮助信息查看,涵盖所有的快捷键
空格d 手动刷新界面信息
Esc键q 退出
B 粗体显示功能
ds 改变间隔时间
Ee 切换内存显示的单位,从KiBEiB
g 然后输入1-4其中一个数字,选择哪种窗口(1.默认,2.任务,3.内存,4.用户)
H 进程、线程显示切换
k 输入PID信息,杀掉一个任务
Z 改变配色

我们可以看到top默认的排序列是“%CPU”。但也可以通过”shift + >”或”shift + <”可以向右或左改变排序列,下图是按一次”shift + >”的效果图

image-20240516144558989

按”shift + >”后改变为按 “%MEM” 进行排序

image-20240516144715052

上面介绍了一些比较常见的交互式命令,还有更多需要你去探索哦!

5、性能分析与辅助

top命令是Linux上进行系统监控的首选命令,但有时候却达不到我们的要求,比如当前这台服务器运行着多个Sptingboot工程,但top命令的监控最小单位是进程,所以看不到我关心的java线程数和客户连接数,而这两个指标是java的web服务非常重要的指标,通常我用ps和netstate两个命令来补充top的不足。

# 监控java线程数:
ps -eLf | grep java | wc -l

# 监控80端口网络客户连接数
netstat -n | grep tcp | grep 80 | wc -l

另外在Linux系统“一切都是文件”的思想贯彻指导下,所有进程的运行状态都可以用文件来获取。系统根目录/proc中,每一个数字子目录的名字都是运行中的进程的PID,进入任一个进程目录,可通过其中文件或目录来观察进程的各项运行指标,例如task目录就是用来描述进程中线程的,因此也可以通过下面的方法获取某进程中运行中的线程数量(PID指的是进程ID):

  PID USER      PR  NI    VIRT    RES    SHR S  %CPU %MEM     TIME+ COMMAND               
31228 root 20 0 5729988 860656 8276 S 0.0 10.7 16340:50 java
31095 root 20 0 6013408 781780 15684 S 2.0 9.8 648:46.35 java
6091 root 20 0 6088820 675508 10664 S 0.0 8.4 224:37.15 java
28552 root 20 0 5933624 512756 6560 S 0.3 6.4 620:32.45 java
3298 root 20 0 5675160 448232 5968 S 0.0 5.6 631:44.08 java
11423 root 20 0 1038640 97240 17848 S 1.3 1.2 694:08.97 YDService

# 例如 如上多个 java PID,我需要查看 PID=31228 这个进程中线程数时可以使用以下命令
[root@VM-10-4-centos ~]# ls /proc/31228/task | wc -l
25

# 同样的在linux中还有一个命令pmap,来输出进程内存的状况,可以用来分析线程堆栈
pmap 31228