System Configuration
Everything needed to build my NixOS system. Note this is highly customized configuration that’s not targeting a wide audience. However, feel free to copy and use any parts of if you like in your own configuration.
Table of Contents
Folder Structure
The following is 1 level deep directory structure generated using tree -L 1 -d
.
. ├── config ├── config-backups ├── emacs ├── hosts ├── keyboard-firmware ├── modules ├── nvim ├── profiles ├── secrets ├── users └── xmonad
config
Config files used in NixOS that are symlinked to /.config/
and managed with
home manager.
config-backups
Miscellaneous configuration files that I’m backing up and are not deployed automatically.
emacs / nvim
My emacs configuration code. See its readme for more information.
I typically only use Vim if Emacs is not available for some reason. In the
init.vim
file there are just the most important key bindings in my customized
Evil / Vim keybindings
hosts
host specific configuration files.
keyboard-firmware
Holds my keyboard firmware code managed by Nix and the readme that goes into depth on my key layout and customized Evil / Vim keybindings.
modules, profiles, and users
similar to and inspired by: https://devos.divnix.com/index.html
secrets
A place for me to store encrypted secrets using git-crypt.
xmonad
My Xmonad configuration code which is symlinked by home-manager. See its readme for more information.
NixOS
Build Custom ISO
I have a custom bootable ISO that provides a graphical environment similar to the one in nixpkgs with a few nice to have tools and my Emacs configuration for installing NixOS.
To build it:
git clone https://github.com/willbush/system.git
cd system
nix build ".#iso"
The ISO will be in the ./result/iso
build result folder.
Write Custom ISO to a USB stick
Use lsblk
to determine the device and replace /dev/sdX
in the example below
with your device. You should not have the device mounted before running the
following command. In addition, the exact file name will probably be different
from the example below. Also see the manual on this topic for additional
information.
sudo dd if=./result/iso/nixos-21.03.20201209.e9158ec-x86_64-linux.iso of=/dev/sdX status=progress bs=4M
If you’re in Windows try https://rufus.ie/.
Install
The primary source of documentation for installing NixOS is the manual. The following are my own notes on how I install things in various situations. I thought about making a install script that automates most of this for me, but it just doesn’t seem worth it with the varying use cases and low frequency of re-formatting.
Virt Manager
- File > New virtual machine > Forward.
- Choose ISO > Forward (it should auto-detect that it’s NixOS).
- Choose Memory and CPU amount (~4 CPUs and ~6148 RAM when host can afford it) > Forward.
- Choose available disk size (I usually increase to 30 GiB) > Forward.
- Check the
Customize configuration before install
> Forward. - In the Overview section consider changing the Firmware from BIOS to UEFI > Apply
- In the Video QXL section change the model Virtio and enable 3D acceleration (allows increasing desktop resolution) > Apply > Begin Installation.
- Once booted into the ISO the first thing I do is go to View > Scale Display Always. In addition, I increase the resolution using Display Configuration for plasma5.
Dual booting NixOS with Windows
These are my abridged notes on dual booting Windows 10 along side NixOS on a single drive and UEFI system. The following outlines how to ensure the EFI partition that Windows creates isn’t ridiculously small, how to remove the Recovery partition that Windows creates, and how to shrink the Primary partition to make space for NixOS.
Create custom sized EFI partition that NixOS will share and Install
- Boot into the Windows setup and select custom install.
- Delete all partitions on the drive until only unallocated space remains.
- Press Shift+F10 to open an elevated command prompt.
- Open the disk partitioning tool’s REPL by entering
diskpart
. - Enter
list disk
andselect disk n
where n is your disk number. create partition efi size=512
to create a EFI system partition 512MiB.format quick fs=fat32 label=System
- Enter
exit
twice to get out of the REPL and command prompt. - Select the unallocated space and hit next (it will automatically utilize the created EFI partition).
Delete Recovery partition
- Once booted into Windows open another elevated command prompt and
diskpart
. - Again enter
list disk
andselect disk n
where n is your disk number. list partition
andselect partition n
where n is the Recovery partition number.delete partition override
andexit
twice.
Shrink Primary partition to make space for NixOS
- Open the Disk management GUI application.
- Right click on the large
C:
NTFS partition and shrink it to your desired size. - Continue with the UEFI version of the next section.
Basic partitioning and formatting
The following is mostly just following the manual instructions here. However, I
switched to using cfdisk
instead of parted
because I’ve hit the misalignment
warning using parted
when following the manual’s instructions. Most
suggestions to fix the warning involve using percentages, but that’s annoying
when you want to create 3 or more partitions. The cfdisk
utility allows
specifying sizes and auto aligns partitions optimally.
- Note that one can wipe all the file systems on a device using
sudo wipefs -a /dev/sdX
which is useful to start over or prepare a device. - Note your system booted in UEFI mode when
/sys/firmware/efi/
folder exists and has files in it.
BIOS
sudo cfdisk
- select dos
- new > 2G (adjust size to your liking) > primary > type > Linux swap / Solaris.
- Select free space > new > enter (for remaining space) > primary.
- Write > yes > quit
Check alignment
At this point I like to use parted
just to double check the alignment.
- Open a parted REPL:
sudo parted
- Print all devices to determine the device to format:
print all
- Select device:
select /dev/sda
(Note the exact disk depends on yourprint all
output.) align-check optimal 1
and repeat for2
(both should output aligned)q
to quit.
Formatting
sudo mkswap -L swap /dev/sda1
sudo mkfs.ext4 -L nixos /dev/sda2
Mount
Mount the target NixOS file system:
sudo mount /dev/disk/by-label/nixos /mnt
Continue to the Installation section.
UEFI
sudo cfdisk
- select gpt (if prompted)
- new > 512M > type > EFI System (skip this step if dual booting with Windows)
- select free space
- new > 2G (adjust size to your liking) > type > Linux swap
- Select free space > new > enter (for remaining space)
- Write > yes > quit
Check alignment
At this point I like to use parted just to double check the alignment.
- Open a parted REPL:
sudo parted
- Print all devices to determine the device to format:
print all
- Select device:
select /dev/sda
(Note the exact disk depends on yourprint all
output.) align-check optimal 1
and repeat all partitions (all should output aligned)q
to quit.
Formatting
sudo mkfs.fat -F 32 -n boot /dev/sda1 # Skip when dual booting Windows.
sudo mkswap -L swap /dev/sda2
sudo mkfs.ext4 -L nixos /dev/sda3
Mount
Mount the target NixOS file system:
sudo mkdir -p /mnt/boot
sudo mount /dev/disk/by-label/boot /mnt/boot #by-label/SYSTEM if partition created by Windows
sudo mount /dev/disk/by-label/nixos /mnt
Installation
- If you have swap, then enable it now.
When the
hardware-configuration.nix
is generated it won’t include an entry for the swap partition unless you enable it before generating the file.sudo swapon /dev/sda2
- Prepare the configuration
sudo nixos-generate-config --root /mnt cd /mnt/etc/nixos sudo git clone https://github.com/willbush/system.git
For a new machine setup the new machine in
flake.nix
and under./system/hosts/
using the generatedhardware-configuration.nix
.Change the hashed user passwords in
user.nix
. These hashed passwords can be generated withmkpasswd -m sha-512
.Disable anything else that depends on unlocking the encrypted secrets folder (just
syncthing
at the time of writing this).Be sure to stage all new files created in repository as required for flakes.
- Install
Replace betelgeuse in the following command with your machine name.
sudo nixos-install --flake /mnt/etc/nixos/system/#betelgeuse --no-root-passwd --impure reboot
Notes:
- No root password needs to be created because it should be specified in
user.nix
as a hashed password. - Impure flag is needed because nix thinks
/mnt/nix/store
as a non-store path.
- No root password needs to be created because it should be specified in
- Move system repository
After booting into the newly installation, I personally prefer my system repository in my home directory (change the user as needed):
sudo mv /etc/nixos/system ~/ sudo chown -R will ~/system/
Update
To update all the flake inputs:
nix flake update
To up update a single input:
nix flake update --update-input nixpkgs
Nix Repl
To open the flake in a nix repl
do the following:
nix run '.#repl'
Switch
Build and switch to the generation provided by the flake for machine / host name:
sudo nixos-rebuild switch --flake <PATH_TO_GIT_REPO>#<MACHINE>
For example:
git clone https://github.com/willbush/system.git
cd system
sudo nixos-rebuild switch --flake '.#betelgeuse'
The .
before the #
is the path to the git repository. What comes after the
#
is the machine / host name which can be found enumerated in the flakes.nix
file.
Flake Learning Resources
- https://nixos.wiki/wiki/Flakes
- Original RFC
- Flake talk at NixConf
- https://www.tweag.io/blog/2020-05-25-flakes/
- https://www.tweag.io/blog/2020-06-25-eval-cache/
- https://www.tweag.io/blog/2020-07-31-nixos-flakes/
Flake Examples
- https://github.com/colemickens/nixos-flake-example
- https://github.com/hlissner/dotfiles
- https://github.com/lexuge
- https://github.com/divnix/devos
NixOS on WSL2
Thanks to NixOS-WSL I can run NixOS in WSL2 on Windows.
Anytime I do this, I need to check what’s changed since last time and update code copied from that repo into ./hosts/nixos-wsl. Code was copied there because they don’t yet have modular flake support.
I can build my own tarball:
nix build .#nixosConfigurations.nixos-wsl.config.system.build.tarball
The tarball ends up in ./result/tarball/nixos-system-x86_64-linux.tar.gz
Copy it over to Windows and install:
PS C:\Users\will\Downloads> mkdir C:\NixOS PS C:\Users\will\Downloads> wsl --import NixOS C:\NixOS\ .\nixos-system-x86_64-linux.tar.gz --version 2 PS C:\Users\will\Downloads> wsl -d NixOS $ /nix/var/nix/profiles/system/activate $ exit
Set NixOS as the default wsl -s NixOS
and wsl
will now take me into the
NixOS distribution.
Bootstrap my WSL2 flake using NixOS-WSL’s provided tarball
- Download the tarball from their GitHub page.
- Perform same steps above to install the tarball.
sudo nano /etc/nixos/configuration.nix
Edit the configuration to enable nix flakes and add the git package.
{ # ... nix = { package = pkgs.nixUnstable; extraOptions = '' experimental-features = nix-command flakes ''; }; # List packages installed in system profile. environment.systemPackages = with pkgs; [ git ]; # ... }
Rebuild and switch:
sudo nixos-rebuild switch
- Clone this repository and rebuild switch:
sudo nixos-rebuild switch --flake '/home/nixos/system/#nixos-wsl'
License
Dual licensed under either:
- Apache License, Version 2.0 (LICENSE-APACHE)
- MIT license (LICENSE-MIT)
at your option.
However, code under the ./hosts/nixos-wsl/
directory is distributed solely
under the Apache License, Version 2.0. See its readme for more information.