User:grazzolini
Overview
There is a recent and virtually undocumented GRUB feature called cryptodisk, which enables GRUB to ask for a password to open a LUKS (and possibly plain Dm-Crypt) container, to read it's configuration from and load any initramfs and kernel from. This option try to solve the issue of having an unencrypted boot partition. A great deal of this information was based on this post by Pavel Kogan. Just be careful following the instructions on it, because it has some inaccuracies, such as, this grub bug, which is already solved in the current grub version.
/boot
in a dedicated partition.Deciding where to place /boot
Using this feature, /boot
can become a normal directory inside the /
mount point. Also, it can be a separate logical volume, inside the same LVM on LUKS container as root
. You can choose any partition scheme you want. You'll need to create and use a keyfile inside your initramfs to avoid having to unlock twice your container. This problem is explained on Pavel Kogan's post. Just keep in mind that, by making /boot
as a directory inside /
, or by creating a logical volume under the same container as root
, you loose the ability of trying to check if your boot loader code was compromised with mkinitcpio-chkcryptobootAUR.
If you want that ability, /boot
must be placed in a separate container than your root
container. Accordingly, you should use a different passphrase and/or keyfile than your root
container. This setup has the drawback of having to type two passphrases, one for opening the boot container and the other for opening the root container.
Placing /boot inside /
This will cover both the installation process and the conversion from an already installed arch system to a /boot
cryptodisk setup. And both a BIOS/MBR or UEFI/GPR setup, with /boot
residing inside /
.
On the installation
BIOS/MBR setup
All your need to do is follow the advice on the LUKS page, skipping the creation of a separate boot
partition. You can, optionally, follow the LVM on LUKS steps, creating a separate logical volume for boot. That way /boot
will reside in the same root
volume group, inside the same LUKS container as the swap
and root
logical volumes.
UEFI/GPT setup
In this case, the ESP must exist and, unfortunately, be left unencrypted. You can follow the partition scheme example on Beginners' guide for creating this partition. If it already exists, because you already have another operational system booting from it, then leave it alone. After that, you can follow either the simple partition layout or the LVM on LUKS setup. You will need to mount it under another mount point than /boot
, because it is a directory under /
. I suggest /esp
. For the installation process, you will need to mount the ESP under the chosen alternative mount point and for the GRUB installation step, you will need to follow the GRUB alternative install method, passing the correct arguments to --efi-directory
and --boot-directory
options.
Converting an already installed system
BIOS/MBR
I assume your setup has a unencrypted boot
partition and a encrypted root
container. If you simply want to place /boot
inside /
, you need to copy it's contents:
# cp -a /boot /boot-new
Then unmount it:
# umount /boot
Now you'll need to delete the line in the /etc/fstab file regarding the /boot partition. After that, remove the existing mount point directory:
# rm -r /boot
After that, you need to rename the copy you made to replace the /boot path:
# mv /boot-new /boot
boot
unencrypted partition and it's space lying around in your disk. You can try to erase this partition, and try to rename and resize your luks container partition. But, since making this kind of changes on MBR is prone to error and data loss, I will not try to cover it in this article. You can always try to accomplish that in a virtual machine environment before trying to do it in your actual installationUEFI/GPT
If you are using your ESP as /boot
, then you can follow almost all the steps on the previous section. The difference here, is that you only need to move the files related with GRUB's configuration and any kernels and initramfs you might have on the partition. If you follow the steps for GRUB installation on UEFI, you must move every file inside the ESP, except the EFI directory:
# mkdir boot-new
Leave the EFI directory and move everything else to this new directory:
# mv /boot/grub /boot/initramfs-linux.img /boot/initramfs-linux-fallback.img /boot/vmlinuz-linux /boot-new
This should leave your ESP partition just like this:
# ls /boot
EFI
Now you can unmount your boot partition:
# umount /boot
Remove the directory mount point:
# rm -r /boot
And now move your new boot directory to it right place:
# mv /boot-new /boot
Now, since the ESP
must be accessible for you being able to reinstall GRUB, if needed, it must have an entry in your /etc/fstab file. I suggest you use blkid
then find your ESP partition id. Since your /boot
is now a directory under /
now, your ESP you need a different mount point. I suggest /esp
, but this is up to you. After this change, for a GRUB reinstallation, you'll need to use GRUB alternative install method. Just pass your /esp
mount point for the --efi-directory
option and your /boot
directory for the --boot-directory
option.
/boot in a dedicated partition
Since you probably already have your boot
as a separate partition, I will explain how to convert it to an encrypted one. The process for BIOS/MBR is quite simple, both in a fresh installation and the conversion process. For the UEFI/GPT case, the installation is also simple, but the conversion process involves partitioning.
On the installation
BIOS/MBR setup
You can follow the same partition scheme that is used for any LUKS installation. But, instead of the boot
partition be unencrypted, it will be also encrypted with LUKS. If you want to boot faster, I suggest you use a smaller hash size, than 512 and don't change the default iter-time. If you want your boot partition to still be secure while having a relatively faster container unlock, I suggest that you use sha256. It is the perfect trade off between security and speed. After formating your root
and boot
partition with LUKS, just unlock then, create a filesystem on them, and mount them as you would for the rest of the installation process. After you run the genfstab
command, you will note that in your /etc/fstab
file will contain your an entry for your /boot
mount point, but referring to the LUKS container. You will need to follow the instructions bellow for unlocking your boot
partition automatically on boot.
UEFI/GPT setup
As already mentioned, your ESP must be left unencrypted. So, instead of just having a ESP
and mount it as /boot
, you will need two partitions. One for the ESP
and another for your encrypted boot
. The same suggestions as above regarding your encrypted boot
partition formating and hash size apply. Also, as already mentioned here and here, your ESP must have a different mount point than /boot
. For the installation, mount your /boot
and /esp
partitions in their respective mount points and follow the rest of the process. When you run genfstab
it will have your ESP partition and your boot partition in /etc/fstab
.
Converting an already installed system
BIOS/MBR
The conversion process of a BIOS/MBR installation is quite straightforward.
First copy the data in your boot
partition:
# cp -a /boot /boot-new
Now umount the partition:
# umount /boot
Format your boot
partition with LUKS:
# cryptsetup -v --hash sha256 --key-size 256 --cipher aes-xts-plain64 luksFormat /dev/sda1
boot
partition with a different password than your root
partition, for obvious reasonsOpen your container:
# cryptsetup luksOpen /dev/sda1 sda1_crypt
Create the filesystem:
# mkfs.ext4 /dev/mapper/sda1_crypt
Now mount it back to /boot
:
# mount /dev/mapper/sda1_crypt /boot
And copy the data you created in the first step:
# mv /boot-new/* /boot
Remove the created directory:
# rm -r /boot-new
Now follow the steps bellow for the remaining configuration.
UEFI/GPT
First of all, I suggest you take notes on your current partition scheme. Running commands like
# parted -l
or
# gdisk -l /dev/sda
are good starting points. Also, I suggest that you backup your GPT partition table:
# sgdisk -b /gpt_backup
If you have a default GPT partition scheme with:
/dev/sda1 being your ESP
/dev/sda2 being your root LUKS container
What we are going to do is to resize your ESP partition, create a new one, and after that sort the partitions. Your scheme will become something like this:
/dev/sda1 still being your ESP, but smaller
/dev/sda2 being your new encrypted boot partition
/dev/sda3 being your root LUKS container
Start by copying your ESP files to another directory (beside the backup you made before):
# cp -a /boot /boot-new
Now umount it:
# umount /boot
The next step depends on the size of your ESP partition and if you boot another operational systems from it. If you followed the specification it will be at least 512MB. More than enough for our purposes. This setup might work with another ESP sizes, but depending on the number of kernels you use, your boot
partition might not have space for them all. If you simply boot arch from your ESP and use only one kernel, you can resize the ESP partition to very small sizes. The last I checked, GRUB's efistub was smaller than 200KB. My instructions will be based on a 512MB ESP partition size, adapt then as needed.
I used both parted and the gdisk
command in gptfdisk for this process.
Started parted on /dev/sda:
# parted /dev/sda
Print your partition scheme and note the end of your ESP partition and the start of your root LUKS container:
(parted) p
1 1049kB 538MB 537MB fat32 EFI System boot, esp 2 538MB <END OF DISK> <SIZE> Linux filesystem
Now, we will resize the ESP partition and shrink it. Beware that the FAT filesystem on it, will most likely need to be recreated. If you mount it after the resize, it will probably mount with no issues, but I suggest you to reformat it:
(parted) resizepart 1 256MB
Warning: Shrinking a partition can cause data loss, are you sure you want to continue? Yes/No? Yes
Now create a new partition, between your ESP and LUKS container partitions:
(parted) mkpart
Partition name? []? File system type? [ext2]? Start? 256MB End? 538MB Warning: The resulting partition is not properly aligned for best performance. Ignore/Cancel? Ignore
If you print again your partition scheme, you will see your new partition, but the number of it will be wrong:
(parted) p
Number Start End Size File system Name Flags 1 1049kB 256MB 255MB EFI System boot, esp 3 256MB 538MB 282MB ext2 2 538MB <END OF DISK> <SIZE> Linux filesystem
Quit parted
and call gdisk
on your disk:
gdisk /dev/sda
Print your partition scheme on gdisk. It is clear why you need to sort your partitions:
{{hc|head=Command (? for help): p|output= Number Start (sector) End (sector) Size Code Name
1 2048 500000 243.1 MiB EF00 EFI System 2 1050624 <LAST SECTOR> <SIZE> GiB 8300 Linux filesystem 3 500001 1050623 268.9 MiB 8300
Now sort your partitions:
Command (? for help): s
You may need to edit /etc/fstab and/or your boot loader configuration!
And write your new partition scheme:
Command (? for help): w
Final checks complete. About to write GPT data. THIS WILL OVERWRITE EXISTING PARTITIONS!! Do you want to proceed? (Y/N): Y OK; writing new GUID partition table (GPT) to /dev/sda. The operation has completed successfully.
Despite the warning that gdisk
displayed, telling you that you might need to update your /etc/fstab
, if you use UUID to identify your partitions, you are probably safe.
Now, format your new boot
partition with crypsetup
and create a filesystem on it, as mentioned on the BIOS/MBR process.
/etc/crypttab configuration
This part of the setup is only relevant when boot is in a dedicated partition. Since your boot
partition is a separate LUKS container than your root
, you need to create a keyfile, so it will be mounted at boot time, without asking for a passphrase. I suggest you create a randomtext or binary keyfile and store it under your /etc
directory, with restrictive permissions. Then add it to your LUKS container. After that you will need to add it to /etc/crypttab. Just take care to use the same device mapper name in both /etc/crypttab
and /etc/fstab
, as is shown here Dm-crypt/System_configuration#Mounting_at_boot_time. GRUB will not use this keyfile for opening your boot
partition, both because it will not have any access to it, and also, as far as I know, GRUB do not have this feature at this moment.
GRUB configuration
This is the easiest part of the setup. You do not need to add any additional modules to GRUB configuration, nor change any of the parameters already on it. Assuming, of course, that you already have a functional LUKS setup.
Just open /etc/default/grub
and add this to the end:
GRUB_ENABLE_CRYPTODISK=y
After that we need to recreated GRUB configuration and after that follow GRUB's alternative install method. For example, in a UEFI setup case, assuming you have your boot
partition mounted or being a directory at /boot
and that you have your ESP
partition mounted at /esp
, by issuing the following commands you will have a functional GRUB cryptodisk setup:
grub-mkconfig -o /boot/grub/grub.cfg
grub-install --target=x86_64-efi --efi-directory=/esp --bootloader-id=grub_uefi --boot-directory=/boot --recheck
All you need to do is reboot your machine, and GRUB should prompt for a password to open the partition containing it's configuration.