Tags: #Artix Linux #security #encryption #FDE #systemd #OpenRC #UEFI #MBR #GPT #LUKS #LVM
Artix Linux: Full Disk Encryption with UEFI
Not everyone fells happy and confident about systemd. In order to keep peace within a linux-based operating system, administrators may study, serve and use the art of mystical energy of the Force…
Introduction
Artix Linux is a systemd-free linux-based distribution, which is derived from Arch Linux. Therefore, it is somewhat “backward-compatible”, as it uses its repositories including the AUR. However, it uses OpenRC instead of the intrusive systemd.
The installation process (without encryption) is “somewhat” described on the project Wiki. The installation ISO can be downloaded from several mirrors and as yet, comes in three flavours: lxqt, i3 and base.
Within the respective (lxqt/i3) graphical user interface (GUI), the first two options provide an installation wizard that can be triggered by the calamares
command, which is a distribution-independent installer framework. The base-flavoured option lacks these features, due to which it is very light-weighted and preferred.
The downloaded ISO image can be transferred to a USB flash medium using the dd
command as follows:
$ dd if=/source/image of=/dev/target bs=4M status=progress && sync
The From CD/DVD/ISO option has to be selected in the GRUB boot menu (and NOT the From Stick/HDD). Those who dared to use the forbidden (second) option, experienced problems with polkit and other issues, examples of which can be found: here, here, here etc.

Artix GRUB Menu Selection
The Goal
This is a brief tutorial to install Artix linux on a notebook, which is:
- equipped with Unified Extensible Firmware Interface (UEFI),
- equipped with a hard-drive (e.g. SSD), which will:
- be formatted using GUID Partition Table (GPT) disk scheme,
- contain two partitions:
- of type
EF00
(EFI System Partition (ESP)) to be mounted as/boot/EFI
with a min. size of 200 MiB,- denoted as
EFI System
byfdisk
, - denoted as
boot, esp
byparted
,
- denoted as
- of type
8E00
(Linux LVM) to contain the encrypted container that will be:- encrypted using Linux Unified Key Setup (LUKS),
- partitioned using Logical Volume Manager (LVM).
- of type
The aforementioned requirements will provide a full disk encryption (FDE) installation, i.e. the root and swap partitions (the lvm-volRoot
and lvm-volSwap
volumes, to be more precise) will be encrypted using the LVM on LUKS method. The only unencrypted partition will be the first partition, i.e. the ESP; and thus, the kernels and initramfs files in the /boot/
directory will be encrypted as well.

UEFI GRUB Disk Partitioning Scheme
Other Disk Format and Firmware Options
Other ideas of disk formatting and firmware options are discussed in: Linux: Full Disk Encryption with BIOS, UEFI using MBR, GPT, LUKS, LVM and GRUB
The Installation Process
Administrators can log into the machine using a terminal session and credentials artix/artix
and change to the privileged account by running:
$ sudo su
The developers changed the project mirrors several months ago. Yet, they haven’t been able to update the installation media accordingly (April 2018). Luckily, it can be repaired as follows:
$ echo "Server = https://mirrors.dotsrc.org/artix-linux/repos/\$repo/os/\$arch" > /etc/pacman.d/mirrorlist
In order to have software tools up-to-date, the pacman
’s database needs to be updated as follows:
$ pacman -Sy
Optionally, it may be handy to perform the installation remotely, i.e. over a (local) network via SSH. For that purpose, openssh
needs to be installed and activated as follows:
$ pacman -S --noconfirm glibc openssh openssh-openrc
$ rc-service sshd start
In order to log into the machine running SSH, the notoriously know command can be used as follows:
$ ssh artix@IP_ADDRESS
In order to manipulate disk partitions, the ISO image (live CD) comes with cfdisk
. However, it does not align partitions to block device I/O limits. It may seem useful to work with tools that do support such elementary features, such as parted
(fdisk
, gdisk
, etc.), which can be installed from the repository by running:
$ pacman -S parted
Disks Availability
Since the syntax of parted
is obvious for example purposes, it will be used in the following command examples. The available disk(s) can be checked as follows:
$ parted -s /dev/sdX print
The comparison of their syntax can be found, for example, in Troy’s Wiki.
Disk Format and Partitioning
The following commands WILL DELETE DATA. As discussed earlier, the SATA disk (/dev/sdX
) will be partitioned using the GPT, since the target machine (notebook) comes with a UEFI firmware (instead of BIOS).
$ parted -s /dev/sdX mklabel gpt
Due to the UEFI firmware, an EFI System Partition of 512MiB should be created in Linux environment (550 MiB is recommended). Additionally, all parted
commands can be run with -a optimal
parameter in order to align partitions accordingly as follows:
$ parted -s -a optimal /dev/sdX mkpart "primary" "fat16" "0%" "512MiB"
$ parted -s /dev/sdX set 1 esp on
Optionally, parted
can align partitions at any time by running:
$ parted -s /dev/sdX print
$ parted -s /dev/sdX align-check optimal <PARTITION_NUMBER>
Furthermore, an empty disk partition needs to be created in the rest of the space:
$ parted -s -a optimal /dev/sdX mkpart "primary" "ext4" "512MiB" "100%"
$ parted -s /dev/sdX set 2 lvm on
Disk Encryption and Logical Volumes
The disk encryption will utilise the Linux Unified Key Setup (LUKS), which is now part of an enhanced version of cryptsetup
, using dm-crypt (device-mapper crypt) as the disk encryption backend.
LUKS physical partition can be created and formatted as follows:
$ cryptsetup luksFormat -v /dev/sdX2
Alternatively, including more details (the following is the default):
$ cryptsetup -v --cipher aes-xts-plain64 --key-size 256 --hash sha256 --iter-time 2000 --use-urandom --verify-passphrase luksFormat /dev/sdX2
The LUKS-encrypted partition (/dev/sdX2
) needs to be opened and mounted using the device mapper (into e.g. lvm-system
):
$ cryptsetup luksOpen /dev/sdX2 lvm-system
Note: If any of the commands produces the following warning, it can be ignored, as: “This is because /run is not available inside the chroot.”
WARNING: Failed to connect to lvmetad. Falling back to device scanning.
or
/run/lvm/lvmetad.socket: connect failed: No such file or directory
or
WARNING: failed to connect to lvmetad: No such file or directory. Falling back to internal scanning.
Now it is possible to create a physical volume using the Logical Volume Manager (LVM) and the previously used id (lvm-system
) as follows:
$ pvcreate /dev/mapper/lvm-system
Having the physical volume, it is possible to create a logical volume group named lvmSystem
as follows:
$ vgcreate lvmSystem /dev/mapper/lvm-system
And having the logical volume group, the logical volumes can be created as follows. As an example, a 16GB for swap (volSwap
) and the rest for the root partition (volRoot
):
$ lvcreate -L 16G lvmSystem -n volSwap
$ lvcreate -l +100%FREE lvmSystem -n volRoot
Note: The size of a swap partition has always been part of many discussions. Basically, in order to have suspend-to-disk (hibernation) mechanism working, it is not necessary to have the swap of the same size as RAM. Reader discretion advised.
Having all physical and virtual disk partitions ready, it is possible to format them as follows (swap
, fat
for ESP and ext4
for /
):
$ mkswap /dev/lvmSystem/volSwap
$ mkfs.fat -n ESP /dev/sdX1
$ mkfs.ext4 -L volRoot /dev/lvmSystem/volRoot
Having each partition formatted, they can be mounted as follows:
$ swapon /dev/lvmSystem/volSwap
$ mount /dev/lvmSystem/volRoot /mnt
$ mkdir -p /mnt/boot/EFI
$ mount /dev/sdX1 /mnt/boot/EFI
Packages Installation, Kernel Compilation
Finally, the operating system parts can be downloaded and installed as follows:
$ basestrap /mnt base base-devel
The /etc/fstab
file can be created using various system identifiers, the following step uses UUIDs:
$ fstabgen -U /mnt >> /mnt/etc/fstab
Optionally, all solid-state disk (SSD) mountpoints can be updated with the discard
option to enable TRIM:
$ sed -i "s/ordered/ordered,discard/g" /mnt/etc/fstab
However, there are opinions that recommend against that. If in doubt about the hardware, the Periodic TRIM can be applied instead.
Optionally, size of the TMPFS partition (e.g. of size 8GB, i.e. half RAM size) can be changed as follows:
$ echo "tmpfs /tmp tmpfs nodev,nosuid,size=8G 0 0" >> /mnt/etc/fstab
Now, it is time to change root (chroot
) to the newly installed environment:
$ artools-chroot /mnt /bin/bash
System-wide locale
(e.g. en_AU.UTF-8
) can be set up as follows:
$ echo -e "en_AU.UTF-8 UTF-8" >> /etc/locale.gen
$ locale-gen
$ echo LANG=en_AU.UTF-8 > /etc/locale.conf
$ export LANG=en_AU.UTF-8
Time zone and hostname
(e.g. 4rt1x
) can be configured as follows:
$ ln -s /usr/share/zoneinfo/Continent/City /etc/localtime
$ echo "hostname=4rt1x" > /etc/conf.d/hostname
The /etc/mkinitcpio.conf
file enables to set up various kernel parameters. Within the HOOKS
part, the encrypt lvm2
need to be put between block
and filesystems
keywords in order to enable the FDE. It may also be useful to include the resume
keyword to enable suspend to disk options. However, this may not work at all times, such as with hardened kernels.
Finally, the GRUB’s /crypto_keyfile.bin
file can be specified to automatically unlock disk X
after system boot:
$ sed -i "s/FILES=(/FILES=(\/crypto_keyfile.bin/g" /etc/mkinitcpio.conf
$ sed -i "s/modconf block/modconf block encrypt lvm2 resume/g" /etc/mkinitcpio.conf
For more details regarding usage of /dev/random
and /dev/urandom
for keys generation, this ArchWiki page can be visited. A random-byte file can be generated in order to serve as key to automatically decrypt the system partition during boot by GRUB as follows:
$ dd if=/dev/random of=/crypto_keyfile.bin bs=512 count=8 iflag=fullblock
$ cryptsetup luksAddKey /dev/sdX2 /crypto_keyfile.bin
$ chmod 000 /crypto_keyfile.bin
Now, the kernel can be compiled and a new initramdisk created (the default kernel is now linux
):
$ mkinitcpio -p linux
Consequently, the root
password needs to be set up:
$ passwd
Boot Loader Installation
There are various bootloaders. However, the following commands use the GRUB (and its optional dependencies):
$ pacman -S grub efibootmgr
$ pacman -S dosfstools freetype2 fuse2 gptfdisk libisoburn mtools os-prober
$ pacman -S iw memtest86+ wpa_supplicant
Optionally when required and after considering that hibernation/resume will not work with hardened kernels, the resume
partition needs to be configured in the /etc/default/grub
file as follows:
$ sed -i "s/quiet/quiet resume=UUID=`blkid -s UUID -o value /dev/lvmSystem/volSwap`/g" /etc/default/grub
As discussed earlier, in order to prevent the password to open the LUKS volume to be asked the second time (the first time it is asked by GRUB), the /etc/mkinitcpio.conf
file (the FILES
variable) needs to be updated with the key file path reference as follows:
$ sed -i "s/GRUB_CMDLINE_LINUX=\"\"/GRUB_CMDLINE_LINUX=\"cryptdevice=UUID=`blkid -s UUID -o value /dev/sdX2`:lvm-system\"/g" /etc/default/grub
Grub needs to be configured in /etc/default/grub
in order to find the LUKS-encrypted partition as follows:
$ sed -i "s/#GRUB_ENABLE_CRYPTODISK/GRUB_ENABLE_CRYPTODISK/g" /etc/default/grub
Optionally, GRUB colours can be modified as follows:
$ sed -i "s/#GRUB_COLOR_NORMAL/GRUB_COLOR_NORMAL/g" /etc/default/grub
$ sed -i "s/#GRUB_COLOR_HIGHLIGHT/GRUB_COLOR_HIGHLIGHT/g" /etc/default/grub
Finally, GRUB can be installed at the beginning of the first disk (/dev/sdX
) that contains the ESP mounted in the /boot/EFI
directory as follows:
$ grub-install --target=x86_64-efi --efi-directory=/boot/EFI --bootloader-id=artix --recheck /dev/sdX
$ grub-mkconfig -o /boot/grub/grub.cfg
Note: Every change in the configuration of GRUB needs to be followed by the following command in order to be applied:
$ grub-mkconfig -o /boot/grub/grub.cfg
Note: When reinstalling GRUB, the following warnings may be observed and ignored:
/run/lvm/lvmetad.socket: connect failed: No such file or directory
or
WARNING: failed to connect to lvmetad: No such file or directory. Falling back to internal scanning.
This is because /run
is not available inside the chroot
. These warnings will not prevent the system from booting, provided that everything has been done correctly, so you may continue with the installation.
Optionally, the GRUB setup needs to be changed in order to prevent the (e)udev
from renaming the kernel eth0
, wlan0
interfaces to enp0s25
, wlp4s0
etc. using the optional net.ifnames=0
parameter as follows:
$ vi /etc/default/grub
GRUB_CMDLINE_LINUX="... net.ifnames=0"
$ grub-mkconfig -o /boot/grub/grub.cfg
Necessary Services Setup
In order to decrypt and use the LUKS/LVM volumes, the following services need to be installed and activated:
$ pacman -S device-mapper-openrc lvm2-openrc cryptsetup-openrc
$ rc-update add device-mapper boot
$ rc-update add lvm boot
$ rc-update add dmcrypt boot
The udev
service (eudev/eudev-openrc
) should be started by default in the sysinit
runlevel. Its activation can be confirmed as follows:
$ rc-status sysinit | grep udev
Service `netmount' needs non existent service `net'
udev [ stopped ]
udev-trigger [ stopped ]
The dbus
service should be installed and activated. Should it not, it can be done as follows:
$ rc-update add dbus default
The systemd project’s logind should be installed as part of the base
meta package. Should it not be activated, it can be done as follows:
$ rc-update add elogind boot
The haveged service is a simple entropy daemon useful for unpredictable random number generation, which can be installed and activated as follows:
$ pacman -S haveged haveged-openrc
$ rc-update add haveged default
Cron job daemons (cronie, fcron etc.) can be installed and activated as follows (e.g. cronie):
$ pacman -S cronie cronie-openrc
$ rc-update add cronie default
Adding Unprivileged User Accounts
As an example, the following list of commands adds a non-privileged user (USERNAME
) into the system as part of the wheel
and users
groups and including a prompt for password:
$ useradd -m -G wheel -s /bin/bash USERNAME
$ passwd USERNAME
Sudoers setup for the wheel
group can be simply changed as follows:
$ sed -i "s/# %wheel ALL=(ALL) ALL/%wheel ALL=(ALL) ALL/g" /etc/sudoers
Network Setup using Network Manager
If Network Manager GUI is the desired choice to manage network interfaces, the following needs to be run in order to install and activate the service:
$ pacman -S networkmanager networkmanager-openrc networkmanager-openvpn network-manager-applet
$ rc-update add NetworkManager default
Optionally, more plugin options for NetworkManager can be looked up as follows:
$ pacman -Ss networkmanager
Since the unprivileged user should be in either wheel
or network
group in order to manage network interfaces, it may be necessary to run, e.g.:
$ usermod -a -G wheel USERNAME
One of the downsides is that the passwords are stored in clear text in:
$ grep -H '^psk=' /etc/NetworkManager/system-connections/*
Another issue is a bit privacy-concerned, since the NetworkManager
service periodically connects to http://www.archlinux.org/check_network_status.txt
(formerly apollo.archlinux.org
) to check its online status.
$ curl http://www.archlinux.org/check_network_status.txt
NetworkManager is online
Luckily, the URL can be changed as follows:
$ vi /etc/NetworkManager/conf.d/11-connectivity-check.conf
[connectivity]
uri=http://server.domain.tld/nm-status/index.php
interval=120
response="You're up, buddy!"
#response="NetworkManager is online"
Obviously, a replacement URL needs to be accessible on another web server. Assuming that the web server runs HTTPD with PHP Support, the configuration can be updated as follows:
### server.domain.tld:80
server "server.domain.tld" {
...
# NetworkManager
location "/nm-status/index.php" {
root "/htdocs/nm-status"
root strip 1
fastcgi socket "/run/php-fpm.sock"
}
...
}
Naturally, the index.php
script needs to be created. The example is as follows:
$ mkdir /var/www/htdocs/nm-status
$ vi /var/www/htdocs/nm-status/index.php
<?php
header('X-NetworkManager-Status: online');
header('Content-Type: text/plain');
echo "You're up, buddy!";
header("HTTP/1.1 200 OK");
?>
Testing and verification:
$ curl http://server.domain.tld/nm-status/index.php
You're up, buddy!
Network Setup using RC scripts
If Network Manager GUI is not the preferred solution, relevant RC services need to be started during system startup (in the default
runlevel). In order to activate such option, the following commands need to be run to activate all interfaces (found in the /sys/class/net
directory):
$ rc-update add net.lo default
$ for i in `ls /sys/class/net | grep -v lo`; do
ln -s /etc/init.d/net.lo /etc/init.d/net.$i
rc-update add net.$i default
done
Note: The previous will not work if the default interface names recognised by udev
were changed to eth0
etc. It needs to be run manually and not as per the /sys/class/net
directory in chroot enviroment, e.g. for eth0
, it needs to be run as: ln -s /etc/init.d/net.lo /etc/init.d/net.eth0; rc-update add net.eth0 default
.
A WiFi interface can be configured using the WPA supplicant as follows:
$ wpa_passphrase "SSID" "PASSWORD" > /etc/wpa_supplicant/wpa_supplicant.conf
$ echo "modules_INTERFACE_ID=\"wpa_supplicant dhcpcd\"" >> /etc/conf.d/net
Optionally, the configuration of WPA supplicant can be verified using:
$ wpa_supplicant -iINTERFACE_ID -c/etc/wpa_supplicant/wpa_supplicant.conf
Optionally, to fine-tune any interface, there are many options present in the /etc/conf.d/net
file. The following may come handy to decrease the carrier timeout (in seconds), which is ten seconds by default (i.e. waiting until the physical interface is “brought up”):
$ echo "carrier_timeout_INTERFACE_ID=5" >> /etc/conf.d/net
Additional Services Setup
Optionally, numlock can be automatically enabled after system start (generally not desirable for laptops/notebooks):
$ pacman -S numlockx
$ rc-update add numlock default
Optionally, the bloody system beeper can be disabled as follows:
$ echo "blacklist pcspkr" > /etc/modprobe.d/nobeep.conf
SSH daemon can be installed as follows:
$ pacman -S openssh openssh-openrc
$ rc-update add sshd default
For some reason, the basestrap
command does install only group nobody
without the matching user nobody
. A brief check, whether the user and the group are present in the system, can be run as follows:
$ grep nobody /etc/group
nobody:x:99:
$ grep nobody /etc/passwd
<EMPTY-RESULT>
Should the result of the previous command is empty, user nobody
needs to be created manually in /etc/passwd
as follows:
$ UGID=`grep nobody /etc/group | awk -F: '{print $3}'`
$ echo "nobody:x:$UGID:$UGID:nobody:/:/usr/bin/nologin" >> /etc/passwd
Note: The missing account of user nobody
will prevent the SSH daemon from starting (after the installation is complete and system is restarted) such as the following:
$ rc-service sshd start
Privilege separation user nobody does not exist
ERROR: sshd failed to start
NTP, ACPI, Syslog-NG daemons can be installed and activated as follows:
$ pacman -S ntp ntp-openrc acpid acpid-openrc syslog-ng syslog-ng-openrc
$ rc-update add ntpd default
$ rc-update add acpid default
$ rc-update add syslog-ng default
Useful commands (will include samba, samba client):
$ pacman -S artools bash-completion lsof strace
$ pacman -S wget htop mc zip samba unrar p7zip unzip
$ pacman -S hdparm smartmontools hwinfo dmidecode
$ pacman -S whois rsync nmap tcpdump inetutils net-tools ndisc6
In order to access AUR, yaourt
can be installed:
$ pacman -S yaourt
Congratulations
The chroot can be escaped as follows:
$ exit
Optionally, everything can be unmounted (should be done automatically, though):
$ umount -R /mnt
$ swapoff -a
The system now can be rebooted:
$ reboot
Post Installation Steps
The very first step after the system restart and successful login attempt is to BACKUP THE LVM METADATA. The process is as simple as follows:
$ cp /etc/lvm/backup/* /somewhere/safe
Furthermore, a brief tutorial of how to install XFCE4 desktop environment is described in Artix Linux: Installation of XFCE4.