Linux根据 PID 进行性能分析
根据 PID 进行性能分析
当需要深入分析某个特定进程的性能问题时,Linux 提供了多种强大的工具来监控和分析进程行为。以下是针对 PID 进行性能分析的完整方法:
1. 基础监控命令
1.1 top
- 实时监控指定进程
top -p PID1,PID2,PID3 # 监控多个PID
- 交互命令:
E
:切换内存单位(KB/MB/GB)c
:显示完整命令H
:显示线程视图
1.2 htop
(增强版)
htop --pid=PID
- 彩色显示,支持鼠标操作
- 按
F5
进入树状视图查看父子进程关系
1.3 ps
- 获取进程详情
ps -p PID -o %cpu,%mem,cmd,lstart,etime # 查看CPU/内存占用、启动时间、运行时长
2. CPU 分析
2.1 pidstat
- 进程级CPU监控
pidstat -p PID 1 3 # 每秒采样1次,共3次
- 关键指标:
%usr
:用户态CPU使用率%system
:内核态CPU使用率%CPU
:总CPU使用率
2.2 perf
- 性能分析
perf top -p PID # 实时函数级CPU分析
perf stat -p PID # 统计CPU周期/缓存命中等
perf record -p PID # 记录性能数据(生成perf.data)
2.3 火焰图生成
# 记录数据
perf record -F 99 -p PID -g -- sleep 30# 生成火焰图
perf script | FlameGraph/stackcollapse-perf.pl | FlameGraph/flamegraph.pl > flame.svg
- 需要安装 FlameGraph
3. 内存分析
3.1 pmap
- 内存映射详情
pmap -x PID # 显示详细内存分配
- 查看堆/栈/共享库的内存占用
3.2 valgrind
- 内存泄漏检测
valgrind --leak-check=full --show-leak-kinds=all -v ./program
- 适用于开发环境调试
3.3 统计内存使用
ps -p PID -o rss,vsz,cmd # RSS(物理内存), VSZ(虚拟内存)
cat /proc/PID/status | grep -i vm # 更详细的内存信息
4. I/O 分析
4.1 iotop
- 磁盘I/O监控
sudo iotop -p PID # 查看进程磁盘读写
4.2 strace
- 跟踪系统调用
strace -p PID -e trace=file # 只跟踪文件操作
strace -p PID -c # 统计系统调用次数
4.3 lsof
- 查看打开的文件
sudo lsof -p PID # 列出进程打开的所有文件/网络连接
5. 网络分析
5.1 ss
/netstat
- 连接查看
ss -tupn | grep PID # 查看进程的网络连接
5.2 nethogs
- 进程级带宽
sudo nethogs -p PID # 监控进程网络流量
5.3 tcpdump
- 抓包分析
sudo tcpdump -i any -w dump.pcap host x.x.x.x and port xx # 抓取特定流量
6. PostgreSQL 监控
6.1 实时查询监控
-- 查看长时间运行的查询
SELECT pid, now() - query_start AS duration, query
FROM pg_stat_activity
WHERE state = 'active'
ORDER BY duration DESC;-- 取消问题查询
SELECT pg_cancel_backend([PID]);-- 终止问题进程
SELECT pg_terminate_backend([PID]);
6.2 性能统计视图
-- 查看锁等待
SELECT blocked_locks.pid AS blocked_pid,blocking_locks.pid AS blocking_pid
FROM pg_catalog.pg_locks blocked_locks
JOIN pg_catalog.pg_locks blocking_locks ON blocking_locks.locktype = blocked_locks.locktypeAND blocking_locks.DATABASE IS NOT DISTINCT FROM blocked_locks.DATABASEAND blocking_locks.relation IS NOT DISTINCT FROM blocked_locks.relationAND blocking_locks.page IS NOT DISTINCT FROM blocked_locks.pageAND blocking_locks.tuple IS NOT DISTINCT FROM blocked_locks.tupleAND blocking_locks.virtualxid IS NOT DISTINCT FROM blocked_locks.virtualxidAND blocking_locks.transactionid IS NOT DISTINCT FROM blocked_locks.transactionidAND blocking_locks.classid IS NOT DISTINCT FROM blocked_locks.classidAND blocking_locks.objid IS NOT DISTINCT FROM blocked_locks.objidAND blocking_locks.objsubid IS NOT DISTINCT FROM blocked_locks.objsubidAND blocking_locks.pid != blocked_locks.pid;-- 查看缓存命中率
SELECT sum(heap_blks_read) as heap_read,sum(heap_blks_hit) as heap_hit,(sum(heap_blks_hit) - sum(heap_blks_read)) / sum(heap_blks_hit) as ratio
FROM pg_statio_user_tables;
6.3 配置日志记录
# postgresql.conf 中设置:
log_min_duration_statement = 1000 # 记录超过1秒的查询
log_lock_waits = on
log_temp_files = 0
6.4 分析日志
# 查找慢查询
grep "duration:" /var/lib/postgresql/log/postgresql-*.log | sort -nk3# 分析锁等待
grep "lock wait" /var/lib/postgresql/log/postgresql-*.log
7. 自动化监控脚本
#!/bin/bash
PID=$1echo "===== PostgreSQL 进程 $PID 分析 ====="
echo "1. 系统资源:"
ps -p $PID -o %cpu,%mem,rss,vsz,cmdecho -e "\n2. 数据库连接信息:"
psql -U postgres -c "SELECT datname, usename, state, query FROM pg_stat_activity WHERE pid = $PID;"echo -e "\n3. 最近查询统计:"
psql -U postgres -c "SELECT query, calls, total_time, rows FROM pg_stat_statements WHERE userid = (SELECT usesysid FROM pg_user WHERE usename = (SELECT usename FROM pg_stat_activity WHERE pid = $PID)) ORDER BY total_time DESC LIMIT 5;"
8. 典型问题诊断流程
-
CPU 100%问题:
top -p [PID]
→ 确认是Postgres进程SELECT pg_stat_activity
→ 找到问题查询EXPLAIN ANALYZE [query]
→ 分析执行计划
-
内存泄漏:
pmap -x [PID]
观察内存增长- 检查共享缓冲区配置 (
shared_buffers
)
-
I/O 瓶颈:
iotop -p [PID]
查看磁盘负载- 检查
random_page_cost
和effective_cache_size
-
锁等待:
- 查询
pg_locks
和pg_stat_activity
- 检查
deadlock_timeout
设置
- 查询
9. 高级分析工具
9.1 gdb
- 调试运行中进程
gdb -p PID # 附加到进程进行调试
9.2 bpftrace
- 动态追踪
# 监控进程的open()系统调用
sudo bpftrace -e 'tracepoint:syscalls:sys_enter_open { if (pid == PID) { printf("%s %s\n", comm, str(args->filename)); }
}'
9.3 systemtap
- 内核级分析
# 监控进程的上下文切换
sudo stap -e 'probe scheduler.cpu_on { if (pid() == target()) printf("PID %d migrated to CPU %d\n", pid(), cpu())
}'
10. /proc 文件系统
通过 /proc/PID/
获取详细数据:
cat /proc/PID/stat # 进程状态(CPU/内存等)
cat /proc/PID/io # I/O统计
cat /proc/PID/sched # 调度信息
cat /proc/PID/fd # 打开的文件描述符
11. 典型问题诊断流程
- CPU高:
top -p PID
→perf top -p PID
→ 火焰图分析
- 内存泄漏:
pmap -x PID
→valgrind
检测
- I/O瓶颈:
iotop -p PID
→strace -p PID -e trace=file
- 网络问题:
ss -tupn | grep PID
→tcpdump
抓包
12. 可视化工具推荐
工具 | 用途 |
---|---|
nmon | 实时监控单个进程资源 |
glances | 综合监控界面 |
NetData | 网页版实时监控 |
掌握这些方法后,你可以精准定位任何进程的性能瓶颈!