diff --git a/pkgs/bootstrap/archlinux/default.nix b/pkgs/bootstrap/archlinux/default.nix new file mode 100644 index 0000000..46dad06 --- /dev/null +++ b/pkgs/bootstrap/archlinux/default.nix @@ -0,0 +1,102 @@ +{ + lib, + concatText, + fetchzip, + stdenvNoCC, + writeText, + writeShellApplication, + + bash, + cacert, + coreutils, + pacman, + systemd, + zstd, + + repos ? ["core" "community" "extra"], + keyring-version ? "20241015-1", + keyring-hash ? "sha256-7IegfprKTNn0aPRMgTw34SEc/GRCfy92mE9CVI4rxr0=", + mirror ? "https://mirror.rackspace.com/archlinux/$repo/os/$arch", +}: rec { + keyring = (fetchzip.override { withUnzip = false; }) { + url = "${builtins.replaceStrings ["$repo" "$arch"] ["core" "x86_64"] mirror}/archlinux-keyring-${keyring-version}-any.pkg.tar.zst"; + hash = keyring-hash; + nativeBuildInputs = [ zstd ]; + stripRoot = false; + postFetch = '' + rm "$out"/.BUILDINFO "$out"/.INSTALL "$out"/.MTREE "$out"/.PKGINFO + mkdir "$out"/share/pacman -p + mv "$out"/usr/share/pacman/keyrings "$out"/share/pacman + rm -rf "$out"/usr + ''; + }; + + pacman_conf_in = + writeText + "pacman-mirrors.conf" + (lib.strings.concatLines + (lib.map + (repo: '' + [${repo}] + Server = ${mirror} + '') + repos)); + + pacman_conf = concatText "pacman.conf" [ "${pacman}/etc/pacman.conf" pacman_conf_in ]; + + bootstrap = writeShellApplication { + name = "archlinux-bootstrap"; + + runtimeInputs = [ coreutils pacman systemd ]; + + text = '' + if [ $# -lt 1 ]; then + echo "usage: $0 [directory] [pkgs ...]" + exit 1 + fi + + newroot="$1" + shift + + echo "Installing arch linux to $newroot" + + # set up new base filesystem + install -dm0755 "$newroot" + install -dm0755 "$newroot"/var/{cache/pacman/pkg,lib/pacman,log} + install -dm0755 "$newroot"/{dev,run,etc/pacman.d} + install -dm1777 "$newroot"/tmp + install -dm0555 "$newroot"/{sys,proc} + + # set up mountpoint for nix + install -dm0755 "$newroot"/nix + + # temporarily set up /etc/mtab, pacman needs this to work + ln -sf /proc/mounts "$newroot"/etc/mtab + + # fully initialize the keyring ahead of entering the container + pacman_conf="${pacman_conf}" + pacman-key --gpgdir "$newroot"/etc/pacman.d/gnupg --config "$pacman_conf" --init + pacman-key --gpgdir "$newroot"/etc/pacman.d/gnupg --config "$pacman_conf" \ + --populate archlinux --populate-from "${keyring}/share/pacman/keyrings" + + # install the config file + install -Dm0755 "$pacman_conf" "$newroot"/etc/pacman.conf + + # bootstrap the system. allow pacman to overwrite the existing mtab entry + systemd-nspawn -D "$newroot" --bind-ro=/nix \ + -E SSL_CERT_FILE=${cacert}/etc/ssl/certs/ca-bundle.crt \ + -E PATH=/usr/bin/ \ + -- \ + "${pacman}/bin/pacman" -Sy --noconfirm --overwrite /etc/mtab base "$@" + + # remove nix mount point + rmdir "$newroot"/nix + + echo "Done installing!" + echo "Set root password:" + echo " sudo systemd-nspawn -UD \"$newroot\" -- /bin/passwd root" + echo "Boot system:" + echo " sudo systemd-nspawn -bUD \"$newroot\"" + ''; + }; +}