Re: [PATCH v8 6/6] ieee1275: support added for multiple nvme bootpaths

Vladimir 'phcoder' Serbinenko
2026-02-26T14:52:17Z

[-- Attachment #1.1: Type: text/plain, Size: 7915 bytes --]

Regards
Vladimir 'phcoder' Serbinenko

Le lun. 23 févr. 2026, 16:46, Avnish Chouhan <avnish@linux.ibm.com> a
écrit :

> This patch sets mupltiple NVMe boot-devices for more robust boot.
> Scenario where NVMe multipaths are available, all the available bootpaths
> (Max 5)
> will be added as the boot-device.
>
> Signed-off-by: Avnish Chouhan <avnish@linux.ibm.com>
> ---
> grub-core/osdep/unix/platform.c | 118
> ++++++++++++++++++++++++++++++++++++++++++++++++++++-
> grub-core/osdep/linux/ofpath.c | 4 ++--
> include/grub/util/install.h | 3 +++
> include/grub/util/ofpath.h | 4 ++++
> 4 file changed, 126 insertions(+), 3 deletion(-)
>
> diff --git a/grub-core/osdep/unix/platform.c
> b/grub-core/osdep/unix/platform.c
> index de71221..4632f41 100644
> --- a/grub-core/osdep/unix/platform.c
> +++ b/grub-core/osdep/unix/platform.c
> @@ -28,6 +28,10 @@
> #include <dirent.h>
> #include <string.h>
> #include <errno.h>
> +#include <grub/util/ofpath.h>
> +#include <stdbool.h>
> +
> +#define BOOTDEV_BUFFER 1000
>
> static char *
> get_ofpathname (const char *dev)
> @@ -176,6 +180,107 @@ grub_install_register_efi (grub_device_t
> efidir_grub_dev,
> return ret;
> }
>
> +
> +char *
> +add_multiple_nvme_bootdevices (const char *install_device)
>
Either make it static or add proper namespacing.

+{
> + char *sysfs_path, *nvme_ns, *ptr, *non_splitter_path;
> + unsigned int nsid;
> + char *multipath_boot, *ofpath, *ext_dir;
> + struct dirent *ep, *splitter_ep;
> + DIR *dp, *splitter_dp;
> + char *cntl_id, *dirR1, *dirR2, *splitter_info_path;
> + bool is_FC = false, is_splitter = false;
> +
> + nvme_ns = grub_strstr (install_device, "nvme");
> + nsid = of_path_get_nvme_nsid (nvme_ns);
> + if (nsid == 0)
> + return NULL;
> +
> + sysfs_path = nvme_get_syspath (nvme_ns);
> + ofpath = xasprintf ("%s", get_ofpathname (nvme_ns));
>
Use (x)strdup

> +
> + if (grub_strstr (ofpath, "fibre-channel"))
> + {
> + strcat (sysfs_path, "/device");
> + is_FC = true;
> + }
> + else
> + {
> + strcat (sysfs_path, "/subsystem");
> + is_FC = false;
> + }
>
Where do you ensure sufficient space in sysfs_path?

> + if (is_FC == false)
> + {
> + cntl_id = grub_strstr (nvme_ns, "e");
>
Use strchr

> + dirR1 = xasprintf ("nvme%c",cntl_id[1]);
> +
> + splitter_info_path = xasprintf ("/sys/block/%s/device", nvme_ns);
> + splitter_dp = opendir (splitter_info_path);
> + if (!splitter_dp)
> + return NULL;
> +
> + while ((splitter_ep = readdir (splitter_dp)) != NULL)
> + {
> + if (grub_strstr (splitter_ep->d_name, "nvme"))
> + {
> + if (grub_strstr (splitter_ep->d_name, dirR1))
> + continue;
> +
> + ext_dir = grub_strchr (splitter_ep->d_name, 'e');
> + if (grub_strchr (ext_dir, 'n') == NULL)
> + {
> + dirR2 = xasprintf("%s", splitter_ep->d_name);
> + is_splitter = true;
> + break;
> + }
> + }
> + }
> + closedir (splitter_dp);
> + }
> + sysfs_path = xrealpath (sysfs_path);
> + dp = opendir (sysfs_path);
> + if (!dp)
> + return NULL;
> +
> + ptr = multipath_boot = xmalloc (BOOTDEV_BUFFER);
> + if (is_splitter == false && is_FC == false)
> + {
> + non_splitter_path = xasprintf ("%s/namespace@%x:1 ",
> get_ofpathname (dirR1), nsid);
> + strncpy (ptr, non_splitter_path, strlen (non_splitter_path));
> + ptr += strlen (non_splitter_path);
>
Use stpcpy

> + free (non_splitter_path);
> + }
> + else
> + {
> + while ((ep = readdir (dp)) != NULL)
> + {
> + char *path;
> +
> + if (grub_strstr (ep->d_name, "nvme") != NULL)
> + {
> + if (is_FC == false && grub_strstr (ep->d_name, dirR1) ==
> NULL &&
> + grub_strstr (ep->d_name, dirR2) == NULL)
> + continue;
> + path = xasprintf ("%s/namespace@%x ", get_ofpathname
> (ep->d_name), nsid);
> + if ((strlen (multipath_boot) + strlen (path)) >
> BOOTDEV_BUFFER)
> + {
> + grub_util_warn (_("Maximum five entries are allowed in
> the bootlist"));
> + free (path);
> + break;
> + }
> + strncpy (ptr, path, strlen (path));
> + ptr += strlen (path);
>
Ditto

> + free (path);
> + }
> + }
> + }
> + *--ptr = '\0';
> + closedir (dp);
> +
> + return multipath_boot;
> +}
> +
> void
> grub_install_register_ieee1275 (int is_prep, const char *install_device,
> int partno, const char *relpath)
> @@ -215,8 +320,19 @@ grub_install_register_ieee1275 (int is_prep, const
> char *install_device,
> }
> *ptr = '\0';
> }
> + else if (grub_strstr (install_device, "nvme"))
> + {
> + boot_device = add_multiple_nvme_bootdevices (install_device);
>
What happens if I install via an UUID symlink? What happens if I install on
a file (disk image) named nvme1?

> + }
> else
> - boot_device = get_ofpathname (install_device);
> + {
> + boot_device = get_ofpathname (install_device);
> + if (grub_strstr (boot_device, "nvme-of"))
> + {
> + free (boot_device);
> + boot_device = add_multiple_nvme_bootdevices (install_device);
> + }
> + }
>
> if (grub_util_exec ((const char * []){ "nvsetenv", "boot-device",
> boot_device, NULL }))
> diff --git a/grub-core/osdep/linux/ofpath.c
> b/grub-core/osdep/linux/ofpath.c
> index 7158c8c..3a778e0 100644
> --- a/grub-core/osdep/linux/ofpath.c
> +++ b/grub-core/osdep/linux/ofpath.c
> @@ -209,7 +209,7 @@ find_obppath (const char *sysfs_path_orig)
> }
> }
>
> -static char *
> +char *
> xrealpath (const char *in)
>
Please add namespacing.

