Full Disk Encryption with LUKS

Updated

October 30, 2026

Full Disk Encryption with LUKS

Full Disk Encryption (FDE) protects stored data from physical theft, forensic imaging, and unauthorized offline tampering. In Linux, standard disk encryption is implemented via the kernel’s dm-crypt device-mapper target and managed by LUKS (Linux Unified Key Setup).

+-----------------------------------------------------------+
|              LUKS / dm-crypt Architecture                 |
|                                                           |
| [ Userspace Filesystem: /dev/mapper/root (ext4 / btrfs) ] |
|                             |                             |
|                             v                             |
| [ dm-crypt Kernel Layer (AES-XTS-256 hardware crypto) ]   |
|                             |                             |
|                             v                             |
| [ Physical Partition: /dev/nvme0n1p2 (Encrypted Ciphertext)|
|   ├── LUKS2 Header (Keyslots, Argon2id KDF salt/params)   |
|   └── Encrypted Payload Data                              |
+-----------------------------------------------------------+

LUKS2 Header and Key Derivation (Argon2id)

LUKS separates the Master Encryption Key (which encrypts the actual disk blocks) from the Passphrases typed by users: - The master key is stored securely inside the on-disk LUKS header, encrypted by up to 32 independent keyslots. - When you enter your passphrase, cryptsetup uses Argon2id (a memory-hard Password Key Derivation Function) to compute a decryption key for the keyslot. - Argon2id requires significant RAM (typically 1 GB) and CPU time to evaluate, rendering GPU and ASIC brute-force dictionary attacks computationally infeasible.

Setting Up LUKS Encryption from the Command Line

# 1. Format the partition as a LUKS2 encrypted volume:
# cryptsetup luksFormat --type luks2 --cipher aes-xts-plain64 \
    --key-size 512 --hash sha512 --pbkdf argon2id /dev/vda2

# 2. Open the encrypted container and map it to a plaintext virtual device:
# cryptsetup open /dev/vda2 byol-root
Enter passphrase for /dev/vda2:

# 3. Format the decrypted mapping with a standard filesystem:
# mkfs.ext4 -L "BYOL_ROOT" /dev/mapper/byol-root

# 4. Mount the filesystem for target installation:
# mount /dev/mapper/byol-root /mnt/target

Unlocking in Early Userspace (Initramfs)

In the initramfs /init script, add the unlock logic before mounting /newroot:

echo "[initramfs] Unlocking encrypted root storage..."
cryptsetup open "$ROOT_DEV" cryptroot
mount /dev/mapper/cryptroot /newroot

You can also seal the encryption key inside a hardware TPM 2.0 (Trusted Platform Module) chip using systemd-cryptenroll --tpm2-device=auto, enabling automatic cryptographic unlocking only when UEFI firmware and kernel PCR registers remain untampered!