From a5ba84ec9e173012638eec9559cefeac63a7dfca Mon Sep 17 00:00:00 2001 From: Pavel Valena Date: Tue, 25 Jul 2023 13:34:23 +0200 Subject: [PATCH] dracut-057-38.git20230725 Resolves: #1933787,#2180787,#2181541 --- 0022.patch | 145 +++++++++++++++ 0023.patch | 97 ++++++++++ 0024.patch | 46 +++++ 0025.patch | 59 ++++++ 0026.patch | 59 ++++++ 0027.patch | 65 +++++++ 0028.patch | 26 +++ 0029.patch | 28 +++ 0030.patch | 26 +++ 0031.patch | 48 +++++ 0032.patch | 38 ++++ 0033.patch | 26 +++ 0034.patch | 50 +++++ 0035.patch | 28 +++ 0036.patch | 45 +++++ 0037.patch | 511 ++++++++++++++++++++++++++++++++++++++++++++++++++++ dracut.spec | 36 +++- 17 files changed, 1332 insertions(+), 1 deletion(-) create mode 100644 0022.patch create mode 100644 0023.patch create mode 100644 0024.patch create mode 100644 0025.patch create mode 100644 0026.patch create mode 100644 0027.patch create mode 100644 0028.patch create mode 100644 0029.patch create mode 100644 0030.patch create mode 100644 0031.patch create mode 100644 0032.patch create mode 100644 0033.patch create mode 100644 0034.patch create mode 100644 0035.patch create mode 100644 0036.patch create mode 100644 0037.patch diff --git a/0022.patch b/0022.patch new file mode 100644 index 0000000..90ad85d --- /dev/null +++ b/0022.patch @@ -0,0 +1,145 @@ +From cd2bfd13e80d5a20ca27e3f7e9dd5f4d33c30a6d Mon Sep 17 00:00:00 2001 +From: Valentin Lefebvre +Date: Mon, 13 Mar 2023 12:06:13 +0100 +Subject: [PATCH] fix(dracut.sh): use dynamically uefi's sections offset + +* Uefi section are creating by `objcopy` with hardcoded sections +offset. This commit allow to have the correct offset between +each part of the efi file, needed to create an UKI. Offsets +are simply calculated so no sections overlap, as recommended +in https://wiki.archlinux.org/title/Unified_kernel_image#Manually +Moreover, efi stub file's header is parsed to apply the correct +offsets according the section alignment factor. +* Remove EFI_SECTION_VMA_INITRD, no need anymore as initrd +section offset dynamically calculated + +Fixes dracutdevs#2275 + +Signed-off-by: Valentin Lefebvre + +(Cherry-picked commit: f32e95bcadbc5158843530407adc1e7b700561b1) + +Resolves: #2180787 +--- + dracut-functions.sh | 23 +++++++++++++++++++++++ + dracut.sh | 45 +++++++++++++++++++++++++++++++++++---------- + 2 files changed, 58 insertions(+), 10 deletions(-) + +diff --git a/dracut-functions.sh b/dracut-functions.sh +index ff6749a1..a95755b2 100755 +--- a/dracut-functions.sh ++++ b/dracut-functions.sh +@@ -995,3 +995,26 @@ get_dev_module() { + fi + echo "$dev_drivers" + } ++ ++# Check if file is in PE format ++pe_file_format() { ++ if [[ $# -eq 1 ]]; then ++ local magic ++ magic=$(objdump -p "$1" \ ++ | awk '{if ($1 == "Magic"){print strtonum("0x"$2)}}') ++ magic=$(printf "0x%x" "$magic") ++ # 0x10b (PE32), 0x20b (PE32+) ++ [[ $magic == 0x20b || $magic == 0x10b ]] && return 0 ++ fi ++ return 1 ++} ++ ++# Get the sectionAlignment data from the PE header ++pe_get_section_align() { ++ local align_hex ++ [[ $# -ne "1" ]] && return 1 ++ [[ $(pe_file_format "$1") -eq 1 ]] && return 1 ++ align_hex=$(objdump -p "$1" \ ++ | awk '{if ($1 == "SectionAlignment"){print $2}}') ++ echo "$((16#$align_hex))" ++} +diff --git a/dracut.sh b/dracut.sh +index d2f07ac6..0c963431 100755 +--- a/dracut.sh ++++ b/dracut.sh +@@ -1433,7 +1433,6 @@ if [[ ! $print_cmdline ]]; then + exit 1 + fi + unset EFI_MACHINE_TYPE_NAME +- EFI_SECTION_VMA_INITRD=0x3000000 + case $(uname -m) in + x86_64) + EFI_MACHINE_TYPE_NAME=x64 +@@ -1443,8 +1442,6 @@ if [[ ! $print_cmdline ]]; then + ;; + aarch64) + EFI_MACHINE_TYPE_NAME=aa64 +- # aarch64 kernels are uncompressed and thus larger, so we need a bigger gap between vma sections +- EFI_SECTION_VMA_INITRD=0x4000000 + ;; + *) + dfatal "Architecture '$(uname -m)' not supported to create a UEFI executable" +@@ -2596,29 +2593,57 @@ if [[ $uefi == yes ]]; then + done + fi + ++ offs=$(objdump -h "$uefi_stub" 2> /dev/null | awk 'NF==7 {size=strtonum("0x"$3);\ ++ offset=strtonum("0x"$4)} END {print size + offset}') ++ if [[ $offs -eq 0 ]]; then ++ dfatal "Failed to get the size of $uefi_stub to create UEFI image file" ++ exit 1 ++ fi ++ align=$(pe_get_section_align "$uefi_stub") ++ if [[ $? -eq 1 ]]; then ++ dfatal "Failed to get the sectionAlignment of the stub PE header to create the UEFI image file" ++ exit 1 ++ fi ++ offs=$((offs + "$align" - offs % "$align")) ++ [[ -s $dracutsysrootdir/usr/lib/os-release ]] && uefi_osrelease="$dracutsysrootdir/usr/lib/os-release" ++ [[ -s $dracutsysrootdir/etc/os-release ]] && uefi_osrelease="$dracutsysrootdir/etc/os-release" ++ [[ -s $uefi_osrelease ]] \ ++ && uefi_osrelease_offs=${offs} \ ++ && offs=$((offs + $(stat -Lc%s "$uefi_osrelease"))) \ ++ && offs=$((offs + "$align" - offs % "$align")) ++ + if [[ $kernel_cmdline ]] || [[ $hostonly_cmdline == yes && -d "$initdir/etc/cmdline.d" ]]; then + echo -ne "\x00" >> "$uefi_outdir/cmdline.txt" + dinfo "Using UEFI kernel cmdline:" + dinfo "$(tr -d '\000' < "$uefi_outdir/cmdline.txt")" + uefi_cmdline="${uefi_outdir}/cmdline.txt" ++ uefi_cmdline_offs=${offs} ++ offs=$((offs + $(stat -Lc%s "$uefi_cmdline"))) ++ offs=$((offs + "$align" - offs % "$align")) + else + unset uefi_cmdline + fi + +- [[ -s $dracutsysrootdir/usr/lib/os-release ]] && uefi_osrelease="$dracutsysrootdir/usr/lib/os-release" +- [[ -s $dracutsysrootdir/etc/os-release ]] && uefi_osrelease="$dracutsysrootdir/etc/os-release" + if [[ -s ${dracutsysrootdir}${uefi_splash_image} ]]; then + uefi_splash_image="${dracutsysrootdir}${uefi_splash_image}" ++ uefi_splash_offs=${offs} ++ offs=$((offs + $(stat -Lc%s "$uefi_splash_image"))) ++ offs=$((offs + "$align" - offs % "$align")) + else + unset uefi_splash_image + fi + ++ uefi_linux_offs="${offs}" ++ offs=$((offs + $(stat -Lc%s "$kernel_image"))) ++ offs=$((offs + "$align" - offs % "$align")) ++ uefi_initrd_offs="${offs}" ++ + if objcopy \ +- ${uefi_osrelease:+--add-section .osrel="$uefi_osrelease" --change-section-vma .osrel=0x20000} \ +- ${uefi_cmdline:+--add-section .cmdline="$uefi_cmdline" --change-section-vma .cmdline=0x30000} \ +- ${uefi_splash_image:+--add-section .splash="$uefi_splash_image" --change-section-vma .splash=0x40000} \ +- --add-section .linux="$kernel_image" --change-section-vma .linux=0x2000000 \ +- --add-section .initrd="${DRACUT_TMPDIR}/initramfs.img" --change-section-vma .initrd="${EFI_SECTION_VMA_INITRD}" \ ++ ${uefi_osrelease:+--add-section .osrel="$uefi_osrelease" --change-section-vma .osrel=$(printf 0x%x "$uefi_osrelease_offs")} \ ++ ${uefi_cmdline:+--add-section .cmdline="$uefi_cmdline" --change-section-vma .cmdline=$(printf 0x%x "$uefi_cmdline_offs")} \ ++ ${uefi_splash_image:+--add-section .splash="$uefi_splash_image" --change-section-vma .splash=$(printf 0x%x "$uefi_splash_offs")} \ ++ --add-section .linux="$kernel_image" --change-section-vma .linux="$(printf 0x%x "$uefi_linux_offs")" \ ++ --add-section .initrd="${DRACUT_TMPDIR}/initramfs.img" --change-section-vma .initrd="$(printf 0x%x "$uefi_initrd_offs")" \ + "$uefi_stub" "${uefi_outdir}/linux.efi"; then + if [[ -n ${uefi_secureboot_key} && -n ${uefi_secureboot_cert} ]]; then + if sbsign \ + diff --git a/0023.patch b/0023.patch new file mode 100644 index 0000000..83d3c36 --- /dev/null +++ b/0023.patch @@ -0,0 +1,97 @@ +From 11e1ffb0cf614fb6ec9b740cb6eb8c07c2a081ac Mon Sep 17 00:00:00 2001 +From: keentux +Date: Wed, 22 Mar 2023 10:40:39 +0000 +Subject: [PATCH] fix(dracut.sh): handle imagebase for uefi + +* UEFI creation didn't handle the ImageBase data for the PE file + generation. Create an UKI thanks a stub file with a non zero BaseImage + logs some warning ans generate a bad file offset management. The efi + becomes unloadable. +* This commit parse the PE file header, get the data and apply the + ImageBase on the objcopy command. + +Fixes dracutdevs#2284 + +Signed-off-by: Valentin Lefebvre + +(Cherry-picked commit: 6178a9d83ffad67fa371cef2ff3f5bbb337bc8b7) + +Related: #2180787 +--- + dracut-functions.sh | 26 ++++++++++++++++++++++---- + dracut.sh | 9 ++++++++- + 2 files changed, 30 insertions(+), 5 deletions(-) + +diff --git a/dracut-functions.sh b/dracut-functions.sh +index a95755b2..7f05da6e 100755 +--- a/dracut-functions.sh ++++ b/dracut-functions.sh +@@ -1009,12 +1009,30 @@ pe_file_format() { + return 1 + } + +-# Get the sectionAlignment data from the PE header ++# Get specific data from the PE header ++pe_get_header_data() { ++ local data_header ++ [[ $# -ne "2" ]] && return 1 ++ [[ $(pe_file_format "$1") -eq 1 ]] && return 1 ++ data_header=$(objdump -p "$1" \ ++ | awk -v data="$2" '{if ($1 == data){print $2}}') ++ echo "$data_header" ++} ++ ++# Get the SectionAlignment data from the PE header + pe_get_section_align() { + local align_hex + [[ $# -ne "1" ]] && return 1 +- [[ $(pe_file_format "$1") -eq 1 ]] && return 1 +- align_hex=$(objdump -p "$1" \ +- | awk '{if ($1 == "SectionAlignment"){print $2}}') ++ align_hex=$(pe_get_header_data "$1" "SectionAlignment") ++ [[ $? -eq 1 ]] && return 1 + echo "$((16#$align_hex))" + } ++ ++# Get the ImageBase data from the PE header ++pe_get_image_base() { ++ local base_image ++ [[ $# -ne "1" ]] && return 1 ++ base_image=$(pe_get_header_data "$1" "ImageBase") ++ [[ $? -eq 1 ]] && return 1 ++ echo "$((16#$base_image))" ++} +diff --git a/dracut.sh b/dracut.sh +index 0c963431..a6a27dcf 100755 +--- a/dracut.sh ++++ b/dracut.sh +@@ -2601,7 +2601,7 @@ if [[ $uefi == yes ]]; then + fi + align=$(pe_get_section_align "$uefi_stub") + if [[ $? -eq 1 ]]; then +- dfatal "Failed to get the sectionAlignment of the stub PE header to create the UEFI image file" ++ dfatal "Failed to get the SectionAlignment of the stub PE header to create the UEFI image file" + exit 1 + fi + offs=$((offs + "$align" - offs % "$align")) +@@ -2638,12 +2638,19 @@ if [[ $uefi == yes ]]; then + offs=$((offs + "$align" - offs % "$align")) + uefi_initrd_offs="${offs}" + ++ base_image=$(pe_get_image_base "$uefi_stub") ++ if [[ $? -eq 1 ]]; then ++ dfatal "Failed to get ImageBase data of $uefi_stub to create UEFI image file" ++ exit 1 ++ fi ++ + if objcopy \ + ${uefi_osrelease:+--add-section .osrel="$uefi_osrelease" --change-section-vma .osrel=$(printf 0x%x "$uefi_osrelease_offs")} \ + ${uefi_cmdline:+--add-section .cmdline="$uefi_cmdline" --change-section-vma .cmdline=$(printf 0x%x "$uefi_cmdline_offs")} \ + ${uefi_splash_image:+--add-section .splash="$uefi_splash_image" --change-section-vma .splash=$(printf 0x%x "$uefi_splash_offs")} \ + --add-section .linux="$kernel_image" --change-section-vma .linux="$(printf 0x%x "$uefi_linux_offs")" \ + --add-section .initrd="${DRACUT_TMPDIR}/initramfs.img" --change-section-vma .initrd="$(printf 0x%x "$uefi_initrd_offs")" \ ++ --image-base="$(printf 0x%x "$base_image")" \ + "$uefi_stub" "${uefi_outdir}/linux.efi"; then + if [[ -n ${uefi_secureboot_key} && -n ${uefi_secureboot_cert} ]]; then + if sbsign \ + diff --git a/0024.patch b/0024.patch new file mode 100644 index 0000000..4cf3c3b --- /dev/null +++ b/0024.patch @@ -0,0 +1,46 @@ +From 11cc7032853ea254a7d4cabed0b7bf3a605ccc6c Mon Sep 17 00:00:00 2001 +From: Sam James +Date: Thu, 20 Jul 2023 04:36:01 +0100 +Subject: [PATCH] fix(dracut.sh): use gawk for strtonum + +strtonum is a gawkism and is not available in all awks, e.g. mawk. Use gawk +to avoid failure. + +Fixes: f32e95bcadbc5158843530407adc1e7b700561b1 +Signed-off-by: Sam James + +(Cherry-picked commit: 33a66ed04bdc30eccb172a0cd6dcc36d9d74f825) + +Related: #2180787 +--- + dracut-functions.sh | 2 +- + dracut.sh | 2 +- + 2 files changed, 2 insertions(+), 2 deletions(-) + +diff --git a/dracut-functions.sh b/dracut-functions.sh +index 7f05da6e..3c475ca7 100755 +--- a/dracut-functions.sh ++++ b/dracut-functions.sh +@@ -1001,7 +1001,7 @@ pe_file_format() { + if [[ $# -eq 1 ]]; then + local magic + magic=$(objdump -p "$1" \ +- | awk '{if ($1 == "Magic"){print strtonum("0x"$2)}}') ++ | gawk '{if ($1 == "Magic"){print strtonum("0x"$2)}}') + magic=$(printf "0x%x" "$magic") + # 0x10b (PE32), 0x20b (PE32+) + [[ $magic == 0x20b || $magic == 0x10b ]] && return 0 +diff --git a/dracut.sh b/dracut.sh +index a6a27dcf..1ff51bb1 100755 +--- a/dracut.sh ++++ b/dracut.sh +@@ -2593,7 +2593,7 @@ if [[ $uefi == yes ]]; then + done + fi + +- offs=$(objdump -h "$uefi_stub" 2> /dev/null | awk 'NF==7 {size=strtonum("0x"$3);\ ++ offs=$(objdump -h "$uefi_stub" 2> /dev/null | gawk 'NF==7 {size=strtonum("0x"$3);\ + offset=strtonum("0x"$4)} END {print size + offset}') + if [[ $offs -eq 0 ]]; then + dfatal "Failed to get the size of $uefi_stub to create UEFI image file" + diff --git a/0025.patch b/0025.patch new file mode 100644 index 0000000..00731e3 --- /dev/null +++ b/0025.patch @@ -0,0 +1,59 @@ +From 68814ff425e71c411ba5111c37774cbab429bf9e Mon Sep 17 00:00:00 2001 +From: Pavel Valena +Date: Sun, 23 Jul 2023 19:44:17 +0200 +Subject: [PATCH] fix(rngd): install system service file + +as there's no reason to keep a copy; there shouldn't be any modifications. + +In case there are args stored in a separate file (Fedora and alike), +it needs to be supplied too, but without the option to change the user. + +(Cherry-picked commit: c47a44cb25c0892d9af6e66ee9d7cd2c3beca31f) + +Resolves: #2181541 +--- + modules.d/06rngd/module-setup.sh | 7 ++++++- + modules.d/06rngd/rngd.service | 8 -------- + modules.d/06rngd/sysconfig | 1 + + 3 files changed, 7 insertions(+), 9 deletions(-) + +diff --git a/modules.d/06rngd/module-setup.sh b/modules.d/06rngd/module-setup.sh +index d94a47af..66923a38 100644 +--- a/modules.d/06rngd/module-setup.sh ++++ b/modules.d/06rngd/module-setup.sh +@@ -32,7 +32,12 @@ depends() { + + install() { + inst rngd +- inst_simple "${moddir}/rngd.service" "${systemdsystemunitdir}/rngd.service" ++ inst_simple "${systemdsystemunitdir}/rngd.service" ++ ++ if [ -r /etc/sysconfig/rngd ]; then ++ inst_simple "${moddir}/sysconfig" "/etc/sysconfig/rngd" ++ fi ++ + # make sure dependant libs are installed too + inst_libdir_file opensc-pkcs11.so + +diff --git a/modules.d/06rngd/rngd.service b/modules.d/06rngd/rngd.service +deleted file mode 100644 +index dd5374d7..00000000 +--- a/modules.d/06rngd/rngd.service ++++ /dev/null +@@ -1,8 +0,0 @@ +-[Unit] +-Description=Hardware RNG Entropy Gatherer Daemon +-DefaultDependencies=no +-Before=systemd-udevd.service +-ConditionVirtualization=!container +- +-[Service] +-ExecStart=/usr/sbin/rngd -f +diff --git a/modules.d/06rngd/sysconfig b/modules.d/06rngd/sysconfig +new file mode 100644 +index 00000000..100e8deb +--- /dev/null ++++ b/modules.d/06rngd/sysconfig +@@ -0,0 +1 @@ ++RNGD_ARGS="--fill-watermark=0 -x pkcs11 -x nist -x qrypt" + diff --git a/0026.patch b/0026.patch new file mode 100644 index 0000000..8337819 --- /dev/null +++ b/0026.patch @@ -0,0 +1,59 @@ +From a63fbfe7eb109214fbcee726c9ba898ba3c954d3 Mon Sep 17 00:00:00 2001 +From: Antonio Alvarez Feijoo +Date: Wed, 14 Sep 2022 12:44:26 +0200 +Subject: [PATCH] fix(nvmf): nvme list-subsys prints the address using commas + as separator + +nvme-cli 1.x printed the address using spaces as separator, but nvme-cli 2.x +prints the address using commas as separator (exact output from sysfs). E.g., +output from `cat /sys/class/nvme/nvme0/address`: + +traddr=nn-0x201700a09890f5bf:pn-0x201900a09890f5bf,host_traddr=nn-0x200000109b579ef5:pn-0x100000109b579ef5 + +Also, I suppress rd.nvmf.discover= cmdline option if all fields are empty. + +Resolves: #1933787 +--- + modules.d/95nvmf/module-setup.sh | 21 ++++++++++++++++++--- + 1 file changed, 18 insertions(+), 3 deletions(-) + +diff --git a/modules.d/95nvmf/module-setup.sh b/modules.d/95nvmf/module-setup.sh +index be1c85f3..0825b51c 100755 +--- a/modules.d/95nvmf/module-setup.sh ++++ b/modules.d/95nvmf/module-setup.sh +@@ -61,6 +61,11 @@ cmdline() { + gen_nvmf_cmdline() { + local _dev=$1 + local trtype ++ local traddr ++ local host_traddr ++ local trsvcid ++ local _address ++ local -a _address_parts + + [[ -L "/sys/dev/block/$_dev" ]] || return 0 + cd -P "/sys/dev/block/$_dev" || return 0 +@@ -76,9 +81,19 @@ cmdline() { + done + + [ -z "$trtype" ] && return 0 +- nvme list-subsys "${PWD##*/}" | while read -r _ _ trtype traddr host_traddr _; do +- [ "$trtype" != "${trtype#NQN}" ] && continue +- echo -n " rd.nvmf.discover=$trtype,${traddr#traddr=},${host_traddr#host_traddr=}" ++ nvme list-subsys "${PWD##*/}" | while read -r _ _ trtype _address _; do ++ [[ -z $trtype || $trtype != "${trtype#NQN}" ]] && continue ++ unset traddr ++ unset host_traddr ++ unset trsvcid ++ mapfile -t -d ',' _address_parts < <(printf "%s" "$_address") ++ for i in "${_address_parts[@]}"; do ++ [[ $i =~ ^traddr= ]] && traddr="${i#traddr=}" ++ [[ $i =~ ^host_traddr= ]] && host_traddr="${i#host_traddr=}" ++ [[ $i =~ ^trsvcid= ]] && trsvcid="${i#trsvcid=}" ++ done ++ [[ -z $traddr && -z $host_traddr && -z $trsvcid ]] && continue ++ echo -n " rd.nvmf.discover=$trtype,$traddr,$host_traddr,$trsvcid" + done + } + + diff --git a/0027.patch b/0027.patch new file mode 100644 index 0000000..825b0c6 --- /dev/null +++ b/0027.patch @@ -0,0 +1,65 @@ +From 0322e328d94f70693e1e33fb96bd5d9d771fea3a Mon Sep 17 00:00:00 2001 +From: Martin Wilck +Date: Fri, 16 Sep 2022 23:46:42 +0200 +Subject: [PATCH] fix(nvmf): don't try to validate network connections in + cmdline hook + +The cmdline hook runs before any network interfaces have been brought +up. There's no point in trying to validate the connections at this +stage. + +Resolves: #1933787 +--- + modules.d/95nvmf/parse-nvmf-boot-connections.sh | 31 ------------------------- + 1 file changed, 31 deletions(-) + +diff --git a/modules.d/95nvmf/parse-nvmf-boot-connections.sh b/modules.d/95nvmf/parse-nvmf-boot-connections.sh +index 46c00636..39923503 100755 +--- a/modules.d/95nvmf/parse-nvmf-boot-connections.sh ++++ b/modules.d/95nvmf/parse-nvmf-boot-connections.sh +@@ -26,34 +26,6 @@ fi + + initqueue --onetime modprobe --all -b -q nvme nvme_tcp nvme_core nvme_fabrics + +-validate_ip_conn() { +- if ! getargbool 0 rd.neednet; then +- warn "$trtype transport requires rd.neednet=1" +- return 1 +- fi +- +- local_address=$(ip -o route get to "$traddr" | sed -n 's/.*src \([0-9a-f.:]*\).*/\1/p') +- +- # confirm we got a local IP address +- if ! is_ip "$local_address"; then +- warn "$traddr is an invalid address" +- return 1 +- fi +- +- ifname=$(ip -o route get from "$local_address" to "$traddr" | sed -n 's/.*dev \([^ ]*\).*/\1/p') +- +- if ! ip l show "$ifname" > /dev/null 2>&1; then +- warn "invalid network interface $ifname" +- return 1 +- fi +- +- # confirm there's a route to destination +- if ! ip route get "$traddr" > /dev/null 2>&1; then +- warn "no route to $traddr" +- return 1 +- fi +-} +- + parse_nvmf_discover() { + traddr="none" + trtype="none" +@@ -103,9 +75,6 @@ parse_nvmf_discover() { + warn "unsupported transport $trtype" + return 0 + fi +- if [ "$trtype" = "tcp" ]; then +- validate_ip_conn +- fi + if [ "$trtype" = "fc" ]; then + echo "--transport=$trtype --traddr=$traddr --host-traddr=$hosttraddr" >> /etc/nvme/discovery.conf + else + diff --git a/0028.patch b/0028.patch new file mode 100644 index 0000000..4f93442 --- /dev/null +++ b/0028.patch @@ -0,0 +1,26 @@ +From cd4d4282b5dd7d30af31c41faa807dcf8de01c29 Mon Sep 17 00:00:00 2001 +From: Martin Wilck +Date: Sat, 17 Sep 2022 00:01:07 +0200 +Subject: [PATCH] fix(nvmf): no need to load the nvme module + +The module "nvme" is not required for NVMeoF. + +Resolves: #1933787 +--- + modules.d/95nvmf/parse-nvmf-boot-connections.sh | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/modules.d/95nvmf/parse-nvmf-boot-connections.sh b/modules.d/95nvmf/parse-nvmf-boot-connections.sh +index 39923503..cfed5ae5 100755 +--- a/modules.d/95nvmf/parse-nvmf-boot-connections.sh ++++ b/modules.d/95nvmf/parse-nvmf-boot-connections.sh +@@ -24,7 +24,7 @@ if getargbool 0 rd.nonvmf; then + return 0 + fi + +-initqueue --onetime modprobe --all -b -q nvme nvme_tcp nvme_core nvme_fabrics ++initqueue --onetime modprobe --all -b -q nvme_tcp nvme_core nvme_fabrics + + parse_nvmf_discover() { + traddr="none" + diff --git a/0029.patch b/0029.patch new file mode 100644 index 0000000..059940c --- /dev/null +++ b/0029.patch @@ -0,0 +1,28 @@ +From aef95e59e918ed9aaaf7e5c2daf32ff205ed314c Mon Sep 17 00:00:00 2001 +From: Martin Wilck +Date: Sat, 17 Sep 2022 00:40:49 +0200 +Subject: [PATCH] fix(nvmf): don't create did-setup file + +did-setup files are meant to indicate that an interface setup +was successful. Don't do it here. + +Resolves: #1933787 +--- + modules.d/95nvmf/parse-nvmf-boot-connections.sh | 3 --- + 1 file changed, 3 deletions(-) + +diff --git a/modules.d/95nvmf/parse-nvmf-boot-connections.sh b/modules.d/95nvmf/parse-nvmf-boot-connections.sh +index cfed5ae5..1cdaba69 100755 +--- a/modules.d/95nvmf/parse-nvmf-boot-connections.sh ++++ b/modules.d/95nvmf/parse-nvmf-boot-connections.sh +@@ -102,9 +102,6 @@ done + + if [ -f "/etc/nvme/discovery.conf" ]; then + /sbin/initqueue --settled --onetime --unique --name nvme-discover /usr/sbin/nvme connect-all +- if [ "$trtype" = "tcp" ]; then +- : > /tmp/net."$ifname".did-setup +- fi + else + # No nvme command line arguments present, try autodiscovery + if [ "$trtype" = "fc" ]; then + diff --git a/0030.patch b/0030.patch new file mode 100644 index 0000000..65b2659 --- /dev/null +++ b/0030.patch @@ -0,0 +1,26 @@ +From b4987c9544224e7b3dae7b4411a2c8437ec573ab Mon Sep 17 00:00:00 2001 +From: Martin Wilck +Date: Sat, 17 Sep 2022 00:49:29 +0200 +Subject: [PATCH] fix(nvmf): don't use "finished" queue for autoconnect + +The "finished" initqueue is for testing if everything is alright, +not for triggering any actions. + +Resolves: #1933787 +--- + modules.d/95nvmf/parse-nvmf-boot-connections.sh | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/modules.d/95nvmf/parse-nvmf-boot-connections.sh b/modules.d/95nvmf/parse-nvmf-boot-connections.sh +index 1cdaba69..df104606 100755 +--- a/modules.d/95nvmf/parse-nvmf-boot-connections.sh ++++ b/modules.d/95nvmf/parse-nvmf-boot-connections.sh +@@ -105,6 +105,6 @@ if [ -f "/etc/nvme/discovery.conf" ]; then + else + # No nvme command line arguments present, try autodiscovery + if [ "$trtype" = "fc" ]; then +- /sbin/initqueue --finished --onetime --unique --name nvme-fc-autoconnect /sbin/nvmf-autoconnect.sh ++ /sbin/initqueue --settled --onetime --unique --name nvme-fc-autoconnect /sbin/nvmf-autoconnect.sh + fi + fi + diff --git a/0031.patch b/0031.patch new file mode 100644 index 0000000..39443a2 --- /dev/null +++ b/0031.patch @@ -0,0 +1,48 @@ +From 5f0e59418133379f50cc7af30674ce96569d9038 Mon Sep 17 00:00:00 2001 +From: Martin Wilck +Date: Sat, 17 Sep 2022 00:51:46 +0200 +Subject: [PATCH] fix(nvmf): make sure "rd.nvmf.discover=fc,auto" takes + precedence + +The command line may contain several rd.nvmf.discover options. +The "fc,auto" option should take precedence. + +Resolves: #1933787 +--- + modules.d/95nvmf/parse-nvmf-boot-connections.sh | 16 +++++++++------- + 1 file changed, 9 insertions(+), 7 deletions(-) + +diff --git a/modules.d/95nvmf/parse-nvmf-boot-connections.sh b/modules.d/95nvmf/parse-nvmf-boot-connections.sh +index df104606..c8078a76 100755 +--- a/modules.d/95nvmf/parse-nvmf-boot-connections.sh ++++ b/modules.d/95nvmf/parse-nvmf-boot-connections.sh +@@ -92,19 +92,21 @@ if [ -n "$nvmf_hostid" ]; then + echo "$nvmf_hostid" > /etc/nvme/hostid + fi + ++NVMF_FC_AUTO= + for d in $(getargs rd.nvmf.discover -d nvmf.discover=); do +- parse_nvmf_discover "$d" || break ++ parse_nvmf_discover "$d" || { ++ NVMF_FC_AUTO=1 ++ break ++ } + done + + # Host NQN and host id are mandatory for NVMe-oF + [ -f "/etc/nvme/hostnqn" ] || exit 0 + [ -f "/etc/nvme/hostid" ] || exit 0 + +-if [ -f "/etc/nvme/discovery.conf" ]; then +- /sbin/initqueue --settled --onetime --unique --name nvme-discover /usr/sbin/nvme connect-all ++# If no nvme command line arguments present, try autodiscovery ++if [ $NVMF_FC_AUTO ] || [ ! -f "/etc/nvme/discovery.conf" ]; then ++ /sbin/initqueue --settled --onetime --unique --name nvme-fc-autoconnect /sbin/nvmf-autoconnect.sh + else +- # No nvme command line arguments present, try autodiscovery +- if [ "$trtype" = "fc" ]; then +- /sbin/initqueue --settled --onetime --unique --name nvme-fc-autoconnect /sbin/nvmf-autoconnect.sh +- fi ++ /sbin/initqueue --settled --onetime --unique --name nvme-discover /usr/sbin/nvme connect-all + fi + diff --git a/0032.patch b/0032.patch new file mode 100644 index 0000000..21eb08e --- /dev/null +++ b/0032.patch @@ -0,0 +1,38 @@ +From 5b6ddf6e989f44211e799fec9aac6b7afb36e1ce Mon Sep 17 00:00:00 2001 +From: Martin Wilck +Date: Sat, 17 Sep 2022 00:54:25 +0200 +Subject: [PATCH] fix(nvmf): avoid calling "exit" in a cmdline hook + +"exit" should never be executed in dracut hooks, because the +hooks are sourced by the main script. + +Resolves: #1933787 +--- + modules.d/95nvmf/parse-nvmf-boot-connections.sh | 14 +++++++------- + 1 file changed, 7 insertions(+), 7 deletions(-) + +diff --git a/modules.d/95nvmf/parse-nvmf-boot-connections.sh b/modules.d/95nvmf/parse-nvmf-boot-connections.sh +index c8078a76..cc545ee0 100755 +--- a/modules.d/95nvmf/parse-nvmf-boot-connections.sh ++++ b/modules.d/95nvmf/parse-nvmf-boot-connections.sh +@@ -101,12 +101,12 @@ for d in $(getargs rd.nvmf.discover -d nvmf.discover=); do + done + + # Host NQN and host id are mandatory for NVMe-oF +-[ -f "/etc/nvme/hostnqn" ] || exit 0 +-[ -f "/etc/nvme/hostid" ] || exit 0 ++if [ -f "/etc/nvme/hostnqn" ] && [ -f "/etc/nvme/hostid" ]; then + +-# If no nvme command line arguments present, try autodiscovery +-if [ $NVMF_FC_AUTO ] || [ ! -f "/etc/nvme/discovery.conf" ]; then +- /sbin/initqueue --settled --onetime --unique --name nvme-fc-autoconnect /sbin/nvmf-autoconnect.sh +-else +- /sbin/initqueue --settled --onetime --unique --name nvme-discover /usr/sbin/nvme connect-all ++ # If no nvme command line arguments present, try autodiscovery ++ if [ $NVMF_FC_AUTO ] || [ ! -f "/etc/nvme/discovery.conf" ]; then ++ /sbin/initqueue --settled --onetime --unique --name nvme-fc-autoconnect /sbin/nvmf-autoconnect.sh ++ else ++ /sbin/initqueue --settled --onetime --unique --name nvme-discover /usr/sbin/nvme connect-all ++ fi + fi + diff --git a/0033.patch b/0033.patch new file mode 100644 index 0000000..0a957fe --- /dev/null +++ b/0033.patch @@ -0,0 +1,26 @@ +From 0464b41d8dfc7676429fcee67357bf01e09eac7d Mon Sep 17 00:00:00 2001 +From: Martin Wilck +Date: Sat, 17 Sep 2022 00:02:16 +0200 +Subject: [PATCH] fix(nvmf): run cmdline hook before parse-ip-opts.sh + +This way we can set "rd.neednet" and have it seen by parse-ip-options.sh + +Resolves: #1933787 +--- + modules.d/95nvmf/module-setup.sh | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/modules.d/95nvmf/module-setup.sh b/modules.d/95nvmf/module-setup.sh +index 0825b51c..ce5ccde2 100755 +--- a/modules.d/95nvmf/module-setup.sh ++++ b/modules.d/95nvmf/module-setup.sh +@@ -128,7 +128,7 @@ install() { + inst_script "${moddir}/nvmf-autoconnect.sh" /sbin/nvmf-autoconnect.sh + + inst_multiple nvme +- inst_hook cmdline 99 "$moddir/parse-nvmf-boot-connections.sh" ++ inst_hook cmdline 92 "$moddir/parse-nvmf-boot-connections.sh" + inst_simple "/etc/nvme/discovery.conf" + inst_rules /usr/lib/udev/rules.d/71-nvmf-iopolicy-netapp.rules + inst_rules "$moddir/95-nvmf-initqueue.rules" + diff --git a/0034.patch b/0034.patch new file mode 100644 index 0000000..4f75d54 --- /dev/null +++ b/0034.patch @@ -0,0 +1,50 @@ +From 0a074c5d0813df405e7a5dd55493c78099094106 Mon Sep 17 00:00:00 2001 +From: Martin Wilck +Date: Sat, 17 Sep 2022 00:24:38 +0200 +Subject: [PATCH] feat(nvmf): set rd.neednet=1 if tcp records encountered + +This is currently always the case for NBFT records. +We can do this now, as we run before parse-ip-options.sh + +Resolves: #1933787 +--- + modules.d/95nvmf/parse-nvmf-boot-connections.sh | 11 +++++++++-- + 1 file changed, 9 insertions(+), 2 deletions(-) + +diff --git a/modules.d/95nvmf/parse-nvmf-boot-connections.sh b/modules.d/95nvmf/parse-nvmf-boot-connections.sh +index cc545ee0..6b26f762 100755 +--- a/modules.d/95nvmf/parse-nvmf-boot-connections.sh ++++ b/modules.d/95nvmf/parse-nvmf-boot-connections.sh +@@ -62,7 +62,9 @@ parse_nvmf_discover() { + warn "traddr is mandatory for $trtype" + return 0 + fi +- if [ "$trtype" = "fc" ]; then ++ if [ "$trtype" = "tcp" ]; then ++ : > /tmp/nvmf_needs_network ++ elif [ "$trtype" = "fc" ]; then + if [ "$traddr" = "auto" ]; then + rm /etc/nvme/discovery.conf + return 1 +@@ -71,7 +73,7 @@ parse_nvmf_discover() { + warn "host traddr is mandatory for fc" + return 0 + fi +- elif [ "$trtype" != "rdma" ] && [ "$trtype" != "tcp" ]; then ++ elif [ "$trtype" != "rdma" ]; then + warn "unsupported transport $trtype" + return 0 + fi +@@ -100,6 +102,11 @@ for d in $(getargs rd.nvmf.discover -d nvmf.discover=); do + } + done + ++if [ -e /tmp/nvmf_needs_network ]; then ++ echo "rd.neednet=1" > /etc/cmdline.d/nvmf-neednet.conf ++ rm -f /tmp/nvmf_needs_network ++fi ++ + # Host NQN and host id are mandatory for NVMe-oF + if [ -f "/etc/nvme/hostnqn" ] && [ -f "/etc/nvme/hostid" ]; then + + diff --git a/0035.patch b/0035.patch new file mode 100644 index 0000000..6c146f1 --- /dev/null +++ b/0035.patch @@ -0,0 +1,28 @@ +From 185e200e9969f717faa5014d87be579ce452d2fe Mon Sep 17 00:00:00 2001 +From: Martin Wilck +Date: Thu, 12 Jan 2023 11:06:35 +0100 +Subject: [PATCH] fix(nvmf): install 8021q module unconditionally + +In NBFT setups, VLAN can be configured in the firmware. +Add the 8021q module in hostonly mode even if VLAN is currently +not used to be prepared for such configuration change. + +Resolves: #1933787 +--- + modules.d/95nvmf/module-setup.sh | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/modules.d/95nvmf/module-setup.sh b/modules.d/95nvmf/module-setup.sh +index ce5ccde2..f7fd62a0 100755 +--- a/modules.d/95nvmf/module-setup.sh ++++ b/modules.d/95nvmf/module-setup.sh +@@ -50,7 +50,7 @@ depends() { + # called by dracut + installkernel() { + instmods nvme_fc lpfc qla2xxx +- hostonly="" instmods nvme_tcp nvme_fabrics ++ hostonly="" instmods nvme_tcp nvme_fabrics 8021q + } + + # called by dracut + diff --git a/0036.patch b/0036.patch new file mode 100644 index 0000000..611548e --- /dev/null +++ b/0036.patch @@ -0,0 +1,45 @@ +From 1a6c2fdade221e9d69e14e2b6f3386ca8fc4a8b6 Mon Sep 17 00:00:00 2001 +From: Martin Wilck +Date: Thu, 9 Mar 2023 16:55:36 +0100 +Subject: [PATCH] fix(nvmf): support /etc/nvme/config.json + +Since nvme-cli 2.0, configuration of subsystems to connect to is +stored under `/etc/nvme` in either `discovery.conf` or `config.json`. +Attempt discovery also if the latter exists, but not the former. +Also, install "config.json" if it's present on the root FS. + +As before, "rd.nvmf.discover=fc,auto" will force either file to be ignored, +and NBFT-defined targets take precedence if found. + +Resolves: #1933787 +--- + modules.d/95nvmf/module-setup.sh | 1 + + modules.d/95nvmf/parse-nvmf-boot-connections.sh | 2 +- + 2 files changed, 2 insertions(+), 1 deletion(-) + +diff --git a/modules.d/95nvmf/module-setup.sh b/modules.d/95nvmf/module-setup.sh +index f7fd62a0..46ecb38f 100755 +--- a/modules.d/95nvmf/module-setup.sh ++++ b/modules.d/95nvmf/module-setup.sh +@@ -130,6 +130,7 @@ install() { + inst_multiple nvme + inst_hook cmdline 92 "$moddir/parse-nvmf-boot-connections.sh" + inst_simple "/etc/nvme/discovery.conf" ++ inst_simple "/etc/nvme/config.json" + inst_rules /usr/lib/udev/rules.d/71-nvmf-iopolicy-netapp.rules + inst_rules "$moddir/95-nvmf-initqueue.rules" + dracut_need_initqueue +diff --git a/modules.d/95nvmf/parse-nvmf-boot-connections.sh b/modules.d/95nvmf/parse-nvmf-boot-connections.sh +index 6b26f762..6c5ef4bc 100755 +--- a/modules.d/95nvmf/parse-nvmf-boot-connections.sh ++++ b/modules.d/95nvmf/parse-nvmf-boot-connections.sh +@@ -66,7 +66,7 @@ parse_nvmf_discover() { + : > /tmp/nvmf_needs_network + elif [ "$trtype" = "fc" ]; then + if [ "$traddr" = "auto" ]; then +- rm /etc/nvme/discovery.conf ++ rm -f /etc/nvme/discovery.conf /etc/nvme/config.json + return 1 + fi + if [ "$hosttraddr" = "none" ]; then + diff --git a/0037.patch b/0037.patch new file mode 100644 index 0000000..72259fd --- /dev/null +++ b/0037.patch @@ -0,0 +1,511 @@ +From add394a3532b968e12bc7b9a8923cc4b85f5f724 Mon Sep 17 00:00:00 2001 +From: Martin Wilck +Date: Fri, 16 Sep 2022 21:36:52 +0200 +Subject: [PATCH] feat(nvmf): add code for parsing the NBFT + +Add code to parse the Nvme-oF Boot Firmware Table (NBFT) according +to the NVM Express Boot Specification 1.0 [1]. The implementation in +dracut follows a similar general approach as iBFT support in the +iscsi module. + +NBFT support requires two steps: + +(1) Setting up the network and routing according to the + HFI ("Host Fabric Interface") records in the NBFT, +(2) Establishing the actual NVMe-oF connection. + +(1) is accomplished by reading the NBFT using JSON output from +the "nvme nbft show" command, and transforming it into command +line options ("ip=", "rd.neednet", etc.) understood by dracut's +network module and its backends. The resulting network setup code +is backend-agnostic. It has been tested with the "network-legacy" +and "network-manager" network backend modules. The network setup +code supports IPv4 and IPv6 with static, RA, or DHCP configurations, +802.1q VLANs, and simple routing / gateway setup. + +(2) is done using the "nvme connect-all" command [2] in the netroot handler, +which is invoked by networking backends when an interface gets fully +configured. This patch adds support for "netboot=nbft". The "nbftroot" +handler calls nvmf-autoconnect.sh, which contains the actual connect +logic. nvmf-autoconnect.sh itself is preserved, because there are +other NVMe-oF setups like NVMe over FC which don't depend on the +network. + +The various ways to configure NVMe-oF are prioritized like this: + + 1 FC autoconnect from kernel commandline (rd.nvmf.discover=fc,auto) + 2 NBFT, if present + 3 discovery.conf or config.json, if present, and cmdline.d parameters, + if present (rd.nvmf.discovery=...) + 4 FC autoconnect (without kernel command line) + +The reason for this priorization is that in the initial RAM fs, we try +to activate only those connections that are necessary to mount the root +file system. This avoids confusion, possible contradicting or ambiguous +configuration, and timeouts from unavailable targets. + +A retry logic is implemented for enabling the NVMe-oF connections, +using the "settled" initqueue, the netroot handler, and eventually, the +"timeout" initqueue. This is similar to the retry logic of the iscsi module. +In the "timeout" case, connection to all possible NVMe-oF subsystems +is attempted. + +Two new command line parameters are introduced to make it possible to +change the priorities above: + + - "rd.nvmf.nonbft" causes the NBFT to be ignored, + - "rd.nvmf.nostatic" causes any statically configured NVMe-oF targets + (config.json, discovery.conf, and cmdline.d) to be ignored. + +These parameters may be helpful to skip attempts to set up broken +configurations. + +At initramfs build time, the nvmf module is now enabled if an NBFT +table is detected in the system. + +[1] https://nvmexpress.org/wp-content/uploads/NVM-Express-Boot-Specification-2022.11.15-Ratified.pdf +[2] NBFT support in nvme-cli requires the latest upstream code (> v2.4). + +Signed-off-by: Martin Wilck +Co-authored-by: John Meneghini +Co-authored-by: Charles Rose + +(Cherry-picked commits: +9664e98b5db603567d42d4d0c6e6ea1bd3d5bf24 +b3ff3f3fbce6878a754332cd4a05374e5e1156c8 +a3cf4ec92202df43adf368c7fdd12e35d304a0e4 +03921ec09e95ea49f89ae307dcca4e2e3d1bc6d6 +e93e46520dd89a7357a15441ab6b141ff9ff9aeb +556ef46aa96650d72b2fd850a09fa04dff64bbb8 +a93968b07567a654d18b8ef2144337d803186eca +a65fab69662d3adf52eb968411f59ebc5a173f7c +cf8986af7d9a3ce73f330de23d5312f924acea34 +7c28e1148c086d8504caab6e70a1bcfda1bbf0b9 +b03dc850e4630c3b727f71b853a1be588507a59e +0a4d7f9aece172f0f9a9286c94308b7e1ef8d500) + +Resolves: #1933787 +--- + man/dracut.cmdline.7.asc | 9 + + modules.d/95nvmf/module-setup.sh | 25 ++- + modules.d/95nvmf/nbftroot.sh | 5 + + modules.d/95nvmf/nvmf-autoconnect.sh | 55 +++++- + modules.d/95nvmf/parse-nvmf-boot-connections.sh | 235 ++++++++++++++++++++++-- + 5 files changed, 305 insertions(+), 24 deletions(-) + +diff --git a/man/dracut.cmdline.7.asc b/man/dracut.cmdline.7.asc +index 40d13d83..abe1ec3f 100644 +--- a/man/dracut.cmdline.7.asc ++++ b/man/dracut.cmdline.7.asc +@@ -898,6 +898,15 @@ NVMf + **rd.nonvmf=0**:: + Disable NVMf + ++**rd.nvmf.nonbft**:: ++ Disable connecting to targets from the NVMe Boot Firmware Table. Without ++ this parameter, NBFT connections will take precedence over _rd.nvmf.discover_. ++ ++**rd.nvmf.nostatic**:: ++ Disable connecting to targets that have been statically configured when ++ the initramfs was built. Targets specified with rd.nvmf.discover on the ++ kernel command line will still be tried. ++ + **rd.nvmf.hostnqn=**____:: + NVMe host NQN to use + +diff --git a/modules.d/95nvmf/module-setup.sh b/modules.d/95nvmf/module-setup.sh +index 46ecb38f..1dd2ca53 100755 +--- a/modules.d/95nvmf/module-setup.sh ++++ b/modules.d/95nvmf/module-setup.sh +@@ -2,7 +2,7 @@ + + # called by dracut + check() { +- require_binaries nvme || return 1 ++ require_binaries nvme jq || return 1 + [ -f /etc/nvme/hostnqn ] || return 255 + [ -f /etc/nvme/hostid ] || return 255 + +@@ -25,17 +25,27 @@ check() { + [[ $trtype == "fc" ]] || [[ $trtype == "tcp" ]] || [[ $trtype == "rdma" ]] + } + ++ has_nbft() { ++ local f found= ++ for f in /sys/firmware/acpi/tables/NBFT*; do ++ [ -f "$f" ] || continue ++ found=1 ++ break ++ done ++ [[ $found ]] ++ } ++ + [[ $hostonly ]] || [[ $mount_needs ]] && { + pushd . > /dev/null + for_each_host_dev_and_slaves is_nvmf + local _is_nvmf=$? + popd > /dev/null || exit + [[ $_is_nvmf == 0 ]] || return 255 +- if [ ! -f /sys/class/fc/fc_udev_device/nvme_discovery ]; then +- if [ ! -f /etc/nvme/discovery.conf ]; then +- echo "No discovery arguments present" +- return 255 +- fi ++ if [ ! -f /sys/class/fc/fc_udev_device/nvme_discovery ] \ ++ && [ ! -f /etc/nvme/discovery.conf ] \ ++ && [ ! -f /etc/nvme/config.json ] && ! has_nbft; then ++ echo "No discovery arguments present" ++ return 255 + fi + } + return 0 +@@ -126,8 +136,9 @@ install() { + inst_multiple ip sed + + inst_script "${moddir}/nvmf-autoconnect.sh" /sbin/nvmf-autoconnect.sh ++ inst_script "${moddir}/nbftroot.sh" /sbin/nbftroot + +- inst_multiple nvme ++ inst_multiple nvme jq + inst_hook cmdline 92 "$moddir/parse-nvmf-boot-connections.sh" + inst_simple "/etc/nvme/discovery.conf" + inst_simple "/etc/nvme/config.json" +diff --git a/modules.d/95nvmf/nbftroot.sh b/modules.d/95nvmf/nbftroot.sh +new file mode 100755 +index 00000000..0f334995 +--- /dev/null ++++ b/modules.d/95nvmf/nbftroot.sh +@@ -0,0 +1,5 @@ ++#! /bin/sh ++# This script is called from /sbin/netroot ++ ++/sbin/nvmf-autoconnect.sh online ++exit 0 +diff --git a/modules.d/95nvmf/nvmf-autoconnect.sh b/modules.d/95nvmf/nvmf-autoconnect.sh +index c8f676a7..35ee9487 100755 +--- a/modules.d/95nvmf/nvmf-autoconnect.sh ++++ b/modules.d/95nvmf/nvmf-autoconnect.sh +@@ -1,5 +1,54 @@ +-#!/bin/bash ++#!/bin/sh ++# Argument $1 is "settled", "online", or "timeout", indicating ++# the queue from which the script is called. ++# In the "timeout" case, try everything. ++# Otherwise, try options according to the priorities below. + +-[ -f /sys/class/fc/fc_udev_device/nvme_discovery ] || exit 1 +-echo add > /sys/class/fc/fc_udev_device/nvme_discovery ++[ "$RD_DEBUG" != yes ] || set -x ++ ++if [ "$1" = timeout ]; then ++ [ ! -f /sys/class/fc/fc_udev_device/nvme_discovery ] \ ++ || echo add > /sys/class/fc/fc_udev_device/nvme_discovery ++ /usr/sbin/nvme connect-all ++ exit 0 ++fi ++ ++NVMF_HOSTNQN_OK= ++[ ! -f "/etc/nvme/hostnqn" ] || [ ! -f "/etc/nvme/hostid" ] || NVMF_HOSTNQN_OK=1 ++ ++# Only nvme-cli 2.5 or newer supports the options --nbft and --no-nbft ++# for the connect-all command. ++# Make sure we don't use unsupported options with earlier versions. ++NBFT_SUPPORTED= ++# shellcheck disable=SC2016 ++/usr/sbin/nvme connect-all --help 2>&1 | sed -n '/[[:space:]]--nbft[[:space:]]/q1;$q0' \ ++ || NBFT_SUPPORTED=1 ++ ++if [ -e /tmp/nvmf-fc-auto ] && [ "$NVMF_HOSTNQN_OK" ] \ ++ && [ -f /sys/class/fc/fc_udev_device/nvme_discovery ]; then ++ # prio 1: cmdline override "rd.nvmf.discovery=fc,auto" ++ echo add > /sys/class/fc/fc_udev_device/nvme_discovery ++ exit 0 ++fi ++if [ "$NBFT_SUPPORTED" ] && [ -e /tmp/valid_nbft_entry_found ]; then ++ # prio 2: NBFT ++ /usr/sbin/nvme connect-all --nbft ++ exit 0 ++fi ++if [ -f /etc/nvme/discovery.conf ] || [ -f /etc/nvme/config.json ] \ ++ && [ "$NVMF_HOSTNQN_OK" ]; then ++ # prio 3: configuration from initrd and/or kernel command line ++ # We can get here even if "rd.nvmf.nonbft" was given, thus use --no-nbft ++ if [ "$NBFT_SUPPORTED" ]; then ++ /usr/sbin/nvme connect-all --no-nbft ++ else ++ /usr/sbin/nvme connect-all ++ fi ++ exit 0 ++fi ++if [ "$NVMF_HOSTNQN_OK" ] \ ++ && [ -f /sys/class/fc/fc_udev_device/nvme_discovery ]; then ++ # prio 4: no discovery entries, try NVMeoFC autoconnect ++ echo add > /sys/class/fc/fc_udev_device/nvme_discovery ++fi + exit 0 +diff --git a/modules.d/95nvmf/parse-nvmf-boot-connections.sh b/modules.d/95nvmf/parse-nvmf-boot-connections.sh +index 6c5ef4bc..66018371 100755 +--- a/modules.d/95nvmf/parse-nvmf-boot-connections.sh ++++ b/modules.d/95nvmf/parse-nvmf-boot-connections.sh +@@ -17,13 +17,225 @@ + # specify any discover parameters for FC. + # + +-type is_ip > /dev/null 2>&1 || . /lib/net-lib.sh ++command -v getarg > /dev/null || . /lib/dracut-lib.sh ++command -v is_ip > /dev/null || . /lib/net-lib.sh ++ ++## Sample NBFT output from nvme show-nbft -H -s -d -o json ++# [ ++# { ++# "filename":"/sys/firmware/acpi/tables/NBFT", ++# "host":{ ++# "nqn":"nqn.2014-08.org.nvmexpress:uuid:d6f07002-7eb5-4841-a185-400e296afae4", ++# "id":"111919da-21ea-cc4e-bafe-216d8372dd31", ++# "host_id_configured":0, ++# "host_nqn_configured":0, ++# "primary_admin_host_flag":"not indicated" ++# }, ++# "subsystem":[ ++# { ++# "index":1, ++# "num_hfis":1, ++# "hfis":[ ++# 1 ++# ], ++# "transport":"tcp", ++# "transport_address":"192.168.100.216", ++# "transport_svcid":"4420", ++# "subsys_port_id":0, ++# "nsid":1, ++# "nid_type":"uuid", ++# "nid":"424d1c8a-8ef9-4681-b2fc-8c343bd8fa69", ++# "subsys_nqn":"timberland-01", ++# "controller_id":0, ++# "asqsz":0, ++# "pdu_header_digest_required":0, ++# "data_digest_required":0 ++# } ++# ], ++# "hfi":[ ++# { ++# "index":1, ++# "transport":"tcp", ++# "pcidev":"0:0:2.0", ++# "mac_addr":"52:54:00:4f:97:e9", ++# "vlan":0, ++# "ip_origin":63, ++# "ipaddr":"192.168.100.217", ++# "subnet_mask_prefix":24, ++# "gateway_ipaddr":"0.0.0.0", ++# "route_metric":0, ++# "primary_dns_ipaddr":"0.0.0.0", ++# "secondary_dns_ipaddr":"0.0.0.0", ++# "dhcp_server_ipaddr":"", ++# "this_hfi_is_default_route":1 ++# } ++# ], ++# "discovery":[ ++# ] ++# } ++# ] ++# ++# If the IP address is derived from DHCP, it sets the field ++# "hfi.dhcp_server_ipaddr" to a non-emtpy value. ++# ++# ++ ++nbft_run_jq() { ++ local st ++ local opts="-e" ++ ++ while [ $# -gt 0 ]; do ++ case $1 in ++ -*) ++ opts="$opts $1" ++ ;; ++ *) ++ break ++ ;; ++ esac ++ shift ++ done ++ # Not quoting is intentional here. We won't get glob expressions passed. ++ # shellcheck disable=SC2086 ++ jq $opts "$1" << EOF ++$2 ++EOF ++ st=$? ++ if [ $st -ne 0 ]; then ++ warn "NBFT: jq error while processing \"$1\"" ++ return $st ++ else ++ return 0 ++ fi ++} ++ ++nbft_check_empty_address() { ++ # suppress meaningless or empty IP addresses ++ # "null" is returned by jq if no match found for expression ++ case $1 in ++ null | "::" | "0.0.0.0") ;; ++ *) ++ echo "$1" ++ ;; ++ esac ++} ++ ++nbft_parse_hfi() { ++ # false positive of shellcheck - no expansion in variable assignments ++ # shellcheck disable=2086 ++ local hfi_json=$1 ++ local mac iface ipaddr prefix vlan gateway dns1 dns2 hostname adrfam dhcp ++ ++ mac=$(nbft_run_jq -r .mac_addr "$hfi_json") || return 1 ++ iface=$(set_ifname nbft "$mac") ++ ++ vlan=$(nbft_run_jq .vlan "$hfi_json") || vlan=0 ++ # treat VLAN zero as "no vlan" ++ [ "$vlan" -ne 0 ] || vlan= ++ ++ [ ! -e /tmp/net."${iface}${vlan:+.$vlan}".has_ibft_config ] || return 0 ++ ++ dhcp=$(nbft_run_jq -r .dhcp_server_ipaddr "$hfi_json") ++ # We need to check $? here as the above is an assignment ++ # shellcheck disable=2181 ++ if [ $? -eq 0 ] && [ "$dhcp" ] && [ "$dhcp" != null ]; then ++ case $dhcp in ++ *:*) ++ echo ip="$iface${vlan:+.$vlan}:dhcp6" ++ ;; ++ *.*.*.*) ++ echo ip="$iface${vlan:+.$vlan}:dhcp" ++ ;; ++ *) ++ warn "Invalid value for dhcp_server_ipaddr: $dhcp" ++ return 1 ++ ;; ++ esac ++ else ++ ipaddr=$(nbft_run_jq -r .ipaddr "$hfi_json") || return 1 ++ ++ case $ipaddr in ++ *.*.*.*) ++ adrfam=ipv4 ++ ;; ++ *:*) ++ adrfam=ipv6 ++ ;; ++ *) ++ warn "invalid address: $ipaddr" ++ return 1 ++ ;; ++ esac ++ prefix=$(nbft_run_jq -r .subnet_mask_prefix "$hfi_json") ++ # Need to check $? here as he above is an assignment ++ # shellcheck disable=2181 ++ if [ $? -ne 0 ] && [ "$adrfam" = ipv6 ]; then ++ prefix=128 ++ fi ++ # Use brackets for IPv6 ++ if [ "$adrfam" = ipv6 ]; then ++ ipaddr="[$ipaddr]" ++ fi ++ ++ gateway=$(nbft_check_empty_address \ ++ "$(nbft_run_jq -r .gateway_ipaddr "$hfi_json")") ++ dns1=$(nbft_check_empty_address \ ++ "$(nbft_run_jq -r .primary_dns_ipaddr "$hfi_json")") ++ dns2=$(nbft_check_empty_address \ ++ "$(nbft_run_jq -r .secondary_dns_ipaddr "$hfi_json")") ++ hostname=$(nbft_run_jq -r .host_name "$hfi_json" 2> /dev/null) || hostname= ++ ++ echo "ip=$ipaddr::$gateway:$prefix:$hostname:$iface${vlan:+.$vlan}:none${dns1:+:$dns1}${dns2:+:$dns2}" ++ fi ++ ++ if [ "$vlan" ]; then ++ echo "vlan=$iface.$vlan:$iface" ++ echo "$mac" > "/tmp/net.$iface.$vlan.has_ibft_config" ++ else ++ echo "$mac" > "/tmp/net.$iface.has_ibft_config" ++ fi ++ : > /tmp/valid_nbft_entry_found ++} ++ ++nbft_parse() { ++ local nbft_json n_nbft all_hfi_json n_hfi ++ local j=0 i ++ ++ nbft_json=$(nvme nbft show -H -o json) || return 0 ++ n_nbft=$(nbft_run_jq ". | length" "$nbft_json") || return 0 ++ ++ while [ "$j" -lt "$n_nbft" ]; do ++ all_hfi_json=$(nbft_run_jq ".[$j].hfi" "$nbft_json") || continue ++ n_hfi=$(nbft_run_jq ". | length" "$all_hfi_json") || continue ++ i=0 ++ ++ while [ "$i" -lt "$n_hfi" ]; do ++ nbft_parse_hfi "$(nbft_run_jq ".[$i]" "$all_hfi_json")" ++ i=$((i + 1)) ++ done ++ j=$((j + 1)) ++ done >> /etc/cmdline.d/40-nbft.conf ++} + + if getargbool 0 rd.nonvmf; then + warn "rd.nonvmf=0: skipping nvmf" + return 0 + fi + ++if getargbool 0 rd.nvmf.nostatic; then ++ rm -f /etc/cmdline.d/95nvmf-args.conf ++ rm -f /etc/nvme/discovery.conf /etc/nvme/config.json ++fi ++ ++if ! getargbool 0 rd.nvmf.nonbft; then ++ for _x in /sys/firmware/acpi/tables/NBFT*; do ++ if [ -f "$_x" ]; then ++ nbft_parse ++ break ++ fi ++ done ++fi ++ + initqueue --onetime modprobe --all -b -q nvme_tcp nvme_core nvme_fabrics + + parse_nvmf_discover() { +@@ -94,26 +306,21 @@ if [ -n "$nvmf_hostid" ]; then + echo "$nvmf_hostid" > /etc/nvme/hostid + fi + +-NVMF_FC_AUTO= ++rm -f /tmp/nvmf-fc-auto + for d in $(getargs rd.nvmf.discover -d nvmf.discover=); do + parse_nvmf_discover "$d" || { +- NVMF_FC_AUTO=1 ++ : > /tmp/nvmf-fc-auto + break + } + done + +-if [ -e /tmp/nvmf_needs_network ]; then ++if [ -e /tmp/nvmf_needs_network ] || [ -e /tmp/valid_nbft_entry_found ]; then + echo "rd.neednet=1" > /etc/cmdline.d/nvmf-neednet.conf ++ # netroot is a global variable that is present in all "sourced" scripts ++ # shellcheck disable=SC2034 ++ netroot=nbft + rm -f /tmp/nvmf_needs_network + fi + +-# Host NQN and host id are mandatory for NVMe-oF +-if [ -f "/etc/nvme/hostnqn" ] && [ -f "/etc/nvme/hostid" ]; then +- +- # If no nvme command line arguments present, try autodiscovery +- if [ $NVMF_FC_AUTO ] || [ ! -f "/etc/nvme/discovery.conf" ]; then +- /sbin/initqueue --settled --onetime --unique --name nvme-fc-autoconnect /sbin/nvmf-autoconnect.sh +- else +- /sbin/initqueue --settled --onetime --unique --name nvme-discover /usr/sbin/nvme connect-all +- fi +-fi ++/sbin/initqueue --settled --onetime --name nvmf-connect-settled /sbin/nvmf-autoconnect.sh settled ++/sbin/initqueue --timeout --onetime --name nvmf-connect-timeout /sbin/nvmf-autoconnect.sh timeout diff --git a/dracut.spec b/dracut.spec index 38df3f6..20a067a 100644 --- a/dracut.spec +++ b/dracut.spec @@ -5,7 +5,7 @@ # strip the automatically generated dep here and instead co-own the # directory. %global __requires_exclude pkg-config -%define dist_free_release 22.git20230530 +%define dist_free_release 38.git20230725 Name: dracut Version: 057 @@ -50,6 +50,22 @@ Patch18: 0018.patch Patch19: 0019.patch Patch20: 0020.patch Patch21: 0021.patch +Patch22: 0022.patch +Patch23: 0023.patch +Patch24: 0024.patch +Patch25: 0025.patch +Patch26: 0026.patch +Patch27: 0027.patch +Patch28: 0028.patch +Patch29: 0029.patch +Patch30: 0030.patch +Patch31: 0031.patch +Patch32: 0032.patch +Patch33: 0033.patch +Patch34: 0034.patch +Patch35: 0035.patch +Patch36: 0036.patch +Patch37: 0037.patch Source1: https://www.gnu.org/licenses/lgpl-2.1.txt @@ -508,6 +524,24 @@ echo 'dracut_rescue_image="yes"' > $RPM_BUILD_ROOT%{dracutlibdir}/dracut.conf.d/ %{_prefix}/lib/kernel/install.d/51-dracut-rescue.install %changelog +* Tue Jul 25 2023 Pavel Valena - 057-38.git20230725 +- fix(dracut.sh): use dynamically uefi's sections offset +- fix(dracut.sh): handle imagebase for uefi +- fix(dracut.sh): use gawk for strtonum +- fix(rngd): install system service file +- fix(nvmf): nvme list-subsys prints the address using commas +- fix(nvmf): don't try to validate network connections in +- fix(nvmf): no need to load the nvme module +- fix(nvmf): don't create did-setup file +- fix(nvmf): don't use "finished" queue for autoconnect +- fix(nvmf): make sure "rd.nvmf.discover=fc,auto" takes +- fix(nvmf): avoid calling "exit" in a cmdline hook +- fix(nvmf): run cmdline hook before parse-ip-opts.sh +- feat(nvmf): set rd.neednet=1 if tcp records encountered +- fix(nvmf): install 8021q module unconditionally +- fix(nvmf): support /etc/nvme/config.json +- feat(nvmf): add code for parsing the NBFT + * Tue May 30 2023 Pavel Valena - 057-22.git20230530 - fix(lvmthinpool-monitor): activate lvm thin pool before