Skip to content

Instantly share code, notes, and snippets.

@henningta
Last active August 23, 2022 16:01
Show Gist options
  • Save henningta/251a17c2b3459ff275e4420a98fe0b22 to your computer and use it in GitHub Desktop.
Save henningta/251a17c2b3459ff275e4420a98fe0b22 to your computer and use it in GitHub Desktop.
My method of installing Arch Linux - based on the ArchWiki installer guide

Arch Linux Installation

This file contains step-by-step instructions on how I install Arch Linux. Most of this information is taken from the ArchWiki articles and installation guide: https://wiki.archlinux.org/index.php/installation_guide.

Securely wipe existing data (optional, recommended)

Identify the drive to be wiped, and map it to a temporary, encrypted container partition

cryptsetup open --type plain /dev/sdX container --key-file /dev/urandom

Check that the new container partition exists as /dev/mapper/container

fdisk -l | grep container

Wipe the container (this can take a while). The "bs=1M" option can be configured on a per-device basis to speed up the overall wipe time. Some more info here: https://stackoverflow.com/questions/6161823/dd-how-to-calculate-optimal-blocksize.

dd if=/dev/zero of=/dev/mapper/container status=progress bs=1M

Close the container

cryptsetup close container

Pre-installation and networking

In the BIOS settings, set the storage mode to AHCI and SecureBoot to off Check for EFI support (check BIOS settings to enable UEFI boot)

ls /sys/firmware/efi/efivars

For ethernet connections, skip to the "Wired connection" section

Wireless connection

Enter the iwd interactive prompt

iwctl

Determine the name of the wireless network interface being used (let's assume it's wlan0, but it may be different)

# in the iwd interactive prompt
device list

Display available networks

# in the iwd interactive prompt
station wlan0 scan
station wlan0 get-networks

Connect to an available network and confirm connection status

# in the iwd interactive prompt
station wlan0 connect <network-name>
station wlan0 show

# exit the iwd interactive prompt
exit

# test connection
ping google.com

Continue with the "Wired connection" steps below to get an IP address and check the connection

Wired connection

Get an automatic IP configuration and confirm the connection works with a ping

dhcpcd
ping archlinux.org

Update the system clock

timedatectl set-ntp true

Encryption and partitioning (LVM on LUKS)

Identify the drive to encrypt and partition (should be the same device which was wiped earlier).

fdisk -l

Physical partitioning

Create an EFI boot partition and an LVM partition

cgdisk /dev/sdX

If there are existing partitions (there will not be if you wiped the device), delete them and create new ones

Create a new partition at the first available free space block
- Size: 512M
- Type: ef00 (efi)
- Name: EFI
Create a new partition at the first available free space block *after* the EFI partition
- Size: 100%
- Type: 8e00 (lvm)
- Name: LVM
Write the changes to disk and quit cgdisk

LUKS encryption

Encrypt and open the LVM partition using LUKS

luksFormat options: --key-size (256, 512, etc.) --hash (sha256, sha512, etc.) --use-(u)random (determines randomness of generation)

cryptsetup luksFormat --type luks2 --key-size XXX --hash XXX --use-(u)random -v -/dev/sdX2
cryptsetup open /dev/sdX2 cryptvolm

LVM mapping

Create the LVM structure on the unlocked partition

pvcreate /dev/mapper/cryptvolm

Create the volume group "lv"

vgcreate lv /dev/mapper/cryptvolm

Create the desired logical volumes on the volume group

lvcreate -L 4G lv -n swap
lvcreate -L 20G lv -n root
lvcreate ...
lvcreate -l 100%FREE lv -n home

Format the file systems on each logical volume

mkfs.ext4 /dev/mapper/lv-root
mkfs.ext4 /dev/mapper/lv-home
mkfs.XXXX ...
mkswap /dev/mapper/lv-swap

File system mounting

Mount the file systems

mount /dev/mapper/lv-root /mnt
mkdir /mnt/home
mount /dev/mapper/lv-home /mnt/home
mkdir ...
mount ...
swapon /dev/mapper/lv-swap

Format and mount the boot partition

mkfs.fat -F32 /dev/sdX1
mkdir -p /mnt/boot/efi
mount /dev/sdX1 /mnt/boot/efi

Installation

Install some important packages to our mounted root

pacstrap /mnt base base-devel linux linux-firmware intel-ucode iwd lvm2 vim zsh

Configuration

Generate an fstab file from the partitions we mounted earlier

genfstab -U /mnt >> /mnt/etc/fstab

Log in as root on the installed system. All further steps should take place on the mounted device.

