zoukankan      html  css  js  c++  java
  • Linux 文件与目录

    笔者在前文《Linux EXT2 文件系统中》中介绍了 EXT2 文件系统中的基本概念,本文继续以 EXT2 文件系统为例介绍文件系统是如何管理文件存储的。

    inode

    在前文介绍文件系统时我们提到了 inode 和 data block。在 EXT2 文件系统中,inode 用来存放文件的元信息,data block 用来存放文件的内容。inode 包含的文件元信息有:

    • 该文件的读写权限(rwx)
    • 该文件的拥有者和所属组(owner/group)
    • 该文件的大小
    • 该文件的 ctime(创建时间)
    • 该文件的 atime(最近一次的读取时间)
    • 该文件的 mtime(最近修改的时间)
    • 该文件的特殊标识,比如 SetUID 等
    • 该文件真正内容的指向(文件 data block 的位置)

    总之,除了文件名之外的所有文件信息都存在 inode 中。我们可以使用 stat 命令来查看文件的 inode 信息:

    $ stat test.txt

    inode 的大小
    inode 本身是会消耗磁盘空间的,我们可以通过下面的方式查看 inode 的大小:

    $ sudo dumpe2fs -h /dev/sdd1 | grep "Inode size"

    在笔者的机器上,输出的结果如下:

    dumpe2fs 1.42.13 (17-May-2015)
    Inode size:              256

    也就是说一个 inode 占用 256 个字节的磁盘空间。

    inode 耗尽问题
    因为每个文件需要占用一个 inode,所以生产中会碰到 inode 耗尽导致无法创建新文件的问题。我们可以通过 df 命令 的 -i 选项查看文件系统中 inode 的使用情况:

    $ df -i

    文件

    每个文件都会占用一个 inode,inode 内则有文件数据放置的 block 号码。当我们在 Linux 下的 ext2 文件系统中创建一个一般文件时,ext2 文件系统会分配一个 inode 与相对于该文件大小的 data block(一个或多个) 给该文件。inode 记录该文件的权限与属性,并记录分配到的 data block 号码。例如:假设一个 data block 的大小为 4 KBytes,而要创建一个 100 Kbytes 的文件,linux 就会分配一个 inode 与 25 个data block 来储存该文件!
    单个文件,inode 和 data block 的示意图(可以简单的理解为下图的样子):

    这种数据存取的方法我们称为索引式文件系统(indexed allocation)。

    虽然从实现的层面上来看,可以直接从 inode 找到其对应的 data block,但是我们却不能通过 inode 直接访问文件,因为这会破坏通过权限进行的访问控制。例如,如果没有遍历目录的权限,那么无论文件上的权限是什么,都不能访问该目录中的任何文件。如果可以通过inode访问文件,就可以绕过目录权限。

    目录

    注意,inode 本身并不记录文件名,文件名的记录是在目录的 data block 当中。
    目录本质上也是一个文件,所以当我们在 ext2 文件系统中创建一个目录时,文件系统会分配一个 inode 和至少一块 data block 给这个目录。其中,inode 记录该目录相关的权限与属性,并记录分配到的 data block 号码。而 data block 中则记录着在这个目录下的文件名(目录也是文件)与该文件名的 inode 号码。也就是说目录所占用的 data block 的内容记录着类似下面的信息:

    目录项
    文件名及其对应的 inode 被称为目录项。其实,目录项是内存中的数据结构,所以实际情况是文件名对应的是指向 inode 的指针。我们可以通过下面的示意图来理解 inode、目录、文件以及目录项之间的关系:

    从磁盘读取一个文件的过程

    由于目录树是由根目录开始读起,因此通过文件系统的挂载信息可以找到挂载点的 inode 号,此时就能够得到根目录的 inode 内容,并通过这个 inode 读取根目录的 data block 中的文件名称,再一层一层的往下查找,直到读到正确的文件名。下面让我们通过读取 /etc/passwd 文件来理解文件的读取过程。

    上面的 ls 命令使用 i 选项输出了 /、 /etc、 /etc/passwd 的 inode 分别为 2、4325377、4329700。
    我们通过当前用户 nick 读取 /etc/passwd 文件的内容,其过程如下:

    1. / 的 inode 号为 2,权限信息允许我们读取 data block 中的内容(有 r 与 x)
    2. / 的 data block 中记录的 etc/ 目录的 inode 号为 4325377
    3. etc/ 的 inode 中权限信息包含 rx,因此用户 nick 可以读取 etc/ data block 的内容
    4. etc/ 的 data block 中记录的 passwd 文件的 inode 号为 4329700
    5. 文件 passwd 的 inode 中权限信息包含 r,因此用户 nick 可以读取 passwd data block 的内容
    6. passwd 的 data block 中的内容被读取出来

    参考:
    鸟哥的私房菜
    理解inode
    Linux inode 详解
    关于 inode
    目录项对象

  • 相关阅读:
    [转]理解java的三大特性之多态
    [转]java:IO流学习小结
    Base64 加密之中文乱码
    piwik优化之定时任务生成统计数据
    php统计中英文混合的文章字数
    Linux常用命令之定时任务
    skype在线状态代码详解
    php+google/baidu翻译接口
    php限制文件下载速度的代码
    PHP破解wifi密码(wifi万能钥匙的接口)
  • 原文地址:https://www.cnblogs.com/sparkdev/p/11249659.html
Copyright © 2011-2022 走看看