diff --git a/nixos-modules/genode-core.nix b/nixos-modules/genode-core.nix index 16cebb1..0a4a5d6 100644 --- a/nixos-modules/genode-core.nix +++ b/nixos-modules/genode-core.nix @@ -25,14 +25,22 @@ in { prefix = mkOption { type = types.str; example = "hw-pc-"; + description = "String prefix signifying the Genode core in use."; }; supportedSystems = mkOption { type = types.listOf types.str; example = [ "i686-genode" "x86_64-genode" ]; + description = "Hardware supported by this core."; }; - basePackages = mkOption { type = types.listOf types.package; }; + basePackages = mkOption { + type = types.listOf types.package; + description = '' + List of packages to make availabe before the Nix store is ready. + These are baked into . + ''; + }; children = mkOption { type = with types; @@ -57,17 +65,6 @@ in { boot = { - kernel = mkOption { - type = types.path; - default = "${pkgs.genodePackages.bender}/bender"; - }; - - initrd = mkOption { - type = types.str; - default = "${pkgs.genodePackages.bender}/bender"; - description = "Path to an image or a command-line arguments"; - }; - configFile = mkOption { type = types.path; description = '' @@ -87,6 +84,18 @@ in { description = "Attr set of initial ROM modules"; }; + storeFsUuid = mkOption { + type = types.str; + default = import ./store-fs-uuid; + description = "Custom partition type of the nix-store file-system."; + }; + + storePartUuid = mkOption { + type = types.str; + default = import ./partition-type; + description = "Custom partition type of the nix-store file-system."; + }; + storeBackend = mkOption { type = types.enum [ "tarball" "usb" ]; # "parent"? default = "tarball"; @@ -119,7 +128,6 @@ in { storePaths = mkOption { type = with types; listOf package; - example = literalExample "[ pkgs.genodePackages.vfs_lwp ]"; description = '' Derivations to be included in the Nix store in the generated boot image. ''; @@ -148,20 +156,17 @@ in { }; mergeManifests = inputs: - localPackages.writeTextFile { - name = "manifest.dhall"; - text = with builtins; - let - f = head: input: - if hasAttr "manifest" input then - '' - ${head}, { mapKey = "${ - lib.getName input - }", mapValue = ${input.manifest} }'' - else - abort "${input.pname} does not have a manifest"; - in (foldl' f "[" inputs) + "]"; - }; + with builtins; + let + f = head: input: + if hasAttr "manifest" input then + '' + ${head}, { mapKey = "${ + lib.getName input + }", mapValue = ${input.manifest} }'' + else + abort "${input.pname} does not have a manifest"; + in (foldl' f "[" inputs) + "]"; romDirectories = filterAttrs (_: value: value != null) (mapAttrs (name: value: @@ -181,51 +186,85 @@ in { message = "invalid Genode core for this system"; }]; - genode.core.children.store_fs.configFile = let + genode.core.basePackages = + lib.optional (config.genode.boot.storeBackend == "usb") + pkgs.genodePackages.part_block; - storeVfsConfig = { - tarball = '' - VFS.vfs [ VFS.leafAttrs "tar" (toMap { name = "${config.system.build.tarball.fileName}.tar" }) ] - ''; - usb = '' - VFS.vfs [ VFS.leafAttrs "rump" (toMap { fs = "ext2fs", ram="12M" }) ] - ''; - }.${config.genode.boot.storeBackend}; + genode.core.children = + # Component to steer the store_fs to a specific partition + (if config.genode.boot.storeBackend == "usb" then { + part_block.configFile = builtins.toFile "part_block.dhall" '' + let Genode = env:DHALL_GENODE - storeResources = { - tarball = "Init.Resources.default"; - usb = "Init.Resources::{ caps = 256, ram = Genode.units.MiB 16 }"; - }.${config.genode.boot.storeBackend}; + let Init = Genode.Init - in builtins.toFile "store_fs.dhall" '' - let Genode = env:DHALL_GENODE - - let Init = Genode.Init - - let VFS = Genode.VFS - - in Init.Child.flat - Init.Child.Attributes::{ - , binary = "vfs" - , resources = ${storeResources} - , config = Init.Config::{ - , content = [ ${storeVfsConfig} ] - , policies = - [ Init.Config.Policy::{ - , service = "File_system" - , label = Init.LabelSelector.suffix "nix-store" - , attributes = toMap { root = "/nix/store" } + in Init.Child.flat + Init.Child.Attributes::{ + , binary = "part_block" + , resources = Init.Resources::{ ram = Genode.units.MiB 8 } + , config = Init.Config::{ + , attributes = toMap { ignore_mbr = "yes" } + , policies = + [ Init.Config.Policy::{ + , service = "Block" + , label = Init.LabelSelector.prefix "store_fs" + , attributes = toMap + { partition = "1" + , writeable = "yes" + , TODO = "select by partition UUID" + } + } + ] } - , Init.Config.Policy::{ - , service = "File_system" - , label = Init.LabelSelector.prefix "store_rom" - , attributes = toMap { root = "/" } + } + ''; + } else + { }) // { + store_fs.configFile = let + + storeVfsConfig = { + tarball = '' + VFS.vfs [ VFS.leafAttrs "tar" (toMap { name = "${config.system.build.tarball.fileName}.tar" }) ] + ''; + usb = '' + VFS.vfs [ VFS.leafAttrs "rump" (toMap { fs = "ext2fs", ram="12M" }) ] + ''; + }.${config.genode.boot.storeBackend}; + + storeResources = { + tarball = "Init.Resources.default"; + usb = "Init.Resources::{ caps = 256, ram = Genode.units.MiB 16 }"; + }.${config.genode.boot.storeBackend}; + + in builtins.toFile "store_fs.dhall" '' + let Genode = env:DHALL_GENODE + + let Init = Genode.Init + + let VFS = Genode.VFS + + in Init.Child.flat + Init.Child.Attributes::{ + , binary = "vfs" + , resources = ${storeResources} + , config = Init.Config::{ + , content = [ ${storeVfsConfig} ] + , policies = + [ Init.Config.Policy::{ + , service = "File_system" + , label = Init.LabelSelector.suffix "nix-store" + , attributes = toMap { root = "/nix/store" } + } + , Init.Config.Policy::{ + , service = "File_system" + , label = Init.LabelSelector.prefix "store_rom" + , attributes = toMap { root = "/" } + } + ] + } } - ] - } - , provides = [ "File_system" ] - } - ''; + ''; + }; genode.boot.configFile = let tarball = @@ -236,9 +275,21 @@ in { usb = [ pkgs.genodePackages.rump ]; }.${config.genode.boot.storeBackend}; - manifest = mergeManifests (map addManifest (with pkgs.genodePackages; - config.genode.core.basePackages ++ storeBackendInputs - ++ [ init cached_fs_rom jitter_sponge report_rom vfs ])); + coreInputs = with builtins; + concatMap (getAttr "inputs") (attrValues config.genode.core.children); + + manifest = + # Manifests are Dhall metadata to be attached to every + # package to be used for dynamically buildings enviroments + # using Dhall expressions. Probably not worth pursuing. + pkgs.writeText "manifest.dhall" (mergeManifests (map addManifest + (with pkgs.genodePackages; + config.genode.core.basePackages ++ storeBackendInputs + ++ [ init cached_fs_rom jitter_sponge report_rom vfs ] + ++ coreInputs)) + ''# [ { mapKey = "romModules", mapValue = [ '' + + (toString + (mapAttrsToList (k: v: '', { mapKey = "${k}", mapValue = "${v}" }'') + config.genode.boot.romModules)) + " ] } ]"); storeRomPolicies = mapAttrsToList (name: value: '', { mapKey = "${name}", mapValue = "${value}" }'') @@ -253,7 +304,7 @@ in { Genode.Init.LabelSelector.Type.Partial { prefix = Some "nixos -> ${name}", suffix = Some "${suffix}" } } - , route = Genode.Init.Route.parent (Some "${suffix}") + , route = Genode.Init.Route.parentLabel "${suffix}" } '') value.coreROMs) config.genode.init.children)); @@ -282,8 +333,8 @@ in { EOF ''; - genode.boot.storePaths = [ config.genode.init.configFile ] - ++ (builtins.attrValues romDirectories); + genode.boot.storePaths = with builtins; + [ config.genode.init.configFile ] ++ (attrValues romDirectories); # Create the tarball of the store to live in core ROM system.build.tarball = @@ -316,17 +367,21 @@ in { ''; system.build.bootDriveImage = let - storeFsImage = pkgs.callPackage ./lib/make-ext2-fs.nix { - inherit (config.genode.boot) storePaths; - inherit (config.system.build) qemu; - volumeLabel = "NIXOS_GENODE"; + espImage = import ./lib/make-esp-fs.nix { inherit config pkgs; }; + storeFsImage = + pkgs.callPackage ./lib/make-ext2-fs.nix { inherit config pkgs; }; + bootDriveImage = import ./lib/make-bootable-image.nix { + inherit config pkgs espImage storeFsImage; }; - in storeFsImage; + in bootDriveImage; + + # virtualisation.useEFIBoot = config.genode.boot.storeBackend == "usb"; virtualisation.qemu.options = lib.optionals (config.genode.boot.storeBackend == "usb") [ - "-usb" + "-bios ${pkgs.buildPackages.OVMF.fd}/FV/OVMF.fd" "-drive id=usbdisk,file=${config.system.build.bootDriveImage},if=none,readonly" + "-usb" "-device usb-storage,drive=usbdisk" ];