我有一台自己管理的 VPS。上面运行着一些 Node.js 项目、docker 项目和 crowdsec。通常CPU负载在20%左右。
有时服务器CPU 使用率飙升至 100%一切都停止了,我无法通过 SSH 连接到它,因为它没有响应。在我的 VPS 提供商的控制面板中,我可以看到一些监控信息,我可以看到它在很短的时间内达到 100%。
第一次发生这种情况时,我没有办法找到发生了什么,因为我没有设置资源监控,我唯一看到的就是我的系统日志:
Feb 14 07:18:46 v1274582 systemd[1]: [email protected]: Failed with result 'exit-code'.
Feb 14 07:18:46 v1274582 systemd[1]: Failed to start OpenVPN connection to server.
Feb 14 07:18:51 v1274582 systemd[1]: [email protected]: Scheduled restart job, restart counter is at 354411.
Feb 14 07:18:51 v1274582 systemd[1]: Stopped OpenVPN connection to server.
Feb 14 07:18:51 v1274582 systemd[1]: Starting OpenVPN connection to server...
Feb 14 07:18:51 v1274582 ovpn-server[3020525]: Options error: In [CMD-LINE]:1: Error opening configuration file: /etc/o>Feb 14 07:18:51 v1274582 ovpn-server[3020525]: Use --help for more information.
Feb 14 07:18:51 v1274582 systemd[1]: [email protected]: Main process exited, code=exited, status=1/FAILURE
Feb 14 07:18:51 v1274582 systemd[1]: [email protected]: Failed with result 'exit-code'.
Feb 14 07:18:51 v1274582 systemd[1]: Failed to start OpenVPN connection to server.
Feb 14 07:18:56 v1274582 systemd[1]: [email protected]: Scheduled restart job, restart counter is at 354412.
Feb 14 07:18:56 v1274582 systemd[1]: Stopped OpenVPN connection to server.
Feb 14 07:18:56 v1274582 systemd[1]: Starting OpenVPN connection to server...
Feb 14 07:18:56 v1274582 ovpn-server[3020557]: Options error: In [CMD-LINE]:1: Error opening configuration file: /etc/o>Feb 14 07:18:56 v1274582 ovpn-server[3020557]: Use --help for more information.
Feb 14 07:18:56 v1274582 systemd[1]: [email protected]: Main process exited, code=exited, status=1/FAILURE
Feb 14 07:18:56 v1274582 systemd[1]: [email protected]: Failed with result 'exit-code'.
Feb 14 07:18:56 v1274582 systemd[1]: Failed to start OpenVPN connection to server.
^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^@^>Feb 14 14:30:13 v1274582 systemd[1]: Mounting FUSE Control File System...
Feb 14 14:30:13 v1274582 systemd[1]: Mounting Kernel Configuration File System...
Feb 14 14:30:13 v1274582 systemd[1]: Condition check resulted in Rebuild Hardware Database being skipped.
Feb 14 14:30:13 v1274582 systemd[1]: Starting Flush Journal to Persistent Storage...
Feb 14 14:30:13 v1274582 systemd[1]: Condition check resulted in Platform Persistent Storage Archival being skipped.
Feb 14 14:30:13 v1274582 systemd[1]: Starting Load/Save Random Seed...
Feb 14 14:30:13 v1274582 systemd[1]: Starting Apply Kernel Variables...
从这个日志中可以看出,大约在早上 07:18 左右出现了问题,然后在我使用 CP 强制重启 VPS 后,它添加了新的 long。为了更好地为下一次做好准备,我atop
设置了每个日志的间隔为 10 分钟。
今天又发生了,我检查了一下atopsar
:
06:30:01 cpu %usr %nice %sys %irq %softirq %steal %guest %wait %idle _cpu_
06:40:01 all 30 0 8 0 0 0 0 0 161
0 16 0 4 0 0 0 0 0 80
1 15 0 4 0 0 0 0 0 81
06:50:01 all 30 0 7 0 0 0 0 0 162
0 15 0 3 0 0 0 0 0 81
1 15 0 4 0 0 0 0 0 81
07:00:01 all 31 0 10 0 0 0 0 0 159
0 16 0 5 0 0 0 0 0 79
1 16 0 5 0 0 0 0 0 79
07:10:01 all 30 0 7 0 0 0 0 0 163
0 14 0 4 0 0 0 0 0 82
1 15 0 4 0 0 0 0 0 81
14:30:13 ......................... logging restarted .........................
14:40:14 all 41 0 19 0 0 0 0 0 139
0 20 0 9 0 0 0 0 0 70
1 21 0 10 0 0 0 0 0 69
14:50:14 all 31 0 7 0 0 0 0 0 161
0 15 0 3 0 0 0 0 0 82
1 17 0 4 0 0 0 0 0 79
15:00:14 all 32 0 7 0 0 0 0 0 161
0 16 0 4 0 0 0 0 0 81
1 16 0 4 0 0 0 0 0 80
据我所知,10 分钟间隔不足以捕捉异常状态。我现在将其设置为 5 分钟,但我怀疑这是否足够,因为我不确定它达到 100% 的速度有多快。每隔几秒记录一次似乎有点太多了。
问题:您还能建议我做什么来找出导致此问题的原因?
谢谢你!
答案1
不,它不是因为消耗了 100% 的 CPU 而挂起,而是因为它挂起才消耗了 100% 的 CPU。
^@^@^@^@^@^@^@^@^@^@^@^@^@^
表示空字符(ASCII 0)。这意味着日志文件没有正确关闭并刷新到磁盘。反过来,这意味着您的系统在 07:18:56 时崩溃。崩溃的系统引发了内核恐慌,只是在那里循环消耗 100% 的 CPU while(1)
。有关发生了什么以及为什么恐慌的唯一信息可在系统控制台上找到。如果您没有系统控制台 - 请更换您的提供商,很可能是他导致了恐慌。
您可以验证系统是否崩溃 - ping 它。即使系统消耗了所有 CPU 并且所有磁盘都物理损坏,网络子系统也可以响应 ICMP ping。如果它无法响应 - 它已经损坏。
答案2
我会在后台运行一个脚本,当 CPU 使用率超过 80% 时,它会开始使用 atop 进行记录。例如
#!/bin/bash
while true; do
# Get current CPU usage
cpu_usage=$(top -bn1 | grep "Cpu(s)" | sed "s/.*, *\([0-9.]*\)%* id.*/\1/" | awk '{print 100 - $1}')
# Check if CPU usage is over 80%
if [ $(echo "$cpu_usage > 80" | bc) -eq 1 ]; then
# Start logging with atop
atop -w /path/to/logfile &
PID=$!
echo "CPU usage is over 80%, logging with atop (PID: $PID)"
wait $PID
fi
# Sleep for 1 minute before checking again
sleep 60
done
将此脚本保存为 cpu-monitor.sh 并使其可执行。要在后台运行它,请使用
nohup ./cpu_monitor.sh > /dev/null 2>&1 &