# 设置开机挂载

手动处理 mount 后不是永久挂载的,就像上一节我的虚拟机软件崩溃了,重启之后挂载的都不在了。

# 开机挂载 /etc/fstab 及 /etc/mtab

可以通过修改 /etc/fstab 文件来达到开机自动挂载,下面说一说系统挂载的限制

  • 根目录 / 是必须挂载的,而且一定要先于其他的 mount point 被挂载出来
  • 其他 mount point 必须为已建立的目录,可任意指定,但一定要遵守必须的系统目录架构原则(FHS)
  • 所有 mount point 在同一时间之内,只能挂载一次
  • 所有 partition 在同一时间之内,只能挂载一次
  • 若进行卸载,必须先将工作目录移到 mount point(及其子目录)之外
[mrcode@study ~]$ cat /etc/fstab

#
# /etc/fstab
# Created by anaconda on Fri Oct  4 18:20:52 2019
#
# Accessible filesystems, by reference, are maintained under '/dev/disk'
# See man pages fstab(5), findfs(8), mount(8) and/or blkid(8) for more info
#
# device								Mount point				filesystem	 paramters		dump fsck
/dev/mapper/centos-root /                       xfs     defaults        0 0
UUID=13d0663f-4cbd-412d-aa9f-975eb18da590 /boot                   xfs     defaults        0 0
/dev/mapper/centos-home /home                   xfs     defaults        0 0
/dev/mapper/centos-swap swap                    swap    defaults        0 0

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15

/etc/fstab(filesystem table)将我们利用 mount 指令进行挂载时,将所有的选项与参数写入该文件。初次之外,/etc/fstab 还加入了 dump 这个备份用指令的支持。与开机时是否进行文件系统检验 fsck 等指令有关。该文件内容提供的 6 个字段很重要,需要背下来

