初学者 Linux 用户请在社区 Wiki 和高级 Linux 用户陪同下观看

好,脑子又发抽了。

怎么的呢,也许是在家闲出病了,想要把装 Arch 的那台笔记本重新给装一遍。到也不能说事出突然吧。最初的缘由是,最近已经完完全全从 KDE 迁移到 Hyprland 了,因此原来 KDE 的那一套臃肿的玩意基本上是使不上了。虽然说以前可能还会开开堆叠式桌面救救急,但现在倒是完全没什么必要了。然后呢,想着既然不用了,那干脆重装了不带 KDE 的那些组件,反正说删也不知道删哪些。再然后呢,就开始嫌弃自己一开始做的加密分卷上的 btrfs 的结构没做好,这次索性重新再来,这么几次反复追加需求,现在变成了把加密分卷拆出个 500GB 出来做一个双系统,留着给其他的 OS 做测试用。等到最终看到自己的需求,这会儿开始犯了难了。

Plan 1

首先是双系统这事,如果还和现在一样做一个裸露的 boot 分卷,把两个系统的内核和 initramfs 都放到 boot 里,都先不提微码,首先内核就开始打架了。两边系统的内核都是为系统做过优化的,必然是不可能共用的。别的发行版内核改动不是很熟,按理说应该是可以指定位置的,但是不清楚,不能做保底;Arch 那边倒好,我知道是肯定要更某个钩子,但是又不知道从哪个 hook 那边下手,因此也能作罢,于是这步作废了。

难绷,问题在下面那验证加密的时候解决了。Arch 不是采用 mkinitcpio 构建内核嘛,配置文件就放在 /etc/mkinitcpio.d/ 里面,所以只需要改一改里面的保存位置参数就行。很贴心,kernel initramfs 以及 ucode 都在。很好,这一个方案最大的问题解决了。然后,你在下面看到创建 efi 镜像的时候,也是在这里配置 :)

Plan 2

接着就是单独开辟一个 esp 分区,里面装 bootloader,然后给两个系统单独留加密分卷,把 boot 留到加密分卷里。这一步从安全性上来讲其实是要高一点的,而且系统之间的 boot 做了隔离,自然避免了打架的事。不过如果 boot 也做一层加密的话,bootloader 就只能选用 grub 了。不过这样做看 wiki 上面的指示需要自行进行密码的输入,同时 boot 的解密直接就是整个根分区的解密,安全性上其实不是很好。

说到底安全这个东西只能说在大部分的情况下都是防自己,别人压根懒得搞。你经常遇到的完全就是直接把你电脑摸了全盘清空了直接拿去卖了,而不是想方设法地去敲你的加密盘,所以如果只是单纯 Dual Boot 的话,我的建议是直接 esp 一个分区,OS 各自分区,然后 bootloader 里配置一下就行,非常的简单完美。要什么自行车!!!!

Plan 3

目前我单个系统的加密方式其实是修改了的“使用 TPM2 和安全启动的简单根分区加密”,原文这里是将 boot 分区放在加密的 / 当中,在 bootloader 读取时直接使用 TPM 进行解密,而我做了一次修改,将 boot 分了出来放在了 esp 里,而且没有加密,直接和 bootloader 放一块。这是我觉得不妥的缘由之一,因为看 wiki 的架势应该是放根里一起加密。其实还有一点比较头疼,就是对于采用了 Secure Boot 和 TPM 自动解密的系统来说,实际上对分区进行加密形同虚设。设想,你的 PC 被未经授权开机,但是对方并没有修改任何 Secure Boot 设定,最后摆在别人面前的还就只有一条防线,你的 root 密码。不过采用 Secure Boot 和 TPM 的理由其实很大程度上就是在方便自己,就像我之前说的,你的全盘加密更多的时候还是在防自己。不过 Secure Boot 也是有非常好的作用在的,就是防止从其他媒介加载系统,这样至少也能防住绕过你 bootloader 的系统加载,当然绕过去了也还是有你的加密在。说到底,加密的关键是要明晰自己的目的到底是防御什么。

Plan 3.A

