首页 > 代码库 > Linux 文件指令

Linux 文件指令

只 要是磁盘就得 式化,好像已经是天经地义的事情了,几乎没有人去问为什么。很多有经验的同学 乎都有过这样的经历,就是风风火火的从朋友那里借来了一张装满高清岛国爱情动作片的移动硬盘,暗爽过后还想留下一些待以后慢慢品味,可是总有那么一些质量 比较好的片子(尺寸超过 4G)复制失败。追问原因还往往被高手们嘲笑:“都什么年代了你还用 FAT32,赶紧换 NTFS 吧。”我想这个时候你就不得不追问一下,为什么 FAT32 不行而 NTFS 却能行吧? 

    因为它们是不同的文件系统,功能不同,能力不同。FAT32 是 在 Windows95 时代开始采用的文件系统,到现在都有人在用(比如 U盘),可以说是伴随着我们成长的文件系统。FAT 是 File Allocation Table 的缩写,从字面意义上就能看出这是一种类 表 一样的文件系统。由于其用于描述文件大小的属性是一个 32 位的 ,导致其能够支持的单个文件最大不能超过 4G。而 NTFS 是微软专门为 NT 系统设计的,单个文件最大可以达到 2T。现在最为常用的 Windows XP 和 Windows 7 都支持 NTFS。至于 NTFS 是怎么管理文件的有点不太好说,因为微软一直当它是个“秘密”。

    Linux 也有自己的文件系统 式,被称为 ExtN(N=2、 3、4)。如果要追溯 ExtN 的起源,其实要比 FAT32 和 NTFS 都要古老。ExtN 文件系统必定要包含 inode 数据结构来代表一个文件,并且存储这个文件的各种属性和权限。至于实际的数据则放在 data block 块区中。除此之外,ExtN 文件系统还有一个超级块区(super block),用于记录整个文件系统的整体信息,包括 inode 与 data block 的总量、使用量和剩余量。

    使用 stat -f filename 可查看系统的 inode 和 data block 使用情况。

        -f, --file-system
              display file system status instead of file status

    weiyuzhang@weiyuzhang:/work/windows$ stat -f /work/workspace/so/main
    文件:"/work/workspace/so/main"

   以下输出都跟 main 文件无关
    ID:1371e0e3c96e0461 文件名长度:255     类型:ext2/ext3
    块大小:4096       基本块大小:4096
    块:总计:23151106   空闲:14056882   可用:12880870
    Inodes: 总计:5881856    空闲:5836277

    data block 与 inode 一样,每一个都有一个唯一编号,inode 只需要记录这些编号,就能够定位整个文件的任意一段数据。我们假定有一个编号为 3 的 inode,它所代表的文件的数据被放置在编号为 2、5、6、8、13 和 20 的这几个 data block 中。那么读取这个文件的过程则如 图1 所示。

 

 alt

 

图 1 ExtN 文件系统读取数据过程示意图

 

采用这种数据存取的方法的文件系统被称之为“索引式文件系统”。它与伴随着很多人成长的 FAT32 有什么不同呢?图2 展示了这个过程。

 

 alt

 

图 2 FAT32 文件系统读取数据过程示意图

 

    通过对两个图的比较,我们可以清晰的看出,ExtN 通过 inode 能够一次性获得文件数据所存放的位置,可以据此来安排磁盘的阅读顺序,尽量保证在磁盘只旋转一圈的情况下将所有内容读出来。而 FAT32 则只有将对应的 data block 读入之后才知道下一个 data block 在什么地方。如果一个文件的 data block 比较分散的话,将很难保证在磁盘只旋转一圈的情况下读取全部数据,有时候甚至要多转很多圈才能读完数据。

    这就是我们非常熟悉的“磁盘碎片”问题。由于长时间的对文件进行创建、删除、读写,很难保证同一个文件的 data block 的位置相邻。而由于 FAT32 的读写特性,在 data block 不相邻的情况下读写性能会急剧下降。所以,为了提高 Windows 系统的磁盘性能,经常性的做“磁盘碎片整理”是非常有必要的。

    而对于 Linux 这种文件系统,则基本上不需要进行磁盘碎片整理。而且你也基本上找不到类 的工具。但是 Linux 系统经过长时间使用之后,还是会有文件数据过于分散的问题的。即便能够做到很好的规划,但是对性能多多稍稍还是会有一些影响,只是没有使用 FAT32 的 Windows 那么严重罢了。所以,一个使用时间很久的Linux 系统也会因为磁盘碎片问题而变慢,这也是事实。只是不需要太过在意它。