> {
> char *out;
> @@ -684,7 +684,7 @@ of_path_get_nvme_nsid (const char* devname)
> return nsid;
> }
>
> -static char *
> +char *
> nvme_get_syspath (const char *nvmedev)
>
Ditto

> {
> char *sysfs_path;
> diff --git a/include/grub/util/install.h b/include/grub/util/install.h
> index 51f3b13..a67e225 100644
> --- a/include/grub/util/install.h
> +++ b/include/grub/util/install.h
> @@ -235,6 +235,9 @@ grub_install_register_efi (grub_device_t
> efidir_grub_dev,
> const char *efifile_path,
> const char *efi_distributor);
>
> +char *
> +add_multiple_nvme_bootdevices (const char *install_device);
> +
> void
> grub_install_register_ieee1275 (int is_prep, const char *install_device,
> int partno, const char *relpath);
> diff --git a/include/grub/util/ofpath.h b/include/grub/util/ofpath.h
> index 5962322..78e78e7 100644
> --- a/include/grub/util/ofpath.h
> +++ b/include/grub/util/ofpath.h
> @@ -30,5 +30,9 @@ int add_filename_to_pile (char *filename, struct
> ofpath_files_list_root* root);
> void find_file (char* filename, char* directory, struct
> ofpath_files_list_root* root, int max_depth, int depth);
> char* of_find_fc_host (char* host_wwpn);
> void free_ofpath_files_list (struct ofpath_files_list_root* root);
> +char* nvme_get_syspath (const char *nvmedev);
> +unsigned int of_path_get_nvme_nsid (const char* devname);
> +char* xrealpath (const char *in);
> +
>
> #endif /* ! GRUB_OFPATH_MACHINE_UTIL_HEADER */
> --
> 2.50.1 (Apple Git-155)
>
>
> _______________________________________________
> Grub-devel mailing list
> Grub-devel@gnu.org
> https://lists.gnu.org/mailman/listinfo/grub-devel
>

[-- Attachment #1.2: Type: text/html, Size: 12173 bytes --]

[-- Attachment #2: Type: text/plain, Size: 141 bytes --]