mkarchiso: copy all GRUB files to the ISO

Do not limit file copying to only grub.cfg and instead copy all GRUB configuration files and assets to both the ISO9660 and FAT image.
This will allow for including custom images, fonts, etc.

To easily match all non-configuration files (i.e. files without the .cfg extension), bash's extended glob feature will be enabled.
Actions common to multiple _make_bootmode_uefi-*.grub are split off into dedicated functions:

* _make_common_bootmode_grub_copy_to_efibootimg,
* _make_common_bootmode_grub_copy_to_isofs,
* _make_common_bootmode_grub_cfg.

Use the same du command in all efiboot_imgsize variable assignments.

Fixes #185.
This commit is contained in:
nl6720 2022-08-08 13:54:43 +03:00
parent 6ac2230953
commit b13e5e3379
No known key found for this signature in database
GPG Key ID: 5CE88535E188D369
2 changed files with 68 additions and 52 deletions

View File

@ -9,6 +9,7 @@ Added
----- -----
- Add ``efibootimg`` to ``mkarchiso`` to abstract the FAT image path. - Add ``efibootimg`` to ``mkarchiso`` to abstract the FAT image path.
- Copy all files from the ``grub`` directory to ISO9660 and the FAT image, not just only ``grub.cfg``.
Changed Changed
------- -------

View File

