-
-
Notifications
You must be signed in to change notification settings - Fork 12.7k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
nixos: support systemd-veritysetup-generator
#305999
base: master
Are you sure you want to change the base?
Conversation
@ofborg test verity-protected-root |
This looks like a nice way into the right direction! Also thanks for writing a test for it ❤️ . |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Very cool that you're interested in dm-verity protected NixOS. That's something I've been working on for while as well!
My biggest issue with this PR is that it's all very entangled with the root kernel command line parameter while it doesn't have to be and probably shouldn't be.
Instead of adding another variant to the root enum, I believe we should add a separate module that you can enable. See https://github.com/nikstur/nix-store-veritysetup-generator/blob/main/nix/modules/verity.nix
If you really want a dm-verity protected root, you can then:
- enable this module
- set the
roothash=
kernel commandline - and set
fileSystems."/"
to use/dev/mapper/root
and whichever fs options (e.g.ro
) you need.
That's all that should be needed and still allows to use dm-verity differently, e.g. to protect /usr
or /nix/store
with nix-store-veritysetup-generator
IMO the test shows (by it's sheer complexity), how ill-suited a verity protected root fs is for NixOS. We'd get the same (or better) security properties if we just protect the Nix store and use some form of impermanence for the root. The simplest form of impermanence would be a tmpfs. What I've already tested and which works remarkable well is to mount the Nix store under /usr/nix/store
and then bind mount it to /nix/store
. Then you can just use the systemd veritysetup-generator.
# For NixOS activation to succeed, we need to have root writable in initrd. So unless root | ||
# is verity-protected (and thus read-only), where the user will have to take care of putting | ||
# overlay mounts in place, let's add "rw" to the kernel command line. | ||
++ lib.optional (config.boot.initrd.systemd.root == "gpt-auto" && cfg.root != "verity") "rw"; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Shouldn't the module system already enfore that this can't be both gpt-auto
and verity
because the option is an enum?
{ | ||
assertion = cfg.root == "verity" -> !(builtins.hasAttr "/" config.fileSystems); | ||
message = "The `fileSystems.\"/\"` option should not be set when `root` is set to `verity`."; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't think this is correct. The systemd-veritysetup-generator
only creates oneshot units that call systemd-veritysetup
. It doesn't itself create any mount units. Only systemd-gpt-auto-generator
or systemd-fstab-generator
do that. You should be able to use the veritysetup-generator
while still providing your own mount configs.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think that's not the case when using roothash
.
However, I'm more and more unsure about whether roothash
is the thing to do, as it also requires a DDI. If we used systemd.verity_root_data=, systemd.verity_root_hash=
, we could probably offer a universal interface that doesn't mount anything, see this Matrix discussion
@@ -211,7 +216,7 @@ in { | |||
}; | |||
|
|||
root = lib.mkOption { | |||
type = lib.types.enum [ "fstab" "gpt-auto" ]; | |||
type = lib.types.enum [ "fstab" "gpt-auto" "verity" ]; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't believe this is the right abstraction. You still need an fstab
or gpt-auto
for this to work because systemd-veritysetup-generator
only opens dm
devices. It doesn't mount anything and indeed you could configure your mounts with either the fstab or gpt-auto when you use dm-verity.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It does mount stuff (see roothash
in https://www.freedesktop.org/software/systemd/man/latest/systemd-veritysetup-generator.html), and it's incompatible with both root=gpt-auto
and root=fstab
unfortunately. I'd very much liked the latter to not be the case, but it is.
Re "automatically mounting", also see this Matrix discussion.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This can be done much simpler, by avoiding to build full images. See: https://github.com/nikstur/nix-store-veritysetup-generator/blob/main/nix/tests/nix-store-veritysetup-generator.nix
supportedFilesystems = [ "erofs" ]; | ||
|
||
# This adds some udev rules that are required for dm-verity to work. | ||
services.lvm.enable = true; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I find it odd that you need to enable this yourself. This should be enabled when you enable dm-verity support.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yeah, I agree. But looking around, I think it's uncommon to have modules enable things in other modules. Is there some kind of agreement around this?
For desktops, or more volatile use-cases (say image-based Linux with A/B-boot), I agree that it's way too complex currently. But for immutable image-based servers, I think this isn't a problem. And for that, at least in my case, I just don't want a writable root at all. I want to specifically enable where I can write to (e.g.
I agree more or less, but unfortunately, using |
@msanft The comments, option values, etc. should probably say “dm-verity” rather than just “verity,” as there's another filesystem integrity feature in Linux called “fs-verity”... and I've been working on integrating that, at least within my config repo (my goal being to extend the guarantees from Secure Boop to the whole system environment, and have the fs-verity root metadata be part of boot measurement... which your PR also achieves, fs- and dm-verity just have different tradeoffs) |
Description of changes
This adds support for using verity-protected root filesystems on NixOS, implemented by
systemd-veritysetup-generator
. This generator looks for verity partitions (e.g. as created bysystemd-repart
) and mounts them automatically. It acts as an alternative to the other generators supported at the moment. (Namelysystemd-gpt-auto-generator
andsystemd-fstab-generator
).The tentative API looks as follows:
I'm not sure yet whether this API is good. I couldn't think of anything else you'd need to have configurability of yet, but I'm happy to get some feedback on this.
Closes #285254
Things done
nix.conf
? (See Nix manual)sandbox = relaxed
sandbox = true
nix-shell -p nixpkgs-review --run "nixpkgs-review rev HEAD"
. Note: all changes have to be committed, also see nixpkgs-review usage./result/bin/
)Add a 👍 reaction to pull requests you find important.