From 386701a8fea5a55fbbf62d6e1739eb9c8f41ca26 Mon Sep 17 00:00:00 2001 From: Vladimir 'phcoder' Serbinenko Date: Thu, 19 Sep 2013 08:48:54 +0200 Subject: [PATCH] Handle the case of partitioned LVM properly. * grub-core/kern/emu/hostdisk.c (grub_util_get_dm_node_linear_info): Stop on meeting LVM, mpath or DMRAID. (grub_hostdisk_os_dev_to_grub_drive): Canonicalize os device. (read_device_map): Likewise. * util/getroot.c (convert_system_partition_to_system_disk): Assume that device is full disk rather than erroring out on LVM and similar cases. --- ChangeLog | 11 ++++++++ grub-core/kern/emu/hostdisk.c | 48 ++++++++++++++++++++++++----------- util/getroot.c | 9 +++---- 3 files changed, 48 insertions(+), 20 deletions(-) diff --git a/ChangeLog b/ChangeLog index 3cf7ffe6e..922bdf87f 100644 --- a/ChangeLog +++ b/ChangeLog @@ -3,6 +3,17 @@ * docs/grub.texi (Networking commands): Add documentation for network related commands. +2013-09-19 Vladimir Serbinenko + + Handle the case of partitioned LVM properly. + + * grub-core/kern/emu/hostdisk.c (grub_util_get_dm_node_linear_info): + Stop on meeting LVM, mpath or DMRAID. + (grub_hostdisk_os_dev_to_grub_drive): Canonicalize os device. + (read_device_map): Likewise. + * util/getroot.c (convert_system_partition_to_system_disk): Assume that + device is full disk rather than erroring out on LVM and similar cases. + 2013-09-18 Vladimir Serbinenko * util/grub-mkconfig_lib.in: Keep supplied pkgdatadir if any. diff --git a/grub-core/kern/emu/hostdisk.c b/grub-core/kern/emu/hostdisk.c index 81d37262b..b90a26d48 100644 --- a/grub-core/kern/emu/hostdisk.c +++ b/grub-core/kern/emu/hostdisk.c @@ -541,6 +541,7 @@ grub_util_get_dm_node_linear_info (const char *dev, int major = 0, minor = 0; int first = 1; grub_disk_addr_t partstart = 0; + const char *node_uuid; while (1) { @@ -560,6 +561,15 @@ grub_util_get_dm_node_linear_info (const char *dev, dm_task_destroy (dmt); break; } + node_uuid = dm_task_get_uuid (dmt); + if (node_uuid && (strncmp (node_uuid, "LVM-", 4) == 0 + || strncmp (node_uuid, "mpath-", 6) == 0 + || strncmp (node_uuid, "DMRAID-", 7) == 0)) + { + dm_task_destroy (dmt); + break; + } + next = dm_get_next_target(dmt, next, &start, &length, &target, ¶ms); if (grub_strcmp (target, "linear") != 0) @@ -920,21 +930,32 @@ const char * grub_hostdisk_os_dev_to_grub_drive (const char *os_disk, int add) { unsigned int i; + char *canon; + + canon = canonicalize_file_name (os_disk); + if (!canon) + canon = xstrdup (os_disk); for (i = 0; i < ARRAY_SIZE (map); i++) if (! map[i].device) break; - else if (strcmp (map[i].device, os_disk) == 0) - return map[i].drive; + else if (strcmp (map[i].device, canon) == 0) + { + free (canon); + return map[i].drive; + } if (!add) - return NULL; + { + free (canon); + return NULL; + } if (i == ARRAY_SIZE (map)) /* TRANSLATORS: it refers to the lack of free slots. */ grub_util_error ("%s", _("device count exceeds limit")); - map[i].device = xstrdup (os_disk); + map[i].device = canon; map[i].drive = xmalloc (sizeof ("hostdisk/") + strlen (os_disk)); strcpy (map[i].drive, "hostdisk/"); strcpy (map[i].drive + sizeof ("hostdisk/") - 1, os_disk); @@ -1433,19 +1454,13 @@ read_device_map (const char *dev_map) continue; } -#ifdef __linux__ /* On Linux, the devfs uses symbolic links horribly, and that confuses the interface very much, so use realpath to expand - symbolic links. Leave /dev/mapper/ alone, though. */ - if (strncmp (p, "/dev/mapper/", 12) != 0) - { - map[drive].device = xmalloc (PATH_MAX); - if (! realpath (p, map[drive].device)) - grub_util_error (_("failed to get canonical path of `%s'"), p); - } - else -#endif - map[drive].device = xstrdup (p); + symbolic links. */ + map[drive].device = canonicalize_file_name (p); + if (! map[drive].device) + map[drive].device = xstrdup (p); + if (!map[drive].drive) { char c; @@ -1467,6 +1482,9 @@ read_device_map (const char *dev_map) *drive_p = c; } + grub_util_info ("adding `%s' -> `%s' from device.map", map[drive].drive, + map[drive].device); + flush_initial_buffer (map[drive].device); } diff --git a/util/getroot.c b/util/getroot.c index 103a3d285..2865355e7 100644 --- a/util/getroot.c +++ b/util/getroot.c @@ -1977,13 +1977,11 @@ convert_system_partition_to_system_disk (const char *os_dev, struct stat *st, if (! node_uuid) { grub_util_info ("%s has no DM uuid", path); - node = NULL; goto devmapper_out; } if (strncmp (node_uuid, "LVM-", 4) == 0) { grub_util_info ("%s is an LVM", path); - node = NULL; goto devmapper_out; } if (strncmp (node_uuid, "mpath-", 6) == 0) @@ -1993,7 +1991,6 @@ convert_system_partition_to_system_disk (const char *os_dev, struct stat *st, grub_util_get_dm_node_linear_info. Multipath disks are not linear mappings and must be handled specially. */ grub_util_info ("%s is a multipath disk", path); - mapper_name = dm_tree_node_get_name (node); goto devmapper_out; } if (strncmp (node_uuid, "DMRAID-", 7) != 0) @@ -2015,7 +2012,6 @@ convert_system_partition_to_system_disk (const char *os_dev, struct stat *st, return ret; } - node = NULL; goto devmapper_out; } @@ -2527,7 +2523,10 @@ grub_util_biosdisk_is_present (const char *os_dev) if (stat (os_dev, &st) < 0) return 0; - return find_system_device (os_dev, &st, 1, 0) != NULL; + int ret= (find_system_device (os_dev, &st, 1, 0) != NULL); + grub_util_info ((ret ? "%s is present" : "%s is not present"), + os_dev); + return ret; } char *