1{ lib, ... }:
2{
3
4 name = "nix-store-veritysetup";
5
6 meta.maintainers = with lib.maintainers; [ nikstur ];
7
8 nodes.machine =
9 { config, modulesPath, ... }:
10 {
11
12 imports = [
13 "${modulesPath}/image/repart.nix"
14 ];
15
16 image.repart = {
17 name = "nix-store";
18 partitions = {
19 "nix-store" = {
20 storePaths = [ config.system.build.toplevel ];
21 stripNixStorePrefix = true;
22 repartConfig = {
23 Type = "linux-generic";
24 Label = "nix-store";
25 Format = "erofs";
26 Minimize = "best";
27 Verity = "data";
28 VerityMatchKey = "nix-store";
29 };
30 };
31 "nix-store-verity" = {
32 repartConfig = {
33 Type = "linux-generic";
34 Label = "nix-store-verity";
35 Verity = "hash";
36 VerityMatchKey = "nix-store";
37 Minimize = "best";
38 };
39 };
40 };
41 };
42
43 boot.initrd = {
44 systemd = {
45 enable = true;
46 dmVerity.enable = true;
47 };
48 nix-store-veritysetup.enable = true;
49 };
50
51 virtualisation = {
52 mountHostNixStore = false;
53 qemu.drives = [
54 {
55 name = "nix-store";
56 file = ''"$NIX_STORE"'';
57 }
58 ];
59 fileSystems = {
60 "/nix/store" = {
61 fsType = "erofs";
62 device = "/dev/mapper/nix-store";
63 };
64 };
65 };
66
67 };
68
69 testScript =
70 { nodes, ... }:
71 ''
72 import os
73 import json
74 import subprocess
75 import tempfile
76
77 with open("${nodes.machine.system.build.image}/repart-output.json") as f:
78 data = json.load(f)
79
80 storehash = data[0]["roothash"]
81
82 os.environ["QEMU_KERNEL_PARAMS"] = f"storehash={storehash}"
83
84 tmp_disk_image = tempfile.NamedTemporaryFile()
85
86 subprocess.run([
87 "${nodes.machine.virtualisation.qemu.package}/bin/qemu-img",
88 "create",
89 "-f",
90 "qcow2",
91 "-b",
92 "${nodes.machine.system.build.image}/${nodes.machine.image.repart.imageFile}",
93 "-F",
94 "raw",
95 tmp_disk_image.name,
96 ])
97
98 os.environ["NIX_STORE"] = tmp_disk_image.name
99
100 machine.start()
101
102 print(machine.succeed("findmnt"))
103 print(machine.succeed("dmsetup info nix-store"))
104
105 machine.wait_for_unit("multi-user.target")
106 '';
107
108}