在 Linux 上(可能作为文件系统块大小的函数),当我创建一个目录时stat
,它返回 4096 的大小。我可以在这个目录中创建文件,直到一定程度,而不会增加目录的感知大小(如 所报告的stat
)。
在某些时候,随着目录中充满了许多文件,目录大小会膨胀(我不是在谈论目录的内容,而是在谈论表示目录本身所消耗的块)。如果删除文件,目录大小保持不变。
以下是一个简单的例子:
[root@uxlabtest:/]$ mkdir test
[root@uxlabtest:/]$ stat test
File: `test'
Size: 4096 Blocks: 8 IO Block: 4096 directory
Device: fd00h/64768d Inode: 1396685 Links: 2
Access: (0755/drwxr-xr-x) Uid: ( 0/ root) Gid: ( 0/ root)
Access: 2011-07-26 14:06:04.000000000 -0400
Modify: 2011-07-26 14:06:04.000000000 -0400
Change: 2011-07-26 14:06:04.000000000 -0400
然后触摸一堆文件:
[root@uxlabtest:/]$ for i in `seq 1 10000`; do touch /test/$i; done
[root@uxlabtest:/]$ stat test
File: `test'
Size: 155648 Blocks: 312 IO Block: 4096 directory
Device: fd00h/64768d Inode: 1396685 Links: 2
Access: (0755/drwxr-xr-x) Uid: ( 0/ root) Gid: ( 0/ root)
Access: 2011-07-26 14:06:04.000000000 -0400
Modify: 2011-07-26 14:06:56.000000000 -0400
Change: 2011-07-26 14:06:56.000000000 -0400
然后删除文件:
[root@uxlabtest:/]$ rm -rf /test/*
[root@uxlabtest:/]$ stat test
File: `test'
Size: 155648 Blocks: 312 IO Block: 4096 directory
Device: fd00h/64768d Inode: 1396685 Links: 2
Access: (0755/drwxr-xr-x) Uid: ( 0/ root) Gid: ( 0/ root)
Access: 2011-07-26 14:07:11.000000000 -0400
Modify: 2011-07-26 14:07:12.000000000 -0400
Change: 2011-07-26 14:07:12.000000000 -0400
我的问题是:
- 为什么目录的大小/块数单调增加?
- 这是底层文件系统或 Linux VFS 的功能吗?
- 如果不删除并重新创建目录,目录大小是否可以减小?
- 加分项:请告诉我实现此行为的内核源代码。
答案1
以下是对 ext2/ext3/ext4 正确的答案。它们是否适用于其他文件系统取决于它们的实现。
- 用户 48838 回答正确。文件越多,消耗的元数据就越多。它们以 4k 块或文件系统创建时定义的任何其他大小进行分配
- 是的,这是真实文件系统的一个特性/问题
- 在 ext3 文件系统中这是不可能的。只有通过重新创建(空)目录
- 源代码如下这里以及相关文件中
但你很幸运。当你重新创建已删除的相同数量的文件时,目录大小将保持不变。只有当你添加更多文件时,它才会增加。
答案2
您看到的块增量是由于文件系统如何管理其文件存储和相关文件管理信息。在您描述的情况下,这似乎是 4K 的增量,因此文件系统中的每个“新”/“唯一”条目都将保留 4K,无论实际数据大小是否填满整个 4K。如果相关数据占用了整个 4K,则将根据需要保留和填充另一个 4K 块以存储整个相关数据流/序列。
根据文件系统管理的“硬”删除与“软”删除,删除可能不会(通常不适用于“取消删除”功能)立即释放保留的块。某些文件系统可能会区分不同类型的“删除”,并提供相应的存储块管理功能。
存储管理的方法和实施方式因文件系统而异,因此在支持多/模块化文件系统的操作系统中,操作系统通常只提供文件系统要集成的“钩子”。
答案3
对用户 48838 的好答案添加一些漫无边际的评论:
一切都是文件,包括目录。要存储所有文件信息,您需要空间。
对于小目录,显示‘已使用 64B’也是有效的,并且实际上显示已使用的空间量,但无论如何我们都会在磁盘上使用 4K 的倍数,因此设计决定只显示已使用的空间量。
从 FS 设计角度来看,你为什么要费心计算使用了什么?没必要。然后你必须移动条目以避免留下漏洞……真讨厌。
当删除发生并且目录大小下降时,你可以释放一个块,在实际释放之前,需要进行所有这些管理。为什么要费心节省几 KB?无论如何,您以后都可能需要扩展它。
留给读者的练习:思考一下为什么你的 /lost+found 目录创建为空但却占用了 16K(至少在 ext3 上)。