3人参与 • 2026-09-18 • Linux
半夜两点被叫起来处理一台业务机响应变慢,登上去第一件事肯定不是重启服务,而是把 cpu、内存、进程、磁盘 io、网口流量这几个维度挨个扫一遍。这套 动作做过几十次之后你会发现,linux 系统里真正高频用到的信息查看命令其实就那二十来个,剩下的都是它们的变体或者祖宗辈的老写法。这篇东西就是把这些命令按"看什么、怎么看、看到数值之后怎么判断"的顺序整理出来,覆盖 cpu、内存、进程、网口、磁盘、硬件这几大类,尽量把每个参数背后的含义和常见的误判点讲清楚。适合刚接手 linux 服务器的新人,也适合平时主要写业务代码、偶尔要自己登机器排查问题的开发同学。命令本身不难记,难的是看到一堆数字之后知道哪个是异常、哪个只是正常波动,这才是真功夫。
很多人一上来就 top ,然后盯着跳动的数字发呆,其实是没有先建立分类的概念。系统信息大致可以分成三层:静态硬件层(这台机器到底是什么配置)、动态资源层(cpu、内存、io、网络的实时消耗)、进程与连接层(具体是谁在消耗)。这三层的查看命令、判读标准、采样方式都不一样,混在一起看只会越看越乱。
静态硬件层回答的是"这台机器有多少家底",典型命令有 lscpu 、 lsblk 、 lspci 、 dmidecode 、 free -h 的 total 列。这类信息基本不会变,除非你热插拔硬盘或者改配置。拿到一台陌生机器,我习惯先把这一层过一遍,记下核数、内存总量、磁盘数量与类型、网卡速率,后面所有"是否异常"的判断都要跟这些基准值对比。
动态资源层回答的是"现在消耗了多少", top 、 vmstat 、 iostat 、 sar 都属于这一类。它们的核心特点是需要采样,单次输出几乎没有意义,必须看趋势。比如 vmstat 1 5 是每秒采一次共采五次, iostat -x 1 是持续输出,看的就是连续性。
进程与连接层则是把上面的消耗定位到具体对象:哪个 pid 吃了 cpu,哪个端口被谁占着,哪个进程打开了这个已删除的大文件。 ps 、 ss 、 lsof 、 fuser 是主力。
提示:排查顺序建议从静态层确认基准,再到动态层找异常维度,最后到进程层定位元凶。反过来直接看 top ,很容易被瞬时峰值带偏。
这是新手最容易踩的坑。cpu 使用率如果只看 top 刷新出来的那一瞬间,很可能看到 90% 就慌了,实际上那只是某个批处理任务刚起来的瞬时冲高。正确的做法是看一段时间内的平均值,比如 top 里按 1 切到每核视图观察几秒,或者直接用 vmstat 1 10 拿十秒的数据。
磁盘 io 同理。 iostat 第一次输出的那一行通常是从开机到现在的累计平均值,不是当前值,真正要看的是第二次及以后的采样行。这个细节官方文档里写得比较隐晦,但实际排查中如果拿第一行当当前值,结论会完全跑偏。
网络流量也一样, sar -n dev 1 5 采五次,看的是每秒的包量和字节数变化,单看 /proc/net/dev 的累计计数只能算总账。
free 默认按 kb 输出, df -h 才是人类可读, iostat 的 kb_read/s 是每秒千字节, ethtool 报的是 mb/s 而 sar 报的是 kb/s,中间差了一个 8 倍的换算。我自己就干过把网卡 1000mb/s 当成 1000mb/s 的事,然后算带宽利用率算出了个荒唐结果。
把这几个换算关系背下来会省很多事:1 字节 = 8 比特,1 mb = 1024 kb,网卡速率标称的是比特。所以一块千兆网卡的理论极限大约是 125 mb/s, sar 里看到 110000 kb/s 就已经接近打满了。
cpu 相关的命令分两拨,一拨认硬件(这是什么 cpu、几个核几个线程、支持什么指令集),一拨看负载(现在忙不忙、谁在忙)。这两拨不要混着用, lscpu 看不出当前负载, top 也看不出你这颗 u 有没有 avx 指令集。
lscpu 是首选,输出整齐,直接告诉你架构、cpu 型号、核心数、线程数、缓存层级、numa 节点。几个关键字段需要看懂:
cpu(s) :逻辑 cpu 总数,也就是 top 里按 1 能看到的条数thread(s) per core :每核线程数,2 表示开了超线程core(s) per socket :每颗物理 cpu 的核心数socket(s) :物理 cpu 颗数它们的关系是 cpu(s) = socket(s) × core(s) per socket × thread(s) per core 。一台双路、每路 16 核、开了超线程的机器, cpu(s) 就是 64。这个数字决定了后面 load average 该怎么判读,非常重要。
cat /proc/cpuinfo 信息更原始更全,但一股脑输出几百行,人眼很难看。它的价值在于脚本化——比如批量查所有机器是否支持某个指令集时, grep -o 'avx512' /proc/cpuinfo | head -1 就很方便。日常人工查看还是 lscpu 舒服。
lscpu | grep -e 'model name|socket|core|thread|numa'
uptime 会输出三个数字,分别是过去 1 分钟、5 分钟、15 分钟的平均负载。很多人以为它表示 cpu 使用率,其实不是——它统计的是运行队列中可运行和不可中断状态的进程数,包含了等待 io 的进程。所以一台 cpu 很闲但磁盘卡死的机器,load 一样会飙到很高。
判读标准是拿它跟逻辑 cpu 核数比。64 核的机器 load 到 30 都算轻松,4 核的机器 load 到 8 就明显过载了。我自己的经验阈值是:load / 核数 小于 0.7 属于健康,0.7 到 1.0 需要关注,超过 1.0 且持续超过 5 分钟就要介入看了。
三个数字的走势也能说明问题。如果 1 分钟很高、15 分钟很低,说明是刚起来的突发流量;如果三个都很高且接近,说明是持续性压力,这种通常更难处理,得从根上找原因。
top 是最直观的,进去之后几个操作必须会:按 p 按 cpu 排序,按 m 按内存排序,按 1 展开每核视图,按 h 显示线程,按 c 显示完整命令行。这几个按键记住之后, top 能解决八成问题。
但 top 有个毛病:默认刷新太快,跳来跳去不好截图也不好观察。我更喜欢在脚本或者长期观察场景下用 ps 排序:
ps -eo pid,ppid,user,%cpu,%mem,stat,etime,cmd --sort=-%cpu | head -15
这里 etime 是进程运行时长,很有用。如果一个进程 cpu 高而且运行了很久,那大概率是慢查询或者死循环;如果刚起来 cpu 就高,可能是正常的初始化或编译任务。 stat 列里出现 d 状态要特别留意,那是不可中断睡眠,通常卡在 io 上。
再深入一点可以用 pidstat ,它能按进程甚至按线程持续采样:
pidstat -u 1 5 # 按进程看 cpu pidstat -t -p 12345 1 5 # 按线程看指定进程
pidstat -t 这个用法在排查 java 应用时特别好使,因为 jvm 是一个大进程, top 只能看到整体占用, pidstat -t 能直接看到是哪个线程在烧 cpu,拿着线程 id 转成十六进制再去 jstack 里搜,一抓一个准。
有时候整体 cpu 使用率不高,但业务就是慢。这种情况要怀疑是不是单线程瓶颈——程序只跑在一个核上,那个核 100%,其他核全闲着, top 里的整体数字只有 1/64,看起来一点都不高。
检查方法是在 top 里按 1 展开每核视图,看是否有单核长期接近 100%。 mpstat -p all 1 也能达到同样效果,而且输出更适合脚本处理:
mpstat -p all 1 3
如果确认是单核打满,方向就是找程序里的单线程瓶颈,或者看能不能通过多进程、多线程模型打散。也有例外情况,比如某些网络中断处理会绑定到固定核上,这时候可能是网卡中断分配不均,需要调整 /proc/irq/*/smp_affinity ,这个属于进阶操作,改之前一定要确认清楚。
注意: %wa (io 等待)也算在 cpu 的 idle 之外,如果 top 里看到 wa 很高,别急着重启 cpu 相关服务,问题八成在磁盘或网络存储上。
内存这块的坑比 cpu 还多,因为 free 的输出列名会让第一次看的人误解。最典型的就是看到 free 只剩几百 mb 就以为内存要爆了,实际上 linux 会把大量空闲内存拿去做文件缓存,需要的时候随时能回收。
假设输出长这样:
total used free shared buff/cache available
mem: 31gi 8.2gi 1.1gi 412mi 22gi 22gi
swap: 2.0gi 0b 2.0gi
total 是物理内存总量。 used 是已使用,注意它包含了部分已被应用占用的缓存。 free 是完全空闲的,也就是真的一点都没被用到的内存,这个数字小不代表有问题。 buff/cache 是内核用于块设备缓存和文件系统缓存的部分,这部分是"借"给内核用的,应用需要时可以快速释放。
关键看 available 。这一列是内核估算的"新应用还能申请到多少内存",它把可回收的 cache 也算进去了。真正判断内存是否紧张,看 available 是不是还很充裕,而不是看 free 。
很多从 windows 转过来的同学会觉得缓存占了 22g 很浪费,其实这正是 linux 内存管理的效率体现。反复读同一批文件时命中缓存,速度比读磁盘快好几个数量级。
有时候确实需要手工清缓存,比如做内存基准测试要排除缓存干扰,或者某些老程序对内存可用量的判断有 bug。命令是:
sync # 先把脏页刷盘,必须做 echo 3 > /proc/sys/vm/drop_caches
echo 3 表示同时释放页缓存、目录项和 inode 缓存。 echo 1 只释放页缓存, echo 2 只释放 dentry 和 inode。
注意:这个操作本身代价不小,清完之后所有后续读文件都得走磁盘,可能造成短时间的 io 峰值。生产环境除非必要别乱敲。
想更细地看内存构成,读 /proc/meminfo 更全,里面 memtotal 、 memfree 、 memavailable 、 cached 、 buffers 、 dirty 、 slab 都是常用字段。其中 dirty 是还没写回磁盘的脏页大小,如果这个数字长期偏高且不下降,说明写的速度超过了磁盘的吞吐能力,迟早要出问题。
进程内存持续增长不释放,是最让人头疼的问题之一。定位的基本流程是:先找到嫌疑进程,再看它的内存构成,最后确认是堆还是栈或者 mmap 的问题。
按内存排序和按 cpu 排序其实命令一样,只是排序字段换一下:
ps -eo pid,user,%mem,rss,vsz,cmd --sort=-rss | head -15
rss 是常驻内存,也就是真正占着物理内存的部分; vsz 是虚拟内存总量,包含了还没实际分配的部分。看内存泄漏主要盯 rss , vsz 大不一定有问题。
确定了 pid 之后, pmap -x pid 能列出这个进程的内存映射明细, cat /proc/pid/smaps 信息更全但更长。这两个工具在追查"内存到底去哪了"的时候能给出地址段的分布,配合 gdb 或者语言自带的 dump 工具可以进一步定位。
smem 这个工具值得装一下,它和 ps 最大的区别是会处理共享内存的重复计算问题。多个进程共同映射同一个共享库时, ps 会把库的大小在每个进程里都算一遍,加起来远超物理内存,容易吓人。 smem 用 pss 来处理这件事,统计更接近真实。
free 输出里的 swap 行别忽略了。swap 使用量持续增长通常意味着物理内存不够,系统开始往磁盘上倒腾。这时候机器的表现是响应变慢但 cpu 不一定高,因为瓶颈在磁盘 io 上。
vmstat 1 5
看 si 和 so 两列,分别是每秒从 swap 读入和写入的量。如果这两个值长期非零,基本可以确认内存不足。短期偶尔跳一下没事,长期持续就要考虑加内存或者优化程序了。
如果进程被杀掉了,去 dmesg 里找 oom 记录:
dmesg -t | grep -i -e 'oom|killed process'
-t 参数会把时间戳转成人类可读的格式,方便跟日志对时间。oom killer 触发时会打印被选中进程的 pid、内存占用、评分,这些信息对于分析"为什么偏偏杀了我这个进程"很有帮助。oom 评分大致和进程占用的内存成正比,但可以用 /proc/pid/oom_score_adj 调整,这个属于调优范畴了。
进程这一块命令最多,但常用的就那么几个组合。核心思路是:先用 ps 或者 top 找到嫌疑进程,再用 ss 或者 lsof 看它占着哪些资源,最后回到 ps 确认它的父子关系和启动参数。
ps 有 bsd 风格和 unix 风格两套参数体系,新手经常混用导致参数被误解析。bsd 风格不加横线, ps aux ;unix 风格加横线, ps -ef 。两者输出的内容差不多,只是列名和排序不同。
ps aux 的列是 user pid %cpu %mem vsz rss tty stat start time command , ps -ef 的列是 uid pid ppid c stime tty time cmd 。
我个人的习惯是:需要快速看 cpu 和内存占比用 aux ,需要看父子进程关系用 -ef 。两者都用 grep 过滤时记得排除自己那条 grep 进程:
ps -ef | grep nginx | grep -v grep
或者更优雅的写法:
pgrep -a nginx
pgrep 和 pkill 是一对,前者按名字找 pid,后者按名字杀进程。 pkill 用之前一定要用 pgrep 确认命中范围,不然很容易误杀。
pstree -p 能直观地把进程树画出来,排查"某个服务被谁拉起来的"这种问题时特别好用,因为它把父子关系用缩进的方式呈现了,一眼就能看出层级。
top 进去之后按 f 可以自定义显示哪些列,按 o 可以设置排序字段,按 k 可以直接杀进程,按 u 只看指定用户,按 z 开彩色显示。这些功能知道的人不多,但用熟了效率提升明显。
top -b -n 1 是批处理模式输出一次就退出,适合写进脚本或者重定向到文件里。想抓某个时间点的快照做对比,这个用法比截图靠谱。
top -h -p pid 可以只显示指定进程的线程,和前面 pidstat -t 效果类似,但交互性更好。
还有一个容易被忽略的: top 输出开头那几行是全局信息, load average 、 tasks 、 %cpu(s) 、 mib mem 、 mib swap 都在这几行里。很多人只看下面的进程列表,其实上面这几行才是第一判断依据。特别是 tasks 那行的 running 、 sleeping 、 zombie 数字,如果 zombie 不为零且持续增长,说明有父进程没有正确回收子进程,需要查代码。
提示:僵尸进程本身不占 cpu 和内存,但会占用 pid 表项。如果数量持续增长到几万,pid 会被耗尽,新进程无法创建。解决方法通常是找到父进程重启它,或者修复代码里的 wait 逻辑。
netstat 是老牌工具,但已经被 ss 取代了。 ss 速度更快,尤其是在连接数很多的时候,因为它是直接从内核空间取数据,而 netstat 要遍历 /proc 。
常用组合:
ss -tulnp # 看所有监听中的 tcp 和 udp 端口 ss -tan state established | head -20 # 看已建立的连接 ss -s # 看连接数汇总统计
参数含义: -t tcp, -u udp, -l 只看监听, -n 不做域名解析(重要,不然会很慢), -p 显示进程,需要 root 权限。
如果想知道某个端口被谁占了,除了 ss -tulnp | grep :8080 ,还可以用 lsof -i :8080 。 lsof 的视角是"进程打开了哪些文件",而 socket 在 linux 里也是文件,所以它能从进程的角度反向查。
fuser -n tcp 8080 是另一个思路,直接告诉你是哪个 pid,适合写脚本时用。
lsof 全称是 list open files,功能极其强大,但输出也极其冗长,必须配合过滤条件用。
查某个进程打开了哪些文件:
lsof -p 12345 | head -30
查某个目录被谁占用(比如卸载文件系统时提示 busy):
lsof +d /mnt/data
查某个文件被谁打开:
lsof /var/log/app.log
这个命令有个实际价值极大的用法:删除大文件后磁盘空间没释放。原因是文件被某个进程还持有句柄, rm 只是删掉了目录项,inode 还在。这时候用 lsof | grep deleted 就能找到是哪个进程还挂着这个文件,重启对应进程或者让它重新打开日志文件,空间就能回收。
lsof -n | grep deleted | awk '{print $1,$2,$7,$9}' | sort -k3 -n -r | head
这个组合会按文件大小倒序列出所有已删除但仍被占用的文件,非常实用。
磁盘问题是最容易引起"服务假死"的,因为磁盘满了之后很多程序写日志失败就卡住了,表现是服务无响应但 cpu 和内存都很正常。所以磁盘检查要养成习惯,至少把容量和 inode 两条线都看一遍。
df -h # 按挂载点看容量 df -i # 按挂载点看 inode 使用率
df -h 的输出里重点看 use% 那一列,超过 80% 就该关注了,超过 90% 需要立即处理。注意有些文件系统比如 /dev/shm 是内存文件系统,它的大小跟你物理内存有关,不是真的磁盘。
发现某个分区快满了,下一步是用 du 找大目录:
du -sh /* 2>/dev/null | sort -hr | head -10
-s 是汇总, -h 是人类可读,配合 sort -hr 按大小倒序。找到最大的那个目录之后,一层层往下钻,直到定位到具体的大文件。这个过程可以写成一个循环脚本,不过手工钻个三四层一般也够了。
du 有个坑:它会跟随符号链接(不加 -x 的情况下可能跨越文件系统),而且遍历大量小文件时非常慢。如果目录里文件数量特别多(十万级以上), du 可能需要几分钟,这时候要有耐心,或者用 ncdu 这种交互式工具,体验好很多。
这是最隐蔽的磁盘问题之一。 df -h 显示还有很多空间,但程序就是报 "no space left on device"。原因通常是 inode 用完了。
inode 是文件系统给每个文件分配的元数据结构,包含权限、时间戳、数据块指针等信息。每个文件(包括空文件)至少占一个 inode。如果某个目录下堆积了海量的小文件,比如 session 文件、临时文件、邮件队列,inode 就可能先于容量耗尽。
df -i
iuse% 那一列到 100% 就是这个问题了。处理方式是找到小文件最多的目录,通常是 /var/spool 、 /tmp 或者某个应用的缓存目录:
find /var/spool -type f | wc -l # 统计文件数 find /var/spool -type f -mtime +7 -delete # 删除 7 天前的文件
注意: find -delete 一定要先加 -print 空跑一遍确认命中的文件范围,确认无误再改成 -delete 。这个命令误删的案例太多了。
治本的办法还是从源头控制,比如限制日志目录的文件数、给临时文件加自动清理、调整应用的文件命名策略避免碎片化。
容量不紧张但 io 慢,也是很常见的场景。 iostat 是主力工具:
iostat -x 1 5
关注这几列: %util 表示设备繁忙程度,接近 100% 说明磁盘被打满了; await 是平均每次 io 的等待时间,单位毫秒,机械盘正常在 10ms 以内,ssd 应该在 1ms 以内,超过这个量级说明有瓶颈; aqu-sz 是平均队列长度,持续大于 1 说明有排队。
第一次输出的那一行通常是开机以来的平均值,从第二次开始才是当前采样值,这个前面提过,一定要记住。
iotop 是另一个视角,从进程角度看谁在读写磁盘:
iotop -o -p # 只看有 io 的进程,-p 显示进程而不是线程(新版本才有)
iotop 需要 root 权限,而且在 io 压力大的时候自身的开销也不小,不适合长期开着。
如果是网络存储(nfs、iscsi),io 的表现会更复杂, await 可能包含网络延迟。这时候最好同时在存储端和客户端两边看,能快速判断瓶颈在哪一侧。
lsblk 用树状结构展示块设备,一眼能看出哪块盘分了哪些区,哪些盘做了 raid 或者 lvm:
lsblk -o name,size,type,fstype,mountpoint,model
-o 指定输出列, model 能显示磁盘型号,排查时确认是不是某批有问题的盘很管用。
blkid 显示每个块设备的 uuid 和文件系统类型,改 /etc/fstab 时经常要用到 uuid,用这个命令取。
如果是物理机, smartctl -a /dev/sda 能读到磁盘的健康状态、通电时间、坏道计数等。重点关注 reallocated_sector_ct 、 current_pending_sector 、 media_wearout_indicator (ssd)这几个值,非零或者持续增长就要考虑换盘了。这个命令需要装 smartmontools 包。
smartctl -h /dev/sda # 快速看健康状态 smartctl -a /dev/sda # 完整信息
这个场景值得单独说,因为它太常见了。现象是服务无响应,但 top 看 cpu 内存都正常, ps 看进程还在。排查顺序我一般是这样:
df -h 看容量df -i 看 inode dmesg 有没有 io 错误 iostat -x 1 5 是不是 io 打满第 5 步容易被忽略。有时候 nfs 服务端挂了,客户端进程访问挂载点时会进入不可中断睡眠( d 状态), ps 里能看到,但 kill -9 杀不掉。这种情况只能等网络恢复或者重启机器。
网络和硬件这两块平时看得少,但出问题的时候信息量很大。网络重点是看连通性、速率、错误计数;硬件重点是看清单、温度、运行状态。
ip addr 已经全面取代 ifconfig ,输出更规整,功能也更全:
ip addr show # 看所有网卡和 ip ip -s link show eth0 # 看指定网卡的收发统计
ip -s link 的输出里有 rx errors 、 tx errors 、 dropped 这几列,持续增长说明有物理层问题,可能是网线、光模块或者交换机端口的问题。
ethtool 看的是网卡的物理层信息:
ethtool eth0
重点看 speed (协商速率,应该是 1000mb/s 或者 10000mb/s)、 duplex (应该是 full)、 link detected (应该是 yes)。如果协商成了半双工或者 100mb/s,说明网线或者对端设备有问题,即使链路是通的,性能也会差很多。
看实时速率用 sar :
sar -n dev 1 5
rxkb/s 和 txkb/s 是每秒的读写量,单位是千字节。换算成带宽利用率的话,千兆网卡对应 125000 kb/s 的极限。 rxpck/s 是每秒包数,如果这个数字特别高但字节数不高,说明都是小包,可能存在小包攻击或者应用设计问题。
lspci 列出所有 pci 设备,主要用来看显卡、网卡、raid 卡、hba 卡这些:
lspci | grep -i -e 'ethernet|raid|vga'
lsusb 列 usb 设备,服务器上用得少,但排查 u 盘、加密狗这类设备时有用。
dmidecode 是最全面的硬件信息工具,能读 bios、主板、内存条、cpu 的详细信息。需要 root 权限。
dmidecode -t memory # 内存条型号、容量、速率、插槽 dmidecode -t system # 整机型号和序列号 dmidecode -t bios # bios 版本
排查内存故障时, dmidecode -t memory 能看到每条内存的插槽位置和状态,如果某条报 unknown 或者容量不对,可能就是坏了或者没插紧。这个在报修的时候能提供关键信息。
提示: dmidecode 的 -t 参数后面接类型编号或者类型名都行, -t 17 就是 memory device, -t 16 是 physical memory array,两者的区别是前者是单条,后者是整个内存阵列。
物理服务器温度异常会触发降频,表现是 cpu 明明不满但性能差。 sensors 命令能读各类温度传感器,需要装 lm-sensors 包:
sensors
输出里会有 cpu 核心温度、主板温度、风扇转速。cpu 核心正常在 40 到 70 度之间,持续超过 85 度就要检查散热了。风扇转速字段如果显示 0 或者 n/a,可能是传感器不认,也可能是风扇真的停了,需要开机箱确认。
ipmitool 是服务器带外管理的利器,能读到更全面的状态:
ipmitool sensor list # 所有传感器 ipmitool sdr type temperature # 只看温度
这个命令走的是 bmc,需要配置好带外网络。优点是即使系统挂了也能读到硬件状态,做无人值守机房巡检特别好用。
最后补几个通用命令,第一次登上一台机器时习惯性敲一遍,能快速建立整体印象:
uname -a # 内核版本、架构、主机名 hostnamectl # 系统版本、内核、架构、虚拟化类型 cat /etc/os-release # 发行版信息 uptime # 开机时长和负载 who -b # 上次启动时间 last reboot | head # 重启历史
hostnamectl 的输出里会明确写出 virtualization: kvm 或者 vmware 之类,一眼就能分辨是物理机还是虚拟机,这个在很多场景下很重要。如果是容器环境, cat /proc/1/cgroup 或者 ls /.dockerenv 能判断是不是跑在容器里。
dmesg -t 是排查硬件和内核问题的第一手资料,启动过程的硬件识别、驱动加载、错误报警都在这。出了问题先看这个,比瞎猜快得多。 dmesg -t | tail -50 看最近的, dmesg -t | grep -i error 抓错误。
命令记熟了不代表会排查,真正的差距在于遇到现象时的判断速度和方向感。这一章把前面提到的判读标准汇总成表,再单独说几个容易误判的场景。
| 关注维度 | 首选命令 | 关键列/字段 | 异常判据 |
|---|---|---|---|
| cpu 全景 | lscpu | cpu(s)、socket、numa | 与预期配置不符 |
| cpu 负载 | uptime / top | load average | load / 核数 > 1.0 |
| cpu 分核 | mpstat -p all 1 | %usr、%sys、%iowait | 单核长期 100% |
| 内存概览 | free -h | available | available 接近 0 |
| 内存明细 | cat /proc/meminfo | dirty、slab | dirty 长期不降 |
| swap 活动 | vmstat 1 | si、so | 持续非零 |
| 内存泄漏 | ps -eo rss / pmap | rss 增长趋势 | 持续单调增长 |
| 进程排序 | ps --sort=-%cpu | %cpu、etime、stat | d 状态长期存在 |
| 线程级 cpu | pidstat -t | 单线程 %cpu | 某个线程持续高 |
| 端口占用 | ss -tulnp | listen、进程名 | 端口与预期不符 |
| 已删除文件 | lsof | grep deleted | size、pid | 占用大量空间 |
| 磁盘容量 | df -h | use% | > 90% |
| inode | df -i | iuse% | 100% |
| 目录大小 | du -sh * | 排序结果 | 异常大目录 |
| 磁盘 io | iostat -x 1 | %util、await | %util 接近 100 |
| 进程 io | iotop -o | disk read/write | 单进程持续高 |
| 块设备 | lsblk | type、mountpoint | 挂载关系异常 |
| 磁盘健康 | smartctl -h | smart overall | failed 或计数增长 |
| 网卡速率 | ethtool eth0 | speed、duplex | 低于预期 |
| 网络流量 | sar -n dev 1 | rxkb/s、txkb/s | 接近理论极限 |
| 网卡错误 | ip -s link | errors、dropped | 持续增长 |
| 温度 | sensors | core temp | > 85 度 |
| 内核日志 | dmesg -t | error、oom | 出现 oom 或 io error |
这张表可以打印出来贴在工位上,遇到问题先扫一眼找到对应命令,比凭记忆瞎敲效率高得多。
第一个是缓存占内存。前面说过了, free 那列小不代表缺内存,看 available 。新手看到 buff/cache 占 20 多 g 就急着清缓存,纯属折腾。
第二个是 load 高但 cpu 不高。这种情况八成是 io 等待,去看 %wa 和 iostat 。load average 统计的是运行队列长度,包含不可中断睡眠的进程,磁盘卡住的进程也算在里面。
第三个是磁盘有空间但写不进去。先查 inode,再查是不是文件被删了但句柄没释放。两个都用 df -i 和 lsof | grep deleted 就能覆盖。
第四个是端口明明没被占但启动报 address already in use。可能是 time_wait 状态的连接, ss -tan | grep time-wait | wc -l 看数量。time_wait 是正常的 tcp 状态,但如果数量特别大(几万),可能需要调整内核参数或者让应用复用连接。也可能是 bind 在了不同网卡但同一个端口上,仔细看 ss -tulnp 的 local address 列。
第五个是 top 的 cpu 加起来不到 100%。这是正常的,因为 %cpu(s) 那行里 us 、 sy 、 ni 、 id 、 wa 、 hi 、 si 、 st 加起来才是 100%。如果 st (steal time)很高,说明是虚拟机,宿主机把你的 cpu 抢走了,这种情况自己优化没用,得找平台方。
每次手敲这一串命令太累,几个办法可以省事。
第一个是写 alias。把 ps -eo pid,ppid,user,%cpu,%mem,stat,etime,cmd --sort=-%cpu | head -15 这种长命令缩成 pcpu , free -h 缩成 mem ,放进 ~/.bashrc 里。
alias pcpu='ps -eo pid,user,%cpu,%mem,stat,etime,cmd --sort=-%cpu | head -15' alias pmem='ps -eo pid,user,%cpu,%mem,rss,cmd --sort=-rss | head -15' alias ports='ss -tulnp' alias disks='df -h; echo; df -i'
第二个是写一个诊断脚本,把最常用的一组命令打包输出,起名叫 syscheck.sh ,需要的时候一跑,所有信息一次性出来。
#!/bin/bash echo "===== 系统概览 =====" hostnamectl | head -6 uptime echo "===== cpu =====" lscpu | grep -e 'model name|^cpu\(s\)|socket|thread' echo "===== 内存 =====" free -h echo "===== 磁盘容量 =====" df -h -x tmpfs -x devtmpfs echo "===== inode =====" df -i -x tmpfs -x devtmpfs echo "===== 磁盘 io =====" iostat -x 1 2 | tail -20 echo "===== 高 cpu 进程 =====" ps -eo pid,user,%cpu,%mem,stat,etime,cmd --sort=-%cpu | head -10 echo "===== 高内存进程 =====" ps -eo pid,user,%cpu,%mem,rss,cmd --sort=-rss | head -10 echo "===== 监听端口 =====" ss -tulnp
第三个技巧是用 watch 做定期刷新,适合盯某个指标的变化:
watch -n 2 'free -h; echo; df -h /data'
-n 2 是每两秒刷新一次。 watch -d 还能高亮变化的部分,看绝对值变化特别直观。
第四个是输出重定向归档。排查问题时把结果存下来,事后复盘或者给同事看都方便:
syscheck.sh > /tmp/syscheck_$(date +%f_%h%m).log 2>&1
用时间戳命名,多次执行不会互相覆盖。这些日志攒一段时间,对比不同时间点的数据,很多缓慢劣化的问题就浮出来了。
聊到这儿基本把 linux 系统信息查看的主干命令过了一遍。我自己这些年最大的体会是,命令本身两三天就能背熟,真正花时间的是建立"看到数值知道意味着什么"的直觉,而这个只能靠在真实故障里一次次对照、记录、复盘慢慢养。上面那张速查表和那个诊断脚本,是我自己在实际运维中反复改过好几版留下来的,你拿去按自己的环境稍微调整一下字段就能用,比临时抱佛脚翻文档靠谱得多。
以上就是linux服务器性能排查常用命令大全:cpu内存磁盘网络一次看懂的详细内容,更多关于linux性能排查命令的资料请关注代码网其它相关文章!
您想发表意见!!点此发布评论
版权声明:本文内容由互联网用户贡献,该文观点仅代表作者本人。本站仅提供信息存储服务,不拥有所有权,不承担相关法律责任。 如发现本站有涉嫌抄袭侵权/违法违规的内容, 请发送邮件至 2386932994@qq.com 举报,一经查实将立刻删除。
发表评论