【装置/UUID等】【挂载点】【文件系统】【文件系统参数】【dump】【fsck】
1
  • 装置文件名/UUID/LABEL name:

    可以填写的数据主要有三个项目

    • 文件系统或磁盘的装置文件名,如 /dev/sda 等
    • 文件系统的 UUID 名称
    • 文件系统的 LABEL name

    看你自己喜好选择填写哪一项。这里建议使用 UUID,可以使用 blkid 或 xfs_admin 来查询 UUID

  • 挂载点 mount point:一定是目录

  • 磁盘分区槽的文件系统:手动挂载时,可以让系统自动测试挂载,该文件中需要手动确定,包括 xfs、ext4、vfat、reiserfs、nfs 等

  • 文件系统参数

    前面讲解 mount 指令谈到很多特殊的文件系统参数,还有我们使用过的 -o codepage=950,这些参数就是写在这里的

    参数 内容含义
    async/sync(异步/同步) 设置磁盘是否已异步允许方式,预设为 async
    auto/noauto(自动/非自动) 当下达 mount -a 时,此文件系统是否被主动测试挂载。预设为 auto
    rw/ro(可擦写/只读) 让该分区槽可以擦写或只读的形态挂载上来,当这里设置为只读之后,在文件系统中对文设置 w 权限,也不能写入
    exec/noexec(可执行/不可执行 限制在此文件系统内是否可以进行「执行」的工作?如果纯粹用来存储数据的话,就可以设置为 noexec 比较安全。不过该参数不能随便使用,因为你不知道该目录下是否默认会有执行文档。比如:将 noexec 设置在 /var ,当某些软件将一些执行文件放置到该文件下时,那么这些软件就不能运行
    user/nouser(允许/不允许使用者挂载) 是否允许用户使用 mount 指令来挂载
    suid/nosuid(具有/不具有 suid 权限) 该文件系统是否允许 SUID 的存在?如果不是执行文件放置目录,也可以设置为 nosuid 来取消 SUID 的功能
    defaults 同时具有 rw、suid、dev、exec、auto、nouser、async 等参数。基本上使用该参数即可
  • 内否被 dump 备份指令作用:dump 是用来做备份的指令,不过现在备份方案太多了,可以不关注该项目,直接输入 0 好了

  • 是否已 fsck 检验扇区

    早期开机的流程中,会有一段时间去检验本机的文件系统,看看文件系统是否完整(clean)。不过该方式使用的主要是通过 fsck 来做的。我们现在用 xfs 文件系统就没有办法适用了,因为 xfs 会自己进行检验,直接填写 0 即可

实践练习

# 将 /dev/sda4 每次开机都自动挂载到 /data/xfs
# 查看 uuid
[root@study ~]# blkid /dev/sda4
/dev/sda4: LABEL="mrcode_xfs" UUID="edfa7161-5847-4935-80e1-6e081be9ab77" TYPE="xfs" PARTLABEL="Linux filesystem" PARTUUID="3819b115-2ab8-4fb6-8425-bb2ff8e797b7" 
# 使用 nano 将下面信息写入到 /etc/fstab 最后
UUID="edfa7161-5847-4935-80e1-6e081be9ab77" /data/xfs xfs defaults 0 0

# 检查是否已挂载
[root@study ~]# df
文件系统                   1K-块    已用    可用 已用% 挂载点
/dev/sda4                1038336   32896 1005440    4% /data/xfs
/dev/sda5                 999320    2564  927944    1% /data/ext4
# 可见已挂载了,先卸除它,我们再来测试,卸载之后自行使用 df 确认
[root@study ~]# umount /dev/sda4 
# 再来挂载,这里使用了 -a 的参数,会默认加载 /etc/fstab 中的项挂载
[root@study ~]# mount -a
[root@study ~]# df /data/xfs
文件系统         1K-块  已用    可用 已用% 挂载点
/dev/sda4      1038336 32896 1005440    4% /data/xfs

# 重启系统后,再观察是否会自动挂载
reboot
# 笔者实测可以被自动挂载
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23

/etc/fstab 是开机时的配置文件,不过实际 filesystem 的挂载是记录到 /etc/mtab/proc/mounts 文件中的。每次当我们更动 filesystem 的挂载时,也会同时更动这两个文件。但是万一发生你再 /etc/fstab 输入的数据错误,导致无法顺利开机成功,而进入单人维护模式当中,哪时候的 / 可是 read only 的状态,就无法修改 /etc/fstab ,也无法更新 /etc/mtab 怎么办?

# 重新挂载下 / 就可以了修改了
mount -n -o remount,rw /
1
2

# 特殊装置 loop 挂载(印象档不刻录就挂载使用)

如果有有光盘映像文件,或则是使用文件作为磁盘的方式时,需要使用特别的方法将他挂载起来,不需要颗粒

# 挂载光盘/DVD 映像文件

前面装系统时从网络上下载的 ISO 文件,不用刻录到光盘上再读取,可以通过 loop 来挂载

# 笔者的虚拟机里面没有这个文件,上传也很慢,现在课程中也还未讲到网络配置等东西
# 这里就不实践了,只记录下步骤
ll -h /tmp/CentOS-7-DVD.iso
mkdir /data/centos_dvd
# 挂载
mount -o loop /tmp/CentOS-7-DVD.iso /data/centos_dvd
df /data/centos_dvd
# 挂载之后,就可以读取该目录下的内容了
ll /data/centos_dev
# 当然这样挂载之后也是可以修改里面的文件的(前面讲解了修改挂载的参数支持写入,获取可以去尝试下)
# 这也是为什么很多 iso 提供之后会有一个 MD5 给使用者来确认该文档没有被修改过
1
2
3
4
5
6
7
8
9
10
11

# 建立大文件以知错 loop 装置文件

既然可以挂载 DVD 的映像文档,那么能不能制作一个大文件,然后将整个文件格式化后挂载?比如:如果当初在分区时,只分区出一个根目录,假设已经没有多余的容量可以进行额外的分区。偏偏根目录的容量还很大!此时就可以制作出一个大文件,然后将整个文件挂载!如此就感觉多了一个分区槽,用途非常的广泛

下面我们再 /srv 下建立一个 512MB 左右的大文件,然后将整个大文件格式化并且实际挂载来玩一下。

# 建立大型文件

可以使用 dd 指令来建立空文件(后续会详细讲解)

[root@study ~]# dd if=/dev/zero of=/srv/loopdev bs=1M count=512
记录了512+0 的读入
记录了512+0 的写出
536870912字节(537 MB)已复制,0.519957 秒,1.0 GB/秒

# 该指令含义如下
if:是 input file 输入文件,/dev/zero 是会一直输出 0 的装置
of:是 output file,将一堆 0 写入到后面接的文件中
bs:每个 block 大小
count:总共几个 bs。所以 bs * count = 该文件容量

# 查看该文件
[root@study ~]# ll -h /srv/loopdev 
-rw-r--r--. 1 root root 512M 1027 20:39 /srv/loopdev

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15

# 大型文件格式化

预设 xfs 不能够格式化文件,所以要格式化文件需要使用特别的参数

# 使用参数 -f 强制格式化
[root@study ~]# mkfs.xfs -f /srv/loopdev 
meta-data=/srv/loopdev           isize=512    agcount=4, agsize=32768 blks
         =                       sectsz=512   attr=2, projid32bit=1
         =                       crc=1        finobt=0, sparse=0
data     =                       bsize=4096   blocks=131072, imaxpct=25
         =                       sunit=0      swidth=0 blks
naming   =version 2              bsize=4096   ascii-ci=0 ftype=1
log      =internal log           bsize=4096   blocks=855, version=2
         =                       sectsz=512   sunit=0 blks, lazy-count=1
realtime =none                   extsz=4096   blocks=0, rtextents=0
[root@study ~]# blkid /srv/loopdev 
# 注意这里的 UUID 后续会用到
/srv/loopdev: UUID="fc6e332b-343f-4a08-921c-9801e3caeb66" TYPE="xfs" 
1
2
3
4
5
6
7
8
9
10
11
12
13
14

# 挂载

[root@study ~]# mount -o loop UUID="fc6e332b-343f-4a08-921c-9801e3caeb66" /mnt
[root@study ~]# df /mnt/
文件系统        1K-块  已用   可用 已用% 挂载点
/dev/loop0     520868 26436 494432    6% /mnt

1
2
3
4
5

通过这个简单的方法,感觉上可以在原本的分区槽在不更改原有的环境下制作出想要的分区槽了,非常好用,尤其是想要玩 linux 上面的「虚拟机」的话,也就是以一部 Linux 主机再切割成为数个独立的主机系统时,类似 VMware 这类的软件,在 Linux 上使用 xen 这个软件,他就可以配合这种 loop device 的文件类型来进行根目录的挂载,真的非常有用

比较特别的是,Centos7.x 越来越智能了,现在不需要使用 -o loop 选项与参数,统一可以被挂载上来,直接输入 blkid 都会列出这个文件内部的文件系统(为了考虑兼容性,还是建议加上 loop 比较妥当),现在将该文件系统永远的自动挂载

[root@study ~]# nano /etc/fstab
# 在该文件中写入下面一行的数据
# 注意这里挂载到了 /data/file 中
# UUID="fc6e332b-343f-4a08-921c-9801e3caeb66" /data/file xfs defaults 0 0
# 这里还是使用文件档名来挂载,毕竟系统大多仅查询 block device 去找 UUID,因此使用文件建立的 filesystem 使用文件名比较不容易出错
/srv/loopdev /data/file xfs defaults 0 0

# 卸载原来的 mnt,以及建立对应的目录
[root@study ~]# umount /mnt
[root@study ~]# mkdir /data/file
[root@study ~]# mount -a
[root@study ~]# df /data/file
文件系统        1K-块  已用   可用 已用% 挂载点
/dev/loop0     520868 26436 494432    6% /data/file


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16