不过这个方案其实我到现在还不是很理解。因为如果按照我理解的,“boot 分区应作为根分区的子目录一同被加密”,那么这样子的话上一条的“加密的 boot 分区”就不应该单独成条。因为这样完全也不需要说 grub 的解密功能来解密 boot 了。莫非是 TPM 来进行了 boot 分区的解密所以 bootloader 就不需要指定拥有解密功能,仅需要能进行 Secure Boot 注册就行了?至少我这边 TPM 失败的时候是已经读取完内核后的状态了,不过我这里也没什么参考性,毕竟确实内核没有做过加密。看来要验证一下。

好的,验证结束了。重新试了一次终于理解了。我把 boot 分出来其实是画蛇添足了。这里的整块加密的思路是,解密情况下的 /root/boot 里面放内核 vmlinuz-linux ,然后由 mkinitcpio(Gentoo 的 dracut 也行,一个意思) 来依次读取内核参数(尤其重要的就是需要解密的分区和其挂载位置)来生成 initramfs,然后把这个 initramfs 和内核一起制作成 efi 镜像放到 /efi 里面,这样 bootloader 就正常读取 efi 镜像就行,加载后就又有内核又有 initramfs 了。之后 initramfs 会去请求解密 / ,这个时候用 TPM 自动解密就行。完美!这样就只有 efi 分区是暴露的,这里我们再启用 Secure Boot 即可。

Plan 3.A 说明

不得不说,wiki 里面的东西能用是能用,但是很有可能你按照人家流程走完了也做功了,结果你自己还不清楚到底发生了什么,是怎么一回事。

上面验证的结果可能还有些朋友没有太理解,那我接着展开说々。首先请看Arch 的启动流程

首先,如果你是按照 Arch Linux Installation Guide 一步步走下来的话,那么你的 PC 的启动流程是这个样子的:主板通电自检完成后,UEFI 读取 EFI 分区,从中启动了 Bootloader(GRUB / Systemd-boot / etc. );bootloader 依照选用的配置,读取系统内核(vmlinux 镜像),内核启动的时候再把 initramfs 挂载了,initramfs 里面包含了我们配置时的那些诸如 base filesystems 和 keyboard 之类的工具和驱动,在有了这些东西的帮助下,才可以继续挂载根文件系统。试想一下,如果你 initramfs 在配置生成的时候不带像 btrfs 这样的文件系统组件时,又怎么能成功读取和挂载这些内核里根本不存在的文件系统呢?当 initramfs 的活也都干完后,剩余的工作就是大同小异,一步步的就到了 tty 那边了。

那么这里就出现了个问题,如果对 boot 分区进行加密的话,那么 bootloader 在读取到 boot 中的内核和 initramfs 之前首先需要对存放这些东西的 boot 分区进行解密,否则根本读不到,但是不是所有的 bootloader 都能支持这项功能,只有 GRUB 提供了利用 LUKS 进行解密的功能,这样对于那些想用漂漂亮亮的 Bootloader (对对对,就是你Limine)的人来说就有点难受了。

那么采用上面的全盘加密呢?一直到启动 bootloader 这里还没有问题,但是下一步 bootloader 就不是先加载 kernel 再读取 initramfs 了。我们利用内核和 initramfs 直接制作了一个 efi 镜像,efi 镜像放在了 esp 分区里,因为和 bootloader 同属一个没有加密的分区,因此可以被直接读取,这样内核和 initramfs 的加载就都完成了,然后 initramfs 接着再去操心根分区的事情。

虽然上面说的很有道理,但是实际上就算你启动了安全启动,esp 分区还是大门敞开在那。就,该说不说,该咋样还是咋样。

没用的总结

那么,总结一下:

  • 独立 esp + 独立共用 boot + 各 OS 单独加密根。需要对 Kernel 和 Initramfs 进行区别。
  • 独立 esp + 各 OS 单独加密根(包括 boot)。 boot 分区解密限制了 bootloader。
  • 独立 esp + 各 OS 单独加密根(包括 boot)+ Secure Boot + TPM 自动解密。上一条的修改版,可以确保 bootloader 不被篡改,而且可以让你在 initramfs 那边不用输密码。

哦,我这下理解了,原来第三种方案的存在是既想要安全性,又想要偷懒摸鱼啊,害!


几种 Linux 全盘加密的对比
https://Mundnaity.moe/post/encrypt_for_others_encrypt_for_yourself
作者
Mundanity Fan
发布于
2024-01-14
许可协议