答案是磁盘空间被已删除但进程仍占用的文件等六类“隐身”对象占用。最常见的是rm后进程未重启导致日志文件句柄未释放,需用lsof +L1定位并重启服务;其次为journald日志膨胀、Docker overlay2堆积、LVM/Btrfs快照、挂载点覆盖及ext4保留空间。

磁盘显示已满但 du 找不到大文件,不是 du 错了,而是空间被“看不见”的东西占用了。核心思路是:先确认是不是真满了,再排查六类常见隐身占用源。
第一步:确认真实使用状态
别急着删,先交叉验证:
- 运行
df -h查看各挂载点使用率,重点关注 Use% ≥ 95% 的分区(比如/或/var) - 同步执行
df -i,检查 inode 是否耗尽(IUse% 达 100% 表示小文件塞爆了,哪怕空间还有余量) - 用
du -sh /* 2>/dev/null | sort -hr统计一级目录,加起来远小于df显示已用空间?说明问题不在常规文件里
第二步:查已被删除但进程仍占用的文件
这是最常见原因——文件被 rm 了,但 nginx、java、rsyslog 等进程还在往它的 fd 写日志,空间锁死不释放。
- 找这类“幽灵文件”:
lsof +L1或lsof / | awk '$5=="REG" && $11~/deleted/ {print $2,$9,$11}' - 看到 PID 和路径后,优先尝试平滑重启对应服务:
systemctl reload nginx或kill -USR1 $(pgrep rsyslog) - 若必须杀进程,确认业务影响后再执行:
kill -9 [PID]
第三步:检查 systemd-journald 日志膨胀
/var/log/journal/ 默认无大小限制,几十 GB 静悄悄吃掉空间,且 du 扫不到(journald 独占管理)。
- 查用量:
journalctl --disk-usage - 临时清理:
journalctl --vacuum-size=500M(保留最近 500MB)或journalctl --vacuum-time=2weeks - 永久限制:编辑
/etc/systemd/journald.conf,取消注释并设SystemMaxUse=500M和MaxRetentionSec=2week,然后systemctl restart systemd-journald
第四步:排查容器、快照与挂载覆盖
在 Docker/K8s 或 LVM/Btrfs 环境中,空间可能藏在更底层:
- Docker:检查
/var/lib/docker/overlay2下的merged和diff目录,用docker system df -v查镜像、容器、卷占用 - LVM/Btrfs/ZFS:运行
lvs、btrfs filesystem usage /或zfs list -t snapshot,看是否有未清理的快照 - 挂载覆盖:执行
mount | grep "on / ",确认是否某个新挂载点盖住了原/data或/home下的旧数据(卸载后du才能扫到)


















