Full Disk Encryption
Warning: Your drive's block device and other information may be different, so make sure it is correct.
Partitioning
Boot a live image and login.
Create a single physical partition on the disk using cfdisk, marking it as bootable. For an MBR system, the partition layout should look like the following.
# fdisk -l /dev/sda
Disk /dev/sda: 48 GiB, 51539607552 bytes, 100663296 sectors
Units: sectors of 1 * 512 = 512 bytes
Sector size (logical/physical): 512 bytes / 512 bytes
I/O size (minimum/optimal): 512 bytes / 512 bytes
Disklabel type: dos
Disk identifier: 0x4d532059
Device Boot Start End Sectors Size Id Type
/dev/sda1 * 2048 100663295 100661248 48G 83 Linux
UEFI systems will need the disk to have a GPT disklabel and an EFI system partition. The required size for this may vary depending on needs, but 100M should be enough for most cases. For an EFI system, the partition layout should look like the following.
# fdisk -l /dev/sda
Disk /dev/sda: 48 GiB, 51539607552 bytes, 100663296 sectors
Units: sectors of 1 * 512 = 512 bytes
Sector size (logical/physical): 512 bytes / 512 bytes
I/O size (minimum/optimal): 512 bytes / 512 bytes
Disklabel type: gpt
Disk identifier: EE4F2A1A-8E7F-48CA-B3D0-BD7A01F6D8A0
Device Start End Sectors Size Type
/dev/sda1 2048 264191 262144 128M EFI System
/dev/sda2 264192 100663262 100399071 47.9G Linux filesystem
Encrypted volume configuration
Cryptsetup defaults to LUKS2, yet GRUB releases before 2.06 only had support for LUKS1.
LUKS2 is only partially supported by GRUB; specifically, only the PBKDF2 key derivation function is implemented, which is not the default KDF used with LUKS2, that being Argon2i (GRUB Bug 59409). LUKS encrypted partitions using Argon2i (as well as the other KDF) can not be decrypted. For that reason, this guide only recommends LUKS1 be used.
Keep in mind the encrypted volume will be /dev/sda2
on EFI systems, since
/dev/sda1
is taken up by the EFI partition.
# cryptsetup luksFormat --type luks1 /dev/sda1
WARNING!
========
This will overwrite data on /dev/sda1 irrevocably.
Are you sure? (Type uppercase yes): YES
Enter passphrase:
Verify passphrase:
Once the volume is created, it needs to be opened. Replace voidvm
with an
appropriate name. Again, this will be /dev/sda2
on EFI systems.
# cryptsetup luksOpen /dev/sda1 voidvm
Enter passphrase for /dev/sda1:
Once the LUKS container is opened, create the LVM volume group using that partition.
# vgcreate voidvm /dev/mapper/voidvm
Volume group "voidvm" successfully created
There should now be an empty volume group named voidvm
.
Next, logical volumes need to be created for the volume group. For this example,
I chose 10G for /
, 2G for swap
, and will assign the rest to /home
.
# lvcreate --name root -L 10G voidvm
Logical volume "root" created.
# lvcreate --name swap -L 2G voidvm
Logical volume "swap" created.
# lvcreate --name home -l 100%FREE voidvm
Logical volume "home" created.
Next, create the filesystems. The example below uses XFS as a personal preference of the author. Any filesystem supported by GRUB will work.
# mkfs.xfs -L root /dev/voidvm/root
meta-data=/dev/voidvm/root isize=512 agcount=4, agsize=655360 blks
...
# mkfs.xfs -L home /dev/voidvm/home
meta-data=/dev/voidvm/home isize=512 agcount=4, agsize=2359040 blks
...
# mkswap /dev/voidvm/swap
Setting up swapspace version 1, size = 2 GiB (2147479552 bytes)
System installation
Next, setup the chroot and install the base system.
# mount /dev/voidvm/root /mnt
# mkdir -p /mnt/home
# mount /dev/voidvm/home /mnt/home
On a UEFI system, the EFI system partition also needs to be mounted.
# mkfs.vfat /dev/sda1
# mkdir -p /mnt/boot/efi
# mount /dev/sda1 /mnt/boot/efi
Copy the RSA keys from the installation medium to the target root directory:
# mkdir -p /mnt/var/db/xbps/keys
# cp /var/db/xbps/keys/* /mnt/var/db/xbps/keys/
Before we enter the chroot to finish up configuration, we do the actual install. Do not forget to use the appropriate repository URL for the type of system you wish to install.
# xbps-install -Sy -R https://repo-default.voidlinux.org/current -r /mnt base-system lvm2 cryptsetup grub
[*] Updating `https://repo-default.voidlinux.org/current/x86_64-repodata' ...
x86_64-repodata: 1661KB [avg rate: 2257KB/s]
130 packages will be downloaded:
...
UEFI systems will have a slightly different package selection. The installation command for a UEFI system will be as follows.
# xbps-install -Sy -R https://repo-default.voidlinux.org/current -r /mnt base-system cryptsetup grub-x86_64-efi lvm2
When it's done, we can enter the chroot with
xchroot(1)
(from xtools
) and finish
up the configuration. Alternatively, entering the chroot can be done
manually.
# xchroot /mnt
[xchroot /mnt] # chown root:root /
[xchroot /mnt] # chmod 755 /
[xchroot /mnt] # passwd root
[xchroot /mnt] # echo voidvm > /etc/hostname
and, for glibc systems only:
[xchroot /mnt] # echo "LANG=en_US.UTF-8" > /etc/locale.conf
[xchroot /mnt] # echo "en_US.UTF-8 UTF-8" >> /etc/default/libc-locales
[xchroot /mnt] # xbps-reconfigure -f glibc-locales
Filesystem configuration
The next step is editing /etc/fstab
, which will depend on how you configured
and named your filesystems. For this example, the file should look like this:
# <file system> <dir> <type> <options> <dump> <pass>
tmpfs /tmp tmpfs defaults,nosuid,nodev 0 0
/dev/voidvm/root / xfs defaults 0 0
/dev/voidvm/home /home xfs defaults 0 0
/dev/voidvm/swap swap swap defaults 0 0
UEFI systems will also have an entry for the EFI system partition.
/dev/sda1 /boot/efi vfat defaults 0 0
GRUB configuration
Next, configure GRUB to be able to unlock the filesystem. Add the following line
to /etc/default/grub
:
GRUB_ENABLE_CRYPTODISK=y
Next, the kernel needs to be configured to find the encrypted device. First, find the UUID of the device.
[xchroot /mnt] # blkid -o value -s UUID /dev/sda1
135f3c06-26a0-437f-a05e-287b036440a4
Edit the GRUB_CMDLINE_LINUX_DEFAULT=
line in /etc/default/grub
and add
rd.lvm.vg=voidvm rd.luks.uuid=<UUID>
to it. Make sure the UUID matches the one
for the sda1
device found in the output of the
blkid(8) command above. This will be
/dev/sda2
on EFI systems.
LUKS key setup
And now to avoid having to enter the password twice on boot, a key will be configured to automatically unlock the encrypted volume on boot. First, generate a random key.
[xchroot /mnt] # dd bs=1 count=64 if=/dev/urandom of=/boot/volume.key
64+0 records in
64+0 records out
64 bytes copied, 0.000662757 s, 96.6 kB/s
Next, add the key to the encrypted volume.
[xchroot /mnt] # cryptsetup luksAddKey /dev/sda1 /boot/volume.key
Enter any existing passphrase:
Change the permissions to protect the generated key.
[xchroot /mnt] # chmod 000 /boot/volume.key
[xchroot /mnt] # chmod -R g-rwx,o-rwx /boot
This keyfile also needs to be added to /etc/crypttab
. Again, this will be
/dev/sda2
on EFI systems.
voidvm /dev/sda1 /boot/volume.key luks
And then the keyfile and crypttab
need to be included in the initramfs. Create
a new file at /etc/dracut.conf.d/10-crypt.conf
with the following line:
install_items+=" /boot/volume.key /etc/crypttab "
Complete system installation
Next, install the boot loader to the disk.
[xchroot /mnt] # grub-install /dev/sda
Ensure an initramfs is generated:
[xchroot /mnt] # xbps-reconfigure -fa
Exit the chroot
, unmount the filesystems, and reboot the system.
[xchroot /mnt] # exit
# umount -R /mnt
# reboot