@ -3,6 +3,7 @@
# SPDX-License-Identifier: GPL-3.0-or-later # SPDX-License-Identifier: GPL-3.0-or-later
set -e -u set -e -u
shopt -s extglob
# Control the environment # Control the environment
umask 0022 umask 0022
@ -529,18 +530,44 @@ _make_efibootimg() {
mmd -i "${efibootimg}" ::/EFI ::/EFI/BOOT mmd -i "${efibootimg}" ::/EFI ::/EFI/BOOT
} }
# Copy the grub.cfg file in efiboot.img which is used by both IA32 UEFI and x64 UEFI. # Copy GRUB files to efiboot.img which is used by both IA32 UEFI and x64 UEFI.
_make_efibootimg_grubcfg() { _make_common_bootmode_grub_copy_to_efibootimg() {
mcopy -i "${efibootimg}" \ local files_to_copy=()
"${work_dir}/grub.cfg" ::/EFI/BOOT/grub.cfg
files_to_copy+=("${work_dir}/grub/"*)
if compgen -G "${profile}/grub/!(*.cfg)" &> /dev/null; then
files_to_copy+=("${profile}/grub/"!(*.cfg))
fi
mcopy -i "${efibootimg}" "${files_to_copy[@]}" ::/EFI/BOOT/
} }
_make_bootmode_uefi-ia32.grub.esp() { # Copy GRUB files to efiboot.img which is used by both IA32 UEFI and x64 UEFI.
_make_common_bootmode_grub_copy_to_isofs() {
local files_to_copy=()
files_to_copy+=("${work_dir}/grub/"*)
if compgen -G "${profile}/grub/!(*.cfg)" &> /dev/null; then
files_to_copy+=("${profile}/grub/"!(*.cfg))
fi
install -m 0644 -- "${files_to_copy[@]}" "${isofs_dir}/EFI/BOOT/"
}
# Prepare GRUB configuration files
_make_common_bootmode_grub_cfg(){
local _cfg
install -d -- "${work_dir}/grub"
# Fill GRUB configuration files # Fill GRUB configuration files
for _cfg in "${profile}/grub/"*'.cfg'; do
sed "s|%ARCHISO_LABEL%|${iso_label}|g; sed "s|%ARCHISO_LABEL%|${iso_label}|g;
s|%INSTALL_DIR%|${install_dir}|g; s|%INSTALL_DIR%|${install_dir}|g;
s|%ARCH%|${arch}|g" \ s|%ARCH%|${arch}|g" \
"${profile}/grub/grub.cfg" > "${work_dir}/grub.cfg" "${_cfg}" > "${work_dir}/grub/${_cfg##*/}"
done
# Add all GRUB files to the list of files used to calculate the required FAT image size.
efiboot_files+=("${work_dir}/grub/"
"${profile}/grub/"!(*.cfg))
IFS='' read -r -d '' grubembedcfg <<'EOF' || true IFS='' read -r -d '' grubembedcfg <<'EOF' || true
if ! [ -d "$cmdpath" ]; then if ! [ -d "$cmdpath" ]; then
@ -553,6 +580,11 @@ fi
configfile "${cmdpath}/grub.cfg" configfile "${cmdpath}/grub.cfg"
EOF EOF
printf '%s\n' "$grubembedcfg" > "${work_dir}/grub-embed.cfg" printf '%s\n' "$grubembedcfg" > "${work_dir}/grub-embed.cfg"
}
_make_bootmode_uefi-ia32.grub.esp() {
# Prepare configuration files
_run_once _make_common_bootmode_grub_cfg
# Create EFI binary # Create EFI binary
grub-mkstandalone -O i386-efi \ grub-mkstandalone -O i386-efi \
@ -571,22 +603,19 @@ EOF
elif [[ " ${bootmodes[*]} " =~ uefi-x64.grub.esp ]]; then elif [[ " ${bootmodes[*]} " =~ uefi-x64.grub.esp ]]; then
_run_once _make_bootmode_uefi-x64.grub.esp _run_once _make_bootmode_uefi-x64.grub.esp
else else
efiboot_imgsize="$(du -bc "${efiboot_files[@]}" \ efiboot_imgsize="$(du -bcs -- "${efiboot_files[@]}" 2>/dev/null | awk 'END { print $1 }')"
2>/dev/null | awk 'END { print $1 }')"
# Create a FAT image for the EFI system partition # Create a FAT image for the EFI system partition
_make_efibootimg "$efiboot_imgsize" _make_efibootimg "$efiboot_imgsize"
fi fi
# Copy GRUB EFI binary to the default/fallback boot path # Copy GRUB EFI binary to the default/fallback boot path
mcopy -i "${efibootimg}" \ mcopy -i "${efibootimg}" "${work_dir}/BOOTIA32.EFI" ::/EFI/BOOT/BOOTIA32.EFI
"${work_dir}/BOOTIA32.EFI" ::/EFI/BOOT/BOOTIA32.EFI
# Copy GRUB configuration files # Copy GRUB files
_run_once _make_efibootimg_grubcfg _run_once _make_common_bootmode_grub_copy_to_efibootimg
if [[ -e "${pacstrap_dir}/usr/share/edk2-shell/ia32/Shell_Full.efi" ]]; then if [[ -e "${pacstrap_dir}/usr/share/edk2-shell/ia32/Shell_Full.efi" ]]; then
mcopy -i "${efibootimg}" \ mcopy -i "${efibootimg}" "${pacstrap_dir}/usr/share/edk2-shell/ia32/Shell_Full.efi" ::/shellia32.efi
"${pacstrap_dir}/usr/share/edk2-shell/ia32/Shell_Full.efi" ::/shellia32.efi
fi fi
_msg_info "Done! GRUB set up for UEFI booting successfully." _msg_info "Done! GRUB set up for UEFI booting successfully."
@ -598,6 +627,9 @@ _make_bootmode_uefi-ia32.grub.eltorito() {
# uefi-ia32.grub.eltorito has the same requirements as uefi-ia32.grub.esp # uefi-ia32.grub.eltorito has the same requirements as uefi-ia32.grub.esp
_run_once _make_bootmode_uefi-ia32.grub.esp _run_once _make_bootmode_uefi-ia32.grub.esp
# Prepare configuration files
_run_once _make_common_bootmode_grub_cfg
# Additionally set up systemd-boot in ISO 9660. This allows creating a medium for the live environment by using # Additionally set up systemd-boot in ISO 9660. This allows creating a medium for the live environment by using
# manual partitioning and simply copying the ISO 9660 file system contents. # manual partitioning and simply copying the ISO 9660 file system contents.
# This is not related to El Torito booting and no firmware uses these files. # This is not related to El Torito booting and no firmware uses these files.
@ -605,39 +637,22 @@ _make_bootmode_uefi-ia32.grub.eltorito() {
install -d -m 0755 -- "${isofs_dir}/EFI/BOOT" install -d -m 0755 -- "${isofs_dir}/EFI/BOOT"
# Copy GRUB EFI binary to the default/fallback boot path # Copy GRUB EFI binary to the default/fallback boot path
install -m 0644 -- "${work_dir}/BOOTIA32.EFI" \ install -m 0644 -- "${work_dir}/BOOTIA32.EFI" "${isofs_dir}/EFI/BOOT/BOOTIA32.EFI"
"${isofs_dir}/EFI/BOOT/BOOTIA32.EFI"
# Copy GRUB configuration files # Copy GRUB configuration files
install -m 0644 -- "${work_dir}/grub.cfg" "${isofs_dir}/EFI/BOOT/grub.cfg" _run_once _make_common_bootmode_grub_copy_to_isofs
# edk2-shell based UEFI shell # edk2-shell based UEFI shell
if [[ -e "${pacstrap_dir}/usr/share/edk2-shell/ia32/Shell_Full.efi" ]]; then if [[ -e "${pacstrap_dir}/usr/share/edk2-shell/ia32/Shell_Full.efi" ]]; then
install -m 0644 -- "${pacstrap_dir}/usr/share/edk2-shell/ia32/Shell_Full.efi" \ install -m 0644 -- "${pacstrap_dir}/usr/share/edk2-shell/ia32/Shell_Full.efi" "${isofs_dir}/shellia32.efi"
"${isofs_dir}/shellia32.efi"
fi fi
_msg_info "Done!" _msg_info "Done!"
} }
_make_bootmode_uefi-x64.grub.esp() { _make_bootmode_uefi-x64.grub.esp() {
# Fill Grub configuration files # Prepare configuration files
sed "s|%ARCHISO_LABEL%|${iso_label}|g; _run_once _make_common_bootmode_grub_cfg
s|%INSTALL_DIR%|${install_dir}|g;
s|%ARCH%|${arch}|g" \
"${profile}/grub/grub.cfg" > "${work_dir}/grub.cfg"
IFS='' read -r -d '' grubembedcfg <<'EOF' || true
if ! [ -d "$cmdpath" ]; then
# On some firmware, GRUB has a wrong cmdpath when booted from an optical disc.
# https://gitlab.archlinux.org/archlinux/archiso/-/issues/183
if regexp --set=1:isodevice '^(\([^)]+\))\/?[Ee][Ff][Ii]\/[Bb][Oo][Oo][Tt]\/?$' "$cmdpath"; then
cmdpath="${isodevice}/EFI/BOOT"
fi
fi
configfile "${cmdpath}/grub.cfg"
EOF
printf '%s\n' "$grubembedcfg" > "${work_dir}/grub-embed.cfg"
# Create EFI binary # Create EFI binary
grub-mkstandalone -O x86_64-efi \ grub-mkstandalone -O x86_64-efi \
@ -650,21 +665,19 @@ EOF
efiboot_files+=("${work_dir}/BOOTx64.EFI" efiboot_files+=("${work_dir}/BOOTx64.EFI"
"${pacstrap_dir}/usr/share/edk2-shell/x64/Shell_Full.efi") "${pacstrap_dir}/usr/share/edk2-shell/x64/Shell_Full.efi")
efiboot_imgsize="$(du -bc "${efiboot_files[@]}" \ efiboot_imgsize="$(du -bcs -- "${efiboot_files[@]}" 2>/dev/null | awk 'END { print $1 }')"
2>/dev/null | awk 'END { print $1 }')"
# Create a FAT image for the EFI system partition # Create a FAT image for the EFI system partition
_make_efibootimg "$efiboot_imgsize" _make_efibootimg "$efiboot_imgsize"
# Copy grub EFI binary to the default/fallback boot path # Copy GRUB EFI binary to the default/fallback boot path
mcopy -i "${efibootimg}" \ mcopy -i "${efibootimg}" "${work_dir}/BOOTx64.EFI" ::/EFI/BOOT/BOOTx64.EFI
"${work_dir}/BOOTx64.EFI" ::/EFI/BOOT/BOOTx64.EFI
_run_once _make_efibootimg_grubcfg # Copy GRUB files
_run_once _make_common_bootmode_grub_copy_to_efibootimg
if [[ -e "${pacstrap_dir}/usr/share/edk2-shell/x64/Shell_Full.efi" ]]; then if [[ -e "${pacstrap_dir}/usr/share/edk2-shell/x64/Shell_Full.efi" ]]; then
mcopy -i "${efibootimg}" \ mcopy -i "${efibootimg}" "${pacstrap_dir}/usr/share/edk2-shell/x64/Shell_Full.efi" ::/shellx64.efi
"${pacstrap_dir}/usr/share/edk2-shell/x64/Shell_Full.efi" ::/shellx64.efi
fi fi
_msg_info "Done! GRUB set up for UEFI booting successfully." _msg_info "Done! GRUB set up for UEFI booting successfully."
@ -676,6 +689,9 @@ _make_bootmode_uefi-x64.grub.eltorito() {
# uefi-x64.grub.eltorito has the same requirements as uefi-x64.grub.esp # uefi-x64.grub.eltorito has the same requirements as uefi-x64.grub.esp
_run_once _make_bootmode_uefi-x64.grub.esp _run_once _make_bootmode_uefi-x64.grub.esp
# Prepare configuration files
_run_once _make_common_bootmode_grub_cfg
# Additionally set up systemd-boot in ISO 9660. This allows creating a medium for the live environment by using # Additionally set up systemd-boot in ISO 9660. This allows creating a medium for the live environment by using
# manual partitioning and simply copying the ISO 9660 file system contents. # manual partitioning and simply copying the ISO 9660 file system contents.
# This is not related to El Torito booting and no firmware uses these files. # This is not related to El Torito booting and no firmware uses these files.
@ -683,11 +699,10 @@ _make_bootmode_uefi-x64.grub.eltorito() {
install -d -m 0755 -- "${isofs_dir}/EFI/BOOT" install -d -m 0755 -- "${isofs_dir}/EFI/BOOT"
# Copy GRUB EFI binary to the default/fallback boot path # Copy GRUB EFI binary to the default/fallback boot path
install -m 0644 -- "${work_dir}/BOOTx64.EFI" \ install -m 0644 -- "${work_dir}/BOOTx64.EFI" "${isofs_dir}/EFI/BOOT/BOOTx64.EFI"
"${isofs_dir}/EFI/BOOT/BOOTx64.EFI"
# Copy GRUB configuration files # Copy GRUB files
install -m 0644 -- "${work_dir}/grub.cfg" "${isofs_dir}/EFI/BOOT" _run_once _make_common_bootmode_grub_copy_to_isofs
# edk2-shell based UEFI shell # edk2-shell based UEFI shell
if [[ -e "${pacstrap_dir}/usr/share/edk2-shell/x64/Shell_Full.efi" ]]; then if [[ -e "${pacstrap_dir}/usr/share/edk2-shell/x64/Shell_Full.efi" ]]; then
@ -715,7 +730,7 @@ _make_bootmode_uefi-x64.systemd-boot.esp() {
"${pacstrap_dir}/boot/vmlinuz-"* "${pacstrap_dir}/boot/vmlinuz-"*
"${pacstrap_dir}/boot/initramfs-"*".img" "${pacstrap_dir}/boot/initramfs-"*".img"
"${_available_ucodes[@]}") "${_available_ucodes[@]}")
efiboot_imgsize="$(du -bc "${efiboot_files[@]}" \ efiboot_imgsize="$(du -bcs -- "${efiboot_files[@]}" \
2>/dev/null | awk 'END { print $1 }')" 2>/dev/null | awk 'END { print $1 }')"
# Create a FAT image for the EFI system partition # Create a FAT image for the EFI system partition
_make_efibootimg "$efiboot_imgsize" _make_efibootimg "$efiboot_imgsize"