一. 文件相关

1. 节点(inode)

    在 Linux 的文件系统中,保存在磁盘分区中的文件,不管是什么类型,都有一个编号,即节点号。

    通过 ls -i 可以查看。

2. atime/ctime/mtime 访问时间/更改时间/修改时间

    后 2 者的区别是,ctime 会同时跟踪文件属性和数据,mtime 仅关系到文件数据。

    例如,修改一个 .sh 文件的内容,mtime 会发生变化,但是仅修改 .sh 文件的权限,例如 chmod a+x test.sh,ctime 会发生变化

    通过 stat filename 可以查看文件的 inode 节点信息:

3. 链接

    分为软链接(符号链接)和硬链接。不论哪一种,都会保持链接文件的同步性;可以使用相对路径链接文件。

    a. 软链接(符号连接)  

        ln -s 源 目

    类 于 Windows 中的快捷方式,实际上是一个文本文件,包含了被链接文件的位置信息,但与被链接文件的节点号不同;支持跨分区链接

    既然是快捷方式,其大小就不是所链接文件的大小,而是只有几个字节。

    stat 命令查看源文件和软链接的结果如下:

    weiyuzhang@weiyuzhang:/work/workspace$ stat client.c
      File: "client.c"
      Size: 686       Blocks: 8(表示为了存储该文件,使用了几个 data block,其结果,并不是严 的 Size/512)         IO Block: 4096  普通文件
    Device: 809h/2057d Inode: 131252      Links: 1
    Access: (0644/-rw-r--r--)  Uid: ( 1000/weiyuzhang)   Gid: ( 1000/weiyuzhang)
    Access: 2012-09-20 10:26:40.466391743 +0800
    Modify: 2012-09-18 17:33:15.405397461 +0800
    Change: 2012-09-20 10:25:06.786254344 +0800

    weiyuzhang@weiyuzhang:/work/workspace$ stat fake
      File: "fake" -> "client.c"
      Size: 8         Blocks: 0          IO Block: 4096   符号链接
    Device: 809h/2057d Inode: 131318      Links: 1
    Access: (0777/lrwxrwxrwx)  Uid: ( 1000/weiyuzhang)   Gid: ( 1000/weiyuzhang)
    Access: 2012-09-20 10:24:12.236174347 +0800
    Modify: 2012-09-20 10:24:11.486173237 +0800
    Change: 2012-09-20 10:24:11.486173237 +0800

    也可以看到,增加软连接,stat 信息中的 Links 不会增加

    b. 硬链接  

        ln 源 目

    通过节点号进行链接,即多个文件名指向同一个节点号;windows 中不具备该功能;

    其功能是,允许一个文件拥有多个有效路径名称,防止误删。只删除一个链接,并不影响节点本身和其它链接,只有当最后一个链接被删除后,文件的数据块才会被释放。即,文件真正删除的条件是,与之相关的所有硬链接文件均被删除。

    只能在同一分区内,否则提示:

        “ln: 创建硬链接"test" => "/work/out": 无效的跨设备连接”

    stat 命令查看源文件和硬链接的结果如下:

    weiyuzhang@weiyuzhang:/work/workspace$ stat client.c

      File: "client.c"
      Size: 686       Blocks: 8          IO Block: 4096   普通文件
    Device: 809h/2057d Inode: 131252      Links: 2
    Access: (0644/-rw-r--r--)  Uid: ( 1000/weiyuzhang)   Gid: ( 1000/weiyuzhang)
    Access: 2012-09-20 10:26:40.466391743 +0800
    Modify: 2012-09-18 17:33:15.405397461 +0800
    Change: 2012-09-20 10:25:06.786254344 +0800

    weiyuzhang@weiyuzhang:/work/workspace$ stat fake2
      File: "fake2"
      Size: 686       Blocks: 8          IO Block: 4096   普通文件
    Device: 809h/2057d Inode: 131252      Links: 2
    Access: (0644/-rw-r--r--)  Uid: ( 1000/weiyuzhang)   Gid: ( 1000/weiyuzhang)
    Access: 2012-09-20 10:26:40.466391743 +0800
    Modify: 2012-09-18 17:33:15.405397461 +0800
    Change: 2012-09-20 10:25:06.786254344 +0800

    此外,ll 命令输出的第二列也显示对应文件的硬链接数目

    weiyuzhang@weiyuzhang:/tmp$ ll

    总用量 68

    drwxrwxrwt 11 root               root                4096 11月 26 14:46 ./

    drwxr-xr-x   25 root               root                4096 11月 9    16:42 ../

    drwx------      2 weiyuzhang weiyuzhang 4096 11月 26  09:10 .com.google.Chrome.X8rA1c/

    drwx------      2 weiyuzhang weiyuzhang 4096 11月 26  09:16 CRX_75DAF8CB7768/

    prw-rw-r--     1 weiyuzhang weiyuzhang 0        11月 26  10:06 fifo|

4. 编辑文件

    除了 vi,还有一个常用的工具是 nano。 

    在其底部有效的命令列表中,^ 表示 Control。

5. touch

    用于更新文件的访问时间和更改时间,虽然实际上不会编辑文件的内容。

6. 压缩和解压

    提供 gzip 和 bzip2 两种压缩方法。

        tar zcvf archive.tar.gz [file1 file2...]

        tar jcvf archive.tar.bz2 [file1 file2...]

7. 挂载

    在 /dev 目录中,有些可用的设备是存储设备,例如软驱或者 CD-ROM。访问它们提供的内容不是简单的 cd 进入驱动器,存储驱动器需要挂载到文件系统。换句话说,驱动器需要附加到一个固定的目录。

        mount /dev/md1 /mnt/alexdrive

    将驱动器 /dev/md1 附加到系统中现有的目录 /mnt/alexdrive。一旦驱动器被挂载,就可以使用文件系统的任何指令访问驱动器。

    查看已启用的驱动器名,可通过 df -h。

    在现代的 Linux 发行版本中,CD-ROM、U盘等一些常见设备能够由系统自动挂载

    此外,不带参数的 mount 指令,可以输出系统中每一个被挂载的驱动器及使用的文件系统。

    例如,插入 U 盘,通过 mount 指令可以看到:

        ......

        /dev/sdb1 on /media/username/PENDRIVE type vfat (rw,nosuid,nodev,uid=1000,gid=1000,shortname=mixed,dmask=0077,utf8=1,showexec,flush,uhelper=udisks2)

    这是系统自动挂载的结果。/dev/sdb1 即为 U 盘对应的驱动器名。可以使用 umount /dev/sdb1 来取消挂载。但是如果再次打开文件,又会被自动挂载。

    如果想让一个驱动器在开机时自动挂载,或者简单设置一个目录作为一个驱动器的默认挂载点,需要修改 /etc/fstab 文件。

8. 文件查找

    a. locate & updatedb

        locate filename

    该命令与 updatedb 关联,完全依赖于索引,如果新建一个文件,使用 locate 是找不到的,除非执行过 updatedb

    updatedb 需要 root 权限,一般通过 cron 定期执行。


Linux 文件指令