arch-chroot /mnt

Set the time zone

ln -sf /usr/share/zoneinfo/America/New_York /etc/localtime
hwclock --systohc

Uncomment en_US.UTF-8 UTF-8 in /etc/locale.gen, then generate the locale

/etc/locale.gen
...
en_US.UTF-8 UTF-8
...
locale-gen
echo LANG=en_US.UTF-8 >> /etc/locale.conf

Set the host name

echo arch-laptop >> /etc/hostname

Create the hosts file

/etc/hosts
127.0.0.1    localhost
::1          localhost
127.0.1.1    arch-laptop.localdomain  arch-laptop

Bootloader installation

Install the systemd bootloader to /boot/efi on the mounted device

bootctl --path=/boot/efi install

Create the arch EFI boot directory

mkdir -p /boot/efi/EFI/arch

Backup the default mkinitcpio config files

cp /etc/mkinitcpio.conf /etc/mkinitcpio.conf.bak
cp /etc/mkinitcpio.d/linux.preset /etc/mkinitcpio.d/linux.preset.bak

Configure mkinitcpio for encryption

/etc/mkinitcpio.conf
...
HOOKS=(base udev autodetect keyboard modconf block encrypt lvm2 filesystems fsck)
...

Edit the linux.preset file to point to the arch esp directory

/etc/mkinitcpio.d/linux.preset

# mkinitcpio preset file for the 'linux' package

# Directory to copy the kernel, initramfs, etc.
ESP_DIR="/boot/efi/EFI/arch"

ALL_config="/etc/mkinitcpio.conf"
ALL_kver="/boot/vmlinuz-linux"

PRESETS=('default' 'fallback')

#default_config="/etc/mkinitcpio.conf"
default_image="${ESP_DIR}/initramfs-linux.img"
default_options="-A esp-update-linux"

#fallback_config="/etc/mkinitcpio.conf"
fallback_image="${ESP_DIR}/initramfs-linux-fallback.img"
fallback_options="-S autodetect"

Create a hook to copy some files to the arch esp directory

/etc/initcpio/install/esp-update-linux

# Directory to copy the kernel, initramfs, etc.
ESP_DIR="/boot/efi/EFI/arch"

build() {
    cp -af /boot/vmlinuz-linux "${ESP_DIR}/"
    cp -af /boot/intel-ucode.img "${ESP_DIR}/"
}

help() {
    cat <<HELPEOF
This hook copies the kernel to the ESP partition
HELPEOF
}

Make it executable

chmod +x /etc/initcpio/install/esp-update-linux

Remove old .img files and rebuild the initramfs. Make sure .img files are built into /boot/efi/EFI/arch.

rm /boot/initramfs-linux-fallback.img
rm /boot/initramfs-linux.img
mkinitcpio -p linux

Bootloader update

Create a pacman hook to update the bootloader whenever systemd is updated

/etc/pacman.d/hooks/systemd-boot.hook

[Trigger]
Type = Package
Operation = Upgrade
Target = systemd

[Action]
Description = Updating systemd-boot...
When = PostTransaction
Exec = /usr/bin/bootctl --path=/boot/efi update

Bootloader configuration

Set the default boot loader settings

/boot/efi/loader/loader.conf
default  arch
timeout  0
editor   0

Copy the example boot entry into the bootloader entries directory

cp /usr/share/systemd/bootctl/arch.conf /boot/efi/loader/entries

Get the UUID of the LVM partition

ls -l /dev/disk/by-uuid/ | grep sdX2

Configure the boot entry file (note: this includes the discard option to allow SSD TRIM on an encrypted volume)

/boot/efi/loader/entries/arch.conf

title   Arch Linux
linux   /EFI/arch/vmlinuz-linux
initrd  /EFI/arch/intel-ucode.img
initrd  /EFI/arch/initramfs-linux.img
options root=/dev/mapper/lv-root rootfstype=ext4 rd.luks.name=*uuid*=cryptvolm rd.luks.options=discard

User account configuration

Set the root password

passwd

Add a user to the wheel group with a default shell and password

# add a user and create a new home directory
useradd -m -g wheel -s /bin/zsh username
# OR add a user to an existing home directory
useradd -M -g wheel -s /bin/zsh -d /home/username username

# set the default password for the user
passwd username

Allow users in the wheel group to execute commands using sudo

/etc/sudoers
...
## Uncomment to allow members of group wheel to execute any command
%wheel ALL=(ALL:ALL) ALL
...

Reboot

The installation is finished! Exit chroot, unmount devices, and reboot the machine.

exit
umount -R /mnt
reboot
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment