先敲 df -i 确认 inode 耗尽:若 df -h 显示磁盘空间充足(如 65% 使用率)但 df -i 显示 iuse% 为 100%、ifree 为 0,即说明文件系统块空间尚余,但 inode 已用尽,无法新建文件或目录。

先敲 df -i,别看 df -h ——90% 的 “No space left on device” 根本不是空间满,而是 inode 耗尽。
怎么确认是 inode 耗尽,而不是磁盘块空间满
直接对比两条命令输出:
-
df -h显示 / 分区使用率只有 65%,但mkdir、touch、docker run全报No space left on device; -
df -i显示同一分区的IUse%是 100%,IFree为 0; - 这时基本可以确定:文件系统还有空闲块,但“发不了新户口本”了。
注意:df -i 必须加 -i,不加就是查空间;df -ih 可读性更好,但本质和 df -i 一样。别用 du -sh 去判断 inode 问题——它只统计大小,不统计文件数量。
怎么快速定位哪个目录在疯狂吃 inode
不能靠 du -sh /*,它只反映空间占用;得按“文件数量”往下筛。推荐用带 -xdev 的 find 统计:
Linux 性能分析与调优专家,覆盖 CPU、内存、磁盘 I/O、网络、内核参数、编译优化、容器/K8s。适用场景:系统卡顿/高负载、内存不足/OOM/Swap 高、CPU 异常/iowait 高。
- 从根开始查一级子目录的文件总数:
for i in /*; do echo "$i:"; find "$i" -xdev -type f | wc -l; done 2>/dev/null | sort -k2,2nr; - 发现
/var下有 80 万文件,就进它:cd /var && for i in */; do echo "$i:"; find "$i" -xdev -type f | wc -l; done 2>/dev/null | sort -k2,2nr; - 常见重灾区:
/var/spool/postfix/maildrop(cron 邮件堆积)、/var/log/journal(systemd 日志碎片)、/tmp(未清理的 session 或临时文件)、/var/lib/docker/overlay2(容器层残留); - 一定要加
-xdev,否则会跨挂载点把其他文件系统(比如/proc、/sys)也算进来,结果失真。
删海量小文件时,rm * 会失败,怎么办
当一个目录下有几万甚至上百万个小文件时,rm * 会因参数列表过长直接报错:Argument list too long。必须绕过 shell 参数限制:
- 安全清理(先预览):
find /path/to/dir -type f -print | head -n 5看几个文件名,确认无业务关键文件; - 分批删除(推荐):
find /path/to/dir -type f -print0 | xargs -0 -n 1000 rm -f; - 按时间删旧文件(适合日志类):
find /var/log/app -name "*.log" -mtime +7 -delete; - 慎用
rm -rf直接删整个目录——如果该目录被进程打开(如 journalctl 正在写),可能触发不可预期行为; - 删完后立刻跑
df -i确认IFree是否回升,别只信ls | wc -l——它不反映文件系统真实释放状态。
为什么删完文件,df -i 还是 100%
有两个常见原因容易被忽略:
- 进程仍在持有已删除文件的句柄(比如 tail -f 正在读某个日志,你
rm它后,inode 并未真正释放);查法:lsof +L1或find /proc/*/fd -ls 2>/dev/null | grep deleted; - 文件系统本身是 ext4 且创建时 inode 数量设得太小(比如 10GB 分区却只分配了 10 万个 inode),后续无法扩容;这种只能重建文件系统或迁移数据;
- 某些场景下,
systemd-journald会把日志按 UID 分散到大量小文件里,journalctl --vacuum-size=200M不一定能清掉 inode,得配合--vacuum-files=10控制文件数量。
真正棘手的不是“怎么删”,而是“删完是否生效”——很多人的操作停在 rm 就以为结束了,其实没验证释放结果,也没检查是否有残留进程锁住 inode。










