From 7a6f6747149fecf7660b6fd81d8e72caf0b10892 Mon Sep 17 00:00:00 2001 From: Rasmus Rosengren Date: Thu, 19 Aug 2021 14:46:57 +0200 Subject: [PATCH] Add efi_gtp_btrfs disksetup strategy --- README.md | 4 +-- ansible/configure.yml | 2 +- ansible/group_vars/all/00-defaults.yml | 6 ++++ ansible/install.yml | 2 +- ansible/inventory/hosts.yml | 9 ++--- .../library/modules/mkinitcpio/mkinitcpio.py | 9 ++--- .../efi_gpt_btrfs/bootloader/files/grub | 10 ++++++ .../efi_gpt_btrfs/bootloader/tasks/main.yml | 23 +++++++++++++ .../partitioning/defaults/main.yml | 32 ++++++++++++++++++ .../partitioning/tasks/format-disk.yml | 33 +++++++++++++++++++ .../partitioning/tasks/format-parts.yml | 31 +++++++++++++++++ .../efi_gpt_btrfs/partitioning/tasks/main.yml | 17 ++++++++++ .../partitioning/tasks/mount.yml | 22 +++++++++++++ .../tasks/mount_btrfs-subvolume.yml | 17 ++++++++++ .../postpartitioning/tasks/main.yml | 30 +++++++++++++++++ 15 files changed, 232 insertions(+), 15 deletions(-) create mode 100644 ansible/group_vars/all/00-defaults.yml create mode 100644 ansible/roles/disksetup/efi_gpt_btrfs/bootloader/files/grub create mode 100644 ansible/roles/disksetup/efi_gpt_btrfs/bootloader/tasks/main.yml create mode 100644 ansible/roles/disksetup/efi_gpt_btrfs/partitioning/defaults/main.yml create mode 100644 ansible/roles/disksetup/efi_gpt_btrfs/partitioning/tasks/format-disk.yml create mode 100644 ansible/roles/disksetup/efi_gpt_btrfs/partitioning/tasks/format-parts.yml create mode 100644 ansible/roles/disksetup/efi_gpt_btrfs/partitioning/tasks/main.yml create mode 100644 ansible/roles/disksetup/efi_gpt_btrfs/partitioning/tasks/mount.yml create mode 100644 ansible/roles/disksetup/efi_gpt_btrfs/partitioning/tasks/mount_btrfs-subvolume.yml create mode 100644 ansible/roles/disksetup/efi_gpt_btrfs/postpartitioning/tasks/main.yml diff --git a/README.md b/README.md index 4f7191c..1119f9b 100644 --- a/README.md +++ b/README.md @@ -4,7 +4,7 @@ Boot the live iso and set a root password, something simple is fine as it's changed to key based auth anyway. Find the ip address (e.g. by `ip a`) and -add to `inventory/hosts.yml` under the `arch_live` group. +add to `inventory/hosts.yml` under the `all` group. Enter the `ansible` directory. Before running any playbook, generate a new SSH key-pair: @@ -20,4 +20,4 @@ $ ansible-playbook install.yml -k ``` When the `install` playbook finishes, wait for the restart. Then find the new -ip address and put in the inventory file under the `arch` group +ip address and put in the inventory file under the `all` group diff --git a/ansible/configure.yml b/ansible/configure.yml index ab21850..6aee4ab 100644 --- a/ansible/configure.yml +++ b/ansible/configure.yml @@ -1,5 +1,5 @@ --- - name: Configure system. - hosts: arch + hosts: all roles: diff --git a/ansible/group_vars/all/00-defaults.yml b/ansible/group_vars/all/00-defaults.yml new file mode 100644 index 0000000..0cd582f --- /dev/null +++ b/ansible/group_vars/all/00-defaults.yml @@ -0,0 +1,6 @@ +disksetup_strategy: efi_gpt_btrfs +# partitioning_priv_device_node: /dev/sda + +# grub_theme_name: xenlism + +# configure_root_password: password diff --git a/ansible/install.yml b/ansible/install.yml index e24ae4a..4ef99ca 100644 --- a/ansible/install.yml +++ b/ansible/install.yml @@ -1,6 +1,6 @@ --- - name: Install system. - hosts: arch_live + hosts: all roles: - passwordless_connection diff --git a/ansible/inventory/hosts.yml b/ansible/inventory/hosts.yml index 966ef18..02019db 100644 --- a/ansible/inventory/hosts.yml +++ b/ansible/inventory/hosts.yml @@ -1,10 +1,5 @@ --- -arch_live: +all: hosts: - 192.168.2.230: + 192.168.2.227: ansible_user: root - -arch: - hosts: - 192.168.2.235: - ansible_user: rsrp diff --git a/ansible/library/modules/mkinitcpio/mkinitcpio.py b/ansible/library/modules/mkinitcpio/mkinitcpio.py index be42719..d17ad63 100644 --- a/ansible/library/modules/mkinitcpio/mkinitcpio.py +++ b/ansible/library/modules/mkinitcpio/mkinitcpio.py @@ -92,7 +92,7 @@ def run_module(): if updated_line is not None: lines[index] = updated_line - if binaries is not None: + if files is not None: updated_line, updated = update_mkinitcpio_line( "FILES", state, files, line) if updated: @@ -100,7 +100,7 @@ def run_module(): if updated_line is not None: lines[index] = updated_line - if binaries is not None: + if hooks is not None: updated_line, updated = update_mkinitcpio_line( "HOOKS", state, hooks, line) if updated: @@ -108,8 +108,9 @@ def run_module(): if updated_line is not None: lines[index] = updated_line - file = open(path, "w") - file.write("".join(lines)) + if result['changed']: + file = open(path, "w") + file.write("".join(lines)) # manipulate or modify the state as needed (this is going to be the # part where your module will do what it needs to do) diff --git a/ansible/roles/disksetup/efi_gpt_btrfs/bootloader/files/grub b/ansible/roles/disksetup/efi_gpt_btrfs/bootloader/files/grub new file mode 100644 index 0000000..c5edfa6 --- /dev/null +++ b/ansible/roles/disksetup/efi_gpt_btrfs/bootloader/files/grub @@ -0,0 +1,10 @@ +GRUB_TIMEOUT=5 +GRUB_DISTRIBUTOR="Arch" +GRUB_CMDLINE_LINUX_DEFAULT="" +GRUB_CMDLINE_LINUX="" +GRUB_PRELOAD_MODULES="btrfs part_gpt" +GRUB_TIMEOUT_STYLE=menu +GRUB_TERMINAL_INPUT=console +GRUB_GFXMODE=auto +GRUB_GFXPAYLOAD_LINUX=keep +GRUB_DISABLE_RECOVERY=true \ No newline at end of file diff --git a/ansible/roles/disksetup/efi_gpt_btrfs/bootloader/tasks/main.yml b/ansible/roles/disksetup/efi_gpt_btrfs/bootloader/tasks/main.yml new file mode 100644 index 0000000..cc2ced8 --- /dev/null +++ b/ansible/roles/disksetup/efi_gpt_btrfs/bootloader/tasks/main.yml @@ -0,0 +1,23 @@ +--- +- name: Install required packages. + command: arch-chroot {{ partitioning_root_mount_point }} pacman -Sy grub efibootmgr os-prober --noconfirm + changed_when: true + +- name: Copy grub default config. + template: + src: files/grub + dest: "{{ partitioning_root_mount_point }}/etc/default/grub" + owner: root + group: root + mode: 0644 + +- name: Install grub. + command: + cmd: arch-chroot {{ partitioning_root_mount_point }} grub-install --efi-directory=/boot/efi --bootloader-id=grub + creates: "{{ partitioning_root_mount_point }}/boot/efi/EFI/grub" + +- name: Install theme. + include_role: + name: grub-theme + vars: + chroot: "{{ partitioning_root_mount_point }}" diff --git a/ansible/roles/disksetup/efi_gpt_btrfs/partitioning/defaults/main.yml b/ansible/roles/disksetup/efi_gpt_btrfs/partitioning/defaults/main.yml new file mode 100644 index 0000000..5b56c93 --- /dev/null +++ b/ansible/roles/disksetup/efi_gpt_btrfs/partitioning/defaults/main.yml @@ -0,0 +1,32 @@ +--- +##### Public variables used by the rest of the playbook ##### +partitioning_root_mount_point: "/mnt" + +##### Private variables used only by the partitioning roles ##### + +# Two partitions will be created on this device node +# * xxx1 will be used by /boot/efi +# * xxx2 will be the root partition +partitioning_priv_device_node: "/dev/sda" + +# The size of the ESP partition to be created +partitioning_priv_esp_size: "{{ 512 * 1024 * 1024 }}" + +# btrfs subvolumes are laid out in a flat fashion: +# +# toplevel (default subvolume, not mounted) +# +-- @ (to be mounted at /) +# +-- @home (to be mmounted at /home) +# +-- ... +# +partitioning_priv_btrfs_subvolumes: "{{ partitioning_priv_core_btrfs_subvolumes + partitioning_priv_extra_btrfs_subvolumes }}" + +# These subvolumes should always be present. DO NOT OVERRIDE. +partitioning_priv_core_btrfs_subvolumes: + - name: "@" + mountpoint: / + +# Other subvolumes can be added here, beginning with an @. +partitioning_priv_extra_btrfs_subvolumes: + - name: "@home" + mountpoint: /home diff --git a/ansible/roles/disksetup/efi_gpt_btrfs/partitioning/tasks/format-disk.yml b/ansible/roles/disksetup/efi_gpt_btrfs/partitioning/tasks/format-disk.yml new file mode 100644 index 0000000..834dc9f --- /dev/null +++ b/ansible/roles/disksetup/efi_gpt_btrfs/partitioning/tasks/format-disk.yml @@ -0,0 +1,33 @@ +--- +- name: Create EFI system partition + parted: + device: "{{ partitioning_priv_device_node }}" + state: present + label: gpt + number: 1 + name: ESP + part_start: "{{ 1024 * 1024 }}B" + part_end: "{{ partitioning_priv_esp_size | int + 1024 * 1024 - 1 }}B" + flags: + - esp + +- name: Create root partition + parted: + device: "{{ partitioning_priv_device_node }}" + state: present + label: gpt + number: 2 + name: root + part_start: "{{ partitioning_priv_esp_size | int + 1024 * 1024 }}B" + +- name: Enumerate created partitions. + shell: | + set -e -o pipefail + lsblk -n -o PATH {{ partitioning_priv_device_node | quote }} | tail -n +2 + register: _partitions + changed_when: false + +- name: Assign partitions to variables. + set_fact: + partitioning_priv_esp_device_node: "{{ _partitions.stdout_lines[0] }}" + partitioning_priv_root_device_node: "{{ _partitions.stdout_lines[1] }}" diff --git a/ansible/roles/disksetup/efi_gpt_btrfs/partitioning/tasks/format-parts.yml b/ansible/roles/disksetup/efi_gpt_btrfs/partitioning/tasks/format-parts.yml new file mode 100644 index 0000000..0d37305 --- /dev/null +++ b/ansible/roles/disksetup/efi_gpt_btrfs/partitioning/tasks/format-parts.yml @@ -0,0 +1,31 @@ +--- +- name: Format the boot partition with vfat. + filesystem: + device: "{{ partitioning_priv_esp_device_node }}" + state: present + type: vfat + +- name: Format the root partition with btrfs. + filesystem: + device: "{{ partitioning_priv_root_device_node }}" + state: present + type: btrfs + +- name: Mount the default subvolume. + mount: + state: mounted + src: "{{ partitioning_priv_root_device_node }}" + path: "{{ partitioning_root_mount_point }}" + fstype: btrfs + opts: defaults,noatime,compress=zstd + +- name: Create subvolumes. + command: + cmd: btrfs subvolume create {{ (partitioning_root_mount_point + "/" + item.name) }} + creates: '{{ (partitioning_root_mount_point + "/" + item.name) }}' + with_items: "{{ partitioning_priv_btrfs_subvolumes }}" + +- name: Unmount the default subvolume. + mount: + state: unmounted + path: "{{ partitioning_root_mount_point }}" diff --git a/ansible/roles/disksetup/efi_gpt_btrfs/partitioning/tasks/main.yml b/ansible/roles/disksetup/efi_gpt_btrfs/partitioning/tasks/main.yml new file mode 100644 index 0000000..46954e9 --- /dev/null +++ b/ansible/roles/disksetup/efi_gpt_btrfs/partitioning/tasks/main.yml @@ -0,0 +1,17 @@ +--- +- name: Fail if not using EFI. + fail: + msg: Must boot using EFI for this disksetup strategy. + when: not efi_mode + +- name: Make sure root mount point is unmounted. + command: umount -R {{ partitioning_root_mount_point }} + changed_when: true + register: result + failed_when: result.rc != 0 and "not mounted" not in result.stderr + +- include_tasks: "{{ item }}" + with_items: + - format-disk.yml + - format-parts.yml + - mount.yml diff --git a/ansible/roles/disksetup/efi_gpt_btrfs/partitioning/tasks/mount.yml b/ansible/roles/disksetup/efi_gpt_btrfs/partitioning/tasks/mount.yml new file mode 100644 index 0000000..f13ea0b --- /dev/null +++ b/ansible/roles/disksetup/efi_gpt_btrfs/partitioning/tasks/mount.yml @@ -0,0 +1,22 @@ +--- +- name: Mount btrfs subvolumes. + include_tasks: mount_btrfs-subvolume.yml + with_items: "{{ partitioning_priv_btrfs_subvolumes }}" + loop_control: + loop_var: subvolume + +- name: Make EFI mount point. + file: + path: "{{ partitioning_root_mount_point }}/boot/efi" + state: directory + recurse: true + owner: root + group: root + mode: 0700 + +- name: Mount EFI boot partition. + mount: + state: mounted + src: "{{ partitioning_priv_esp_device_node }}" + path: "{{ partitioning_root_mount_point }}/boot/efi" + fstype: vfat diff --git a/ansible/roles/disksetup/efi_gpt_btrfs/partitioning/tasks/mount_btrfs-subvolume.yml b/ansible/roles/disksetup/efi_gpt_btrfs/partitioning/tasks/mount_btrfs-subvolume.yml new file mode 100644 index 0000000..9531b30 --- /dev/null +++ b/ansible/roles/disksetup/efi_gpt_btrfs/partitioning/tasks/mount_btrfs-subvolume.yml @@ -0,0 +1,17 @@ +--- +- name: Make btrfs subvolume mount point. + file: + state: directory + path: "{{ (partitioning_root_mount_point + subvolume.mountpoint) | quote }}" + owner: root + group: root + mode: 0755 + +- name: Mount btrfs subvolume. + command: > + mount + -t btrfs + -o defaults,noatime,compress=zstd,subvol={{ subvolume.name }} + {{ partitioning_priv_root_device_node }} + {{ (partitioning_root_mount_point + subvolume.mountpoint) | quote }} + changed_when: true diff --git a/ansible/roles/disksetup/efi_gpt_btrfs/postpartitioning/tasks/main.yml b/ansible/roles/disksetup/efi_gpt_btrfs/postpartitioning/tasks/main.yml new file mode 100644 index 0000000..39f6b34 --- /dev/null +++ b/ansible/roles/disksetup/efi_gpt_btrfs/postpartitioning/tasks/main.yml @@ -0,0 +1,30 @@ +--- +- name: Generate fstab. + include_role: + name: genfstab + vars: + chroot: "{{ partitioning_root_mount_point }}" + +- name: Check if btrfs-progs is installed. + command: arch-chroot {{ partitioning_root_mount_point }} + pacman -Qk btrfs-progs + register: _btrfs_progs_installed + failed_when: false + changed_when: false + +- name: Install btrfs-progs. + command: arch-chroot {{ partitioning_root_mount_point }} + pacman -Sy btrfs-progs --noconfirm + when: _btrfs_progs_installed.rc != 0 + +- name: Configure mkinitcpio. + mkinitcpio: + state: present + path: "{{ partitioning_root_mount_point }}/etc/mkinitcpio.conf" + binaries: /usr/bin/btrfs + hooks: + - btrfs + +- name: Run mkinitcpio. + command: arch-chroot {{ partitioning_root_mount_point }} mkinitcpio -P + changed_when: true