diff --git a/apple-silicon-support/default.nix b/apple-silicon-support/default.nix new file mode 100644 index 00000000..71a5dd0f --- /dev/null +++ b/apple-silicon-support/default.nix @@ -0,0 +1,7 @@ +{ ... }: + +{ + imports = [ + ./modules/default.nix + ]; +} diff --git a/nix/m1-support/boot-m1n1/default.nix b/apple-silicon-support/modules/boot-m1n1/default.nix similarity index 91% rename from nix/m1-support/boot-m1n1/default.nix rename to apple-silicon-support/modules/boot-m1n1/default.nix index ca0a5fb1..39e94c56 100644 --- a/nix/m1-support/boot-m1n1/default.nix +++ b/apple-silicon-support/modules/boot-m1n1/default.nix @@ -1,12 +1,14 @@ { config, pkgs, lib, ... }: let - bootM1n1 = config.hardware.asahi.pkgs.callPackage ../m1n1 { + pkgs' = config.hardware.asahi.pkgs; + + bootM1n1 = pkgs'.m1n1.override { isRelease = true; withTools = false; customLogo = config.boot.m1n1CustomLogo; }; - bootUBoot = config.hardware.asahi.pkgs.callPackage ../u-boot { + bootUBoot = pkgs'.uboot-asahi.override { m1n1 = bootM1n1; }; diff --git a/nix/m1-support/default.nix b/apple-silicon-support/modules/default.nix similarity index 50% rename from nix/m1-support/default.nix rename to apple-silicon-support/modules/default.nix index 50cfd4b4..1ae87bb9 100644 --- a/nix/m1-support/default.nix +++ b/apple-silicon-support/modules/default.nix @@ -7,14 +7,22 @@ ./boot-m1n1 ]; - config = { - hardware.asahi.pkgs = if config.hardware.asahi.pkgsSystem != "aarch64-linux" - then import (pkgs.path) { - system = config.hardware.asahi.pkgsSystem; - crossSystem.system = "aarch64-linux"; - } - else pkgs; - }; + config = + let + cfg = config.hardware.asahi; + in { + nixpkgs.overlays = lib.mkBefore [ cfg.overlay ]; + + hardware.asahi.pkgs = + if cfg.pkgsSystem != "aarch64-linux" + then + import (pkgs.path) { + crossSystem.system = "aarch64-linux"; + localSystem.system = cfg.pkgsSystem; + overlays = [ cfg.overlay ]; + } + else pkgs; + }; options.hardware.asahi = { pkgsSystem = lib.mkOption { @@ -35,5 +43,19 @@ with the system defined by `hardware.asahi.pkgsSystem`. ''; }; + + overlay = lib.mkOption { + type = lib.mkOptionType { + name = "nixpkgs-overlay"; + description = "nixpkgs overlay"; + check = lib.isFunction; + merge = lib.mergeOneOption; + }; + default = import ../packages/overlay.nix; + defaultText = "overlay provided with the module"; + description = '' + The nixpkgs overlay for asahi packages. + ''; + }; }; } diff --git a/nix/m1-support/kernel/default.nix b/apple-silicon-support/modules/kernel/default.nix similarity index 92% rename from nix/m1-support/kernel/default.nix rename to apple-silicon-support/modules/kernel/default.nix index 02f1baa5..985c159d 100644 --- a/nix/m1-support/kernel/default.nix +++ b/apple-silicon-support/modules/kernel/default.nix @@ -3,11 +3,14 @@ { config, pkgs, lib, ... }: { config = { - boot.kernelPackages = config.hardware.asahi.pkgs.callPackage ./package.nix { - inherit (config.boot) kernelPatches; - _4KBuild = config.hardware.asahi.use4KPages; - withRust = config.hardware.asahi.withRust; - }; + boot.kernelPackages = let + pkgs' = config.hardware.asahi.pkgs; + in + pkgs'.linux-asahi.override { + inherit (config.boot) kernelPatches; + _4KBuild = config.hardware.asahi.use4KPages; + withRust = config.hardware.asahi.withRust; + }; # we definitely want to use CONFIG_ENERGY_MODEL, and # schedutil is a prerequisite for using it diff --git a/nix/m1-support/kernel/edge.nix b/apple-silicon-support/modules/kernel/edge.nix similarity index 100% rename from nix/m1-support/kernel/edge.nix rename to apple-silicon-support/modules/kernel/edge.nix diff --git a/nix/m1-support/mesa/default.nix b/apple-silicon-support/modules/mesa/default.nix similarity index 85% rename from nix/m1-support/mesa/default.nix rename to apple-silicon-support/modules/mesa/default.nix index 0cdb697e..7dfea554 100644 --- a/nix/m1-support/mesa/default.nix +++ b/apple-silicon-support/modules/mesa/default.nix @@ -5,14 +5,6 @@ && config.hardware.asahi.experimentalGPUInstallMode == mode); in lib.mkMerge [ (lib.mkIf config.hardware.asahi.useExperimentalGPUDriver { - # make the Asahi Mesa available via an overlay so the user has access to it - # (being careful not to create infinite recursion if the user wants to overlay - # it over the original Mesa) - nixpkgs.overlays = [ - (final: prev: { - mesa-asahi-edge = final.callPackage ./package.nix { inherit (prev) mesa; }; - }) - ]; # install the drivers hardware.opengl.package = pkgs.mesa-asahi-edge.drivers; diff --git a/nix/m1-support/peripheral-firmware/default.nix b/apple-silicon-support/modules/peripheral-firmware/default.nix similarity index 60% rename from nix/m1-support/peripheral-firmware/default.nix rename to apple-silicon-support/modules/peripheral-firmware/default.nix index 5133c51a..2a478e6d 100644 --- a/nix/m1-support/peripheral-firmware/default.nix +++ b/apple-silicon-support/modules/peripheral-firmware/default.nix @@ -11,24 +11,25 @@ ]; hardware.firmware = let - asahi-fwextract = pkgs.callPackage ../asahi-fwextract {}; - in lib.mkIf ((config.hardware.asahi.peripheralFirmwareDirectory != null) - && config.hardware.asahi.extractPeripheralFirmware) [ - (pkgs.stdenv.mkDerivation { - name = "asahi-peripheral-firmware"; + pkgs' = config.hardware.asahi.pkgs; + in + lib.mkIf ((config.hardware.asahi.peripheralFirmwareDirectory != null) + && config.hardware.asahi.extractPeripheralFirmware) [ + (pkgs.stdenv.mkDerivation { + name = "asahi-peripheral-firmware"; - nativeBuildInputs = [ asahi-fwextract pkgs.cpio ]; + nativeBuildInputs = [ pkgs'.asahi-fwextract pkgs.cpio ]; - buildCommand = '' - mkdir extracted - asahi-fwextract ${config.hardware.asahi.peripheralFirmwareDirectory} extracted + buildCommand = '' + mkdir extracted + asahi-fwextract ${config.hardware.asahi.peripheralFirmwareDirectory} extracted - mkdir -p $out/lib/firmware - cat extracted/firmware.cpio | cpio -id --quiet --no-absolute-filenames - mv vendorfw/* $out/lib/firmware - ''; - }) - ]; + mkdir -p $out/lib/firmware + cat extracted/firmware.cpio | cpio -id --quiet --no-absolute-filenames + mv vendorfw/* $out/lib/firmware + ''; + }) + ]; }; options.hardware.asahi = { @@ -43,20 +44,15 @@ peripheralFirmwareDirectory = lib.mkOption { type = lib.types.nullOr lib.types.path; - default = let - paths = [ + + default = lib.findFirst (path: builtins.pathExists (path + "/all_firmware.tar.gz")) null + [ # path when the system is operating normally - "/boot/asahi" + /boot/asahi # path when the system is mounted in the installer - "/mnt/boot/asahi" + /mnt/boot/asahi ]; - validPaths = (builtins.filter - (p: builtins.pathExists (p + "/all_firmware.tar.gz")) - paths) ++ [ null ]; - - firstPath = builtins.elemAt validPaths 0; - in if firstPath != null then "${/. + firstPath}" else null; description = '' Path to the directory containing the non-free non-redistributable peripheral firmware necessary for features like Wi-Fi. Ordinarily, this diff --git a/nix/m1-support/asahi-fwextract/add_entry_point.patch b/apple-silicon-support/packages/asahi-fwextract/add_entry_point.patch similarity index 100% rename from nix/m1-support/asahi-fwextract/add_entry_point.patch rename to apple-silicon-support/packages/asahi-fwextract/add_entry_point.patch diff --git a/nix/m1-support/asahi-fwextract/default.nix b/apple-silicon-support/packages/asahi-fwextract/default.nix similarity index 100% rename from nix/m1-support/asahi-fwextract/default.nix rename to apple-silicon-support/packages/asahi-fwextract/default.nix diff --git a/nix/m1-support/kernel/config b/apple-silicon-support/packages/linux-asahi/config similarity index 100% rename from nix/m1-support/kernel/config rename to apple-silicon-support/packages/linux-asahi/config diff --git a/nix/m1-support/kernel/default-pagesize-16k.patch b/apple-silicon-support/packages/linux-asahi/default-pagesize-16k.patch similarity index 100% rename from nix/m1-support/kernel/default-pagesize-16k.patch rename to apple-silicon-support/packages/linux-asahi/default-pagesize-16k.patch diff --git a/nix/m1-support/kernel/package.nix b/apple-silicon-support/packages/linux-asahi/default.nix similarity index 76% rename from nix/m1-support/kernel/package.nix rename to apple-silicon-support/packages/linux-asahi/default.nix index c618ab75..faa2e844 100644 --- a/nix/m1-support/kernel/package.nix +++ b/apple-silicon-support/packages/linux-asahi/default.nix @@ -1,11 +1,24 @@ -{ pkgs, _4KBuild ? false, withRust ? false, kernelPatches ? [ ] }: let - localPkgs = - # we do this so the config can be read on any system and not affect - # the output hash - if builtins ? currentSystem then import (pkgs.path) { system = builtins.currentSystem; } +{ lib +, pkgs +, callPackage +, writeShellScriptBin +, writeText +, linuxPackagesFor +, _4KBuild ? false +, withRust ? false +, kernelPatches ? [ ] +}: + +let + # TODO: use a pure nix regex parser instead of an IFD, and remove this workaround + localPkgs = if builtins ? currentSystem + then import (pkgs.path) { + crossSystem.system = builtins.currentSystem; + localSystem.system = builtins.currentSystem; + } else pkgs; - lib = localPkgs.lib; + inherit (localPkgs) runCommand; parseExtraConfig = cfg: let lines = builtins.filter (s: s != "") (lib.strings.splitString "\n" cfg); @@ -15,7 +28,7 @@ "CONFIG_${builtins.elemAt kv 0}=${builtins.elemAt kv 1}"; in lib.strings.concatMapStringsSep "\n" perLine lines; - readConfig = configfile: import (localPkgs.runCommand "config.nix" { } '' + readConfig = configfile: import (runCommand "config.nix" { } '' echo "{ } // " > "$out" while IFS='=' read key val; do [ "x''${key#CONFIG_}" != "x$key" ] || continue @@ -25,16 +38,16 @@ echo "{ }" >> $out '').outPath; - linux_asahi_pkg = { stdenv, lib, fetchFromGitHub, fetchpatch, linuxKernel, + linux-asahi-pkg = { stdenv, lib, fetchFromGitHub, fetchpatch, linuxKernel, rustPlatform, rustfmt, rust-bindgen, ... } @ args: let configfile = if kernelPatches == [ ] then ./config else - pkgs.writeText "config" '' - ${builtins.readFile ./config} + writeText "config" '' + ${builtins.readFile ./config} - # Patches - ${lib.strings.concatMapStringsSep "\n" ({extraConfig ? "", ...}: parseExtraConfig extraConfig) kernelPatches} - ''; + # Patches + ${lib.strings.concatMapStringsSep "\n" ({extraConfig ? "", ...}: parseExtraConfig extraConfig) kernelPatches} + ''; _kernelPatches = kernelPatches; in @@ -82,7 +95,7 @@ # is running, so we give the kernel build a rustc that wraps the real rustc # while setting the appropriate environment variable during its execution. # https://github.com/NixOS/nixpkgs/pull/209113 - (pkgs.writeShellScriptBin "rustc" '' + (writeShellScriptBin "rustc" '' NIX_LDFLAGS=-lgcc ${rustPlatform.rust.rustc}/bin/rustc "$@" '') ]; @@ -96,6 +109,6 @@ ''; } else {}); - linux_asahi = (pkgs.callPackage linux_asahi_pkg { }); -in pkgs.recurseIntoAttrs (pkgs.linuxPackagesFor linux_asahi) + linux-asahi = (callPackage linux-asahi-pkg { }); +in lib.recurseIntoAttrs (linuxPackagesFor linux-asahi) diff --git a/nix/m1-support/kernel/sven-iommu-4k.patch b/apple-silicon-support/packages/linux-asahi/sven-iommu-4k.patch similarity index 100% rename from nix/m1-support/kernel/sven-iommu-4k.patch rename to apple-silicon-support/packages/linux-asahi/sven-iommu-4k.patch diff --git a/nix/m1-support/m1n1/default.nix b/apple-silicon-support/packages/m1n1/default.nix similarity index 80% rename from nix/m1-support/m1n1/default.nix rename to apple-silicon-support/packages/m1n1/default.nix index 30d2b775..ee5450fd 100644 --- a/nix/m1-support/m1n1/default.nix +++ b/apple-silicon-support/packages/m1n1/default.nix @@ -1,7 +1,7 @@ { stdenv +, buildPackages , lib , fetchFromGitHub -, pkgsCross , python3 , dtc , imagemagick @@ -36,13 +36,13 @@ in stdenv.mkDerivation rec { fetchSubmodules = true; }; - makeFlags = [ "ARCH=aarch64-unknown-linux-gnu-" ] + makeFlags = [ "ARCH=${stdenv.cc.targetPrefix}" ] ++ lib.optional isRelease "RELEASE=1" ++ lib.optional withChainloading "CHAINLOADING=1"; nativeBuildInputs = [ dtc - pkgsCross.aarch64-multiplatform.buildPackages.gcc + buildPackages.gcc ] ++ lib.optional withChainloading rustenv ++ lib.optional (customLogo != null) imagemagick; @@ -86,14 +86,14 @@ EOF chmod +x $script done - GCC=${pkgsCross.aarch64-multiplatform.buildPackages.gcc} - BINUTILS=${pkgsCross.aarch64-multiplatform.buildPackages.binutils-unwrapped} + GCC=${buildPackages.gcc} + BINUTILS=${buildPackages.binutils-unwrapped} - ln -s $GCC/bin/*-gcc $out/toolchain-bin/ - ln -s $GCC/bin/*-ld $out/toolchain-bin/ - ln -s $BINUTILS/bin/*-objcopy $out/toolchain-bin/ - ln -s $BINUTILS/bin/*-objdump $out/toolchain-bin/ - ln -s $GCC/bin/*-nm $out/toolchain-bin/ + ln -s $GCC/bin/${stdenv.cc.targetPrefix}gcc $out/toolchain-bin/ + ln -s $GCC/bin/${stdenv.cc.targetPrefix}ld $out/toolchain-bin/ + ln -s $BINUTILS/bin/${stdenv.cc.targetPrefix}objcopy $out/toolchain-bin/ + ln -s $BINUTILS/bin/${stdenv.cc.targetPrefix}objdump $out/toolchain-bin/ + ln -s $GCC/bin/${stdenv.cc.targetPrefix}nm $out/toolchain-bin/ '') + '' runHook postInstall ''; diff --git a/nix/m1-support/mesa/package.nix b/apple-silicon-support/packages/mesa-asahi-edge/default.nix similarity index 100% rename from nix/m1-support/mesa/package.nix rename to apple-silicon-support/packages/mesa-asahi-edge/default.nix diff --git a/apple-silicon-support/packages/overlay.nix b/apple-silicon-support/packages/overlay.nix new file mode 100644 index 00000000..635a41db --- /dev/null +++ b/apple-silicon-support/packages/overlay.nix @@ -0,0 +1,8 @@ +final: prev: { + linux-asahi = final.callPackage ./linux-asahi { }; + m1n1 = final.callPackage ./m1n1 { }; + uboot-asahi = final.callPackage ./uboot-asahi { }; + asahi-fwextract = final.callPackage ./asahi-fwextract { }; + mesa-asahi-edge = final.callPackage ./mesa-asahi-edge { inherit (prev) mesa; }; + # TODO: package alsa-ucm-conf-asahi for headphone jack support +} diff --git a/nix/m1-support/u-boot/default.nix b/apple-silicon-support/packages/uboot-asahi/default.nix similarity index 84% rename from nix/m1-support/u-boot/default.nix rename to apple-silicon-support/packages/uboot-asahi/default.nix index 95a9afd6..d9126314 100644 --- a/nix/m1-support/u-boot/default.nix +++ b/apple-silicon-support/packages/uboot-asahi/default.nix @@ -1,14 +1,11 @@ { lib , fetchFromGitHub , fetchpatch -, pkgs -, pkgsCross +, buildUBoot , m1n1 -}: let - # u-boot's buildInputs get a different hash and don't build right if we try to - # cross-build for aarch64 on itself for whatever reason - buildPkgs = if pkgs.stdenv.system == "aarch64-linux" then pkgs else pkgsCross.aarch64-multiplatform; -in (buildPkgs.buildUBoot rec { +}: + +(buildUBoot rec { src = fetchFromGitHub { # tracking: https://github.com/AsahiLinux/PKGBUILDs/blob/stable/uboot-asahi/PKGBUILD owner = "AsahiLinux"; diff --git a/default.nix b/default.nix deleted file mode 100644 index 7c7bd995..00000000 --- a/default.nix +++ /dev/null @@ -1,9 +0,0 @@ -let - pins = import ./nix/pins.nix; - overlays = [ - (import ./nix/overlay.nix) - (import pins.rust-overlay) - ]; -in { - nixpkgs ? pins.nixpkgs -}: (import nixpkgs { overlays = overlays; }).nixos-m1 diff --git a/flake.lock b/flake.lock new file mode 100644 index 00000000..fded32fa --- /dev/null +++ b/flake.lock @@ -0,0 +1,44 @@ +{ + "nodes": { + "nixpkgs": { + "locked": { + "lastModified": 1673796341, + "narHash": "sha256-1kZi9OkukpNmOaPY7S5/+SlCDOuYnP3HkXHvNDyLQcc=", + "owner": "nixos", + "repo": "nixpkgs", + "rev": "6dccdc458512abce8d19f74195bb20fdb067df50", + "type": "github" + }, + "original": { + "owner": "nixos", + "repo": "nixpkgs", + "rev": "6dccdc458512abce8d19f74195bb20fdb067df50", + "type": "github" + } + }, + "root": { + "inputs": { + "nixpkgs": "nixpkgs", + "rust-overlay": "rust-overlay" + } + }, + "rust-overlay": { + "flake": false, + "locked": { + "lastModified": 1674440843, + "narHash": "sha256-kMCGL1wADpbcgGiMgj1pcOxbLy2zfmzsn46YCMWwtIE=", + "owner": "oxalica", + "repo": "rust-overlay", + "rev": "57b363f390f031b8b8d26235c2d21b0ad5a84640", + "type": "github" + }, + "original": { + "owner": "oxalica", + "repo": "rust-overlay", + "type": "github" + } + } + }, + "root": "root", + "version": 7 +} diff --git a/flake.nix b/flake.nix new file mode 100644 index 00000000..902697a6 --- /dev/null +++ b/flake.nix @@ -0,0 +1,73 @@ +{ + description = "Apple Silicon support for NixOS"; + + inputs = { + nixpkgs = { + # https://hydra.nixos.org/jobset/mobile-nixos/unstable/evals + # these evals have a cross-compiled stdenv available + url = "github:nixos/nixpkgs/6dccdc458512abce8d19f74195bb20fdb067df50"; + }; + + rust-overlay = { + url = "github:oxalica/rust-overlay"; + flake = false; + }; + }; + + outputs = { self, ... }@inputs: + let + # build platforms supported for uboot in nixpkgs + systems = [ "aarch64-linux" "x86_64-linux" ]; # "i686-linux" omitted + + forAllSystems = inputs.nixpkgs.lib.genAttrs systems; + in + { + overlays = rec { + apple-silicon-overlay = import ./apple-silicon-support/packages/overlay.nix; + default = apple-silicon-overlay; + }; + + nixosModules = rec { + apple-silicon-support = ./apple-silicon-support; + default = apple-silicon-support; + }; + + packages = forAllSystems (system: + let + pkgs = import inputs.nixpkgs { + crossSystem.system = "aarch64-linux"; + localSystem.system = system; + overlays = [ + (import inputs.rust-overlay) + self.overlays.default + ]; + }; + in { + inherit (pkgs) m1n1 uboot-asahi; + + installer-bootstrap = + let + installer-system = inputs.nixpkgs.lib.nixosSystem { + inherit system; + + # make sure this matches the post-install + # `hardware.asahi.pkgsSystem` + pkgs = import inputs.nixpkgs { + crossSystem.system = "aarch64-linux"; + localSystem.system = system; + overlays = [ self.overlays.default ]; + }; + + specialArgs = { + modulesPath = inputs.nixpkgs + "/nixos/modules"; + }; + + modules = [ + ./iso-configuration + { hardware.asahi.pkgsSystem = system; } + ]; + }; + in installer-system.config.system.build.isoImage; + }); + }; +} diff --git a/nix/installer-bootstrap/iso-configuration.nix b/iso-configuration/default.nix similarity index 66% rename from nix/installer-bootstrap/iso-configuration.nix rename to iso-configuration/default.nix index 15c5b7eb..dacda568 100644 --- a/nix/installer-bootstrap/iso-configuration.nix +++ b/iso-configuration/default.nix @@ -3,22 +3,22 @@ { imports = [ ./installer-configuration.nix - ../m1-support + ../apple-silicon-support ]; # include those modules so the user can rebuild the install iso. that's not - # especially useful at this point, but the user will need the m1-support + # especially useful at this point, but the user will need the apple-silicon-support # directory for their own config. installer.cloneConfigIncludes = [ "./installer-configuration.nix" - "./m1-support" + "./apple-silicon-support" ]; - # copy the m1-support and installer configs into the iso + # copy the apple-silicon-support and installer configs into the iso boot.postBootCommands = lib.optionalString config.installer.cloneConfig '' - if ! [ -e /etc/nixos/m1-support ]; then + if ! [ -e /etc/nixos/apple-silicon-support ]; then cp ${./installer-configuration.nix} /etc/nixos/installer-configuration.nix - cp -r ${../m1-support} /etc/nixos/m1-support + cp -r ${../apple-silicon-support} /etc/nixos/apple-silicon-support fi ''; } diff --git a/nix/installer-bootstrap/installer-configuration.nix b/iso-configuration/installer-configuration.nix similarity index 94% rename from nix/installer-bootstrap/installer-configuration.nix rename to iso-configuration/installer-configuration.nix index db18f370..d5b80350 100644 --- a/nix/installer-bootstrap/installer-configuration.nix +++ b/iso-configuration/installer-configuration.nix @@ -29,7 +29,7 @@ fileSystems = lib.mkOverride 60 config.lib.isoFileSystems; boot.postBootCommands = let - asahi-fwextract = pkgs.callPackage ../m1-support/asahi-fwextract {}; + inherit (config.hardware.asahi.pkgs) asahi-fwextract; in '' for o in $(