From 4eff79d2f93b4f812165fd6318657a198fc06c48 Mon Sep 17 00:00:00 2001 From: Colin Watson Date: Tue, 21 Sep 2010 10:36:44 +0100 Subject: [PATCH] * grub-core/kern/emu/hostdisk.c (find_system_device): Only try to convert partition names to disk names if the new `convert' parameter is set. (grub_util_biosdisk_get_grub_dev): If opening the disk device returns GRUB_ERR_UNKNOWN_DEVICE, treat the partition device as a disk in its own right. This can happen with Xen disk images. --- ChangeLog | 10 ++++++++- grub-core/kern/emu/hostdisk.c | 38 ++++++++++++++++++++++++++++++----- 2 files changed, 42 insertions(+), 6 deletions(-) diff --git a/ChangeLog b/ChangeLog index 6f4835ca7..91e67512e 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,9 +1,17 @@ +2010-09-21 Colin Watson + + * grub-core/kern/emu/hostdisk.c (find_system_device): Only try to + convert partition names to disk names if the new `convert' parameter + is set. + (grub_util_biosdisk_get_grub_dev): If opening the disk device + returns GRUB_ERR_UNKNOWN_DEVICE, treat the partition device as a + disk in its own right. This can happen with Xen disk images. + 2010-09-21 Yves Blusseau * util/grub-editenv.c: Update strings to avoid warnings when generating grub.pot file. * util/grub-setup.c: Likewise. - 2010-09-21 Vladimir Serbinenko diff --git a/grub-core/kern/emu/hostdisk.c b/grub-core/kern/emu/hostdisk.c index e53d9d440..d38208fdc 100644 --- a/grub-core/kern/emu/hostdisk.c +++ b/grub-core/kern/emu/hostdisk.c @@ -1378,12 +1378,15 @@ device_is_wholedisk (const char *os_dev) #endif /* defined(__FreeBSD__) || defined(__FreeBSD_kernel__) */ static int -find_system_device (const char *os_dev, struct stat *st, int add) +find_system_device (const char *os_dev, struct stat *st, int convert, int add) { unsigned int i; char *os_disk; - os_disk = convert_system_partition_to_system_disk (os_dev, st); + if (convert) + os_disk = convert_system_partition_to_system_disk (os_dev, st); + else + os_disk = xstrdup (os_dev); if (! os_disk) return -1; @@ -1416,7 +1419,7 @@ grub_util_biosdisk_is_present (const char *os_dev) if (stat (os_dev, &st) < 0) return 0; - return find_system_device (os_dev, &st, 0) != -1; + return find_system_device (os_dev, &st, 1, 0) != -1; } char * @@ -1431,7 +1434,7 @@ grub_util_biosdisk_get_grub_dev (const char *os_dev) return 0; } - drive = find_system_device (os_dev, &st, 1); + drive = find_system_device (os_dev, &st, 1, 1); if (drive < 0) { grub_error (GRUB_ERR_UNKNOWN_DEVICE, @@ -1514,7 +1517,32 @@ grub_util_biosdisk_get_grub_dev (const char *os_dev) free (name); if (! disk) - return 0; + { + /* We already know that the partition exists. Given that we already + checked the device map above, we can only get + GRUB_ERR_UNKNOWN_DEVICE at this point if the disk does not exist. + This can happen on Xen, where disk images in the host can be + assigned to devices that have partition-like names in the guest + but are really more like disks. */ + if (grub_errno == GRUB_ERR_UNKNOWN_DEVICE) + { + grub_util_warn + ("disk does not exist, so falling back to partition device %s", + os_dev); + + drive = find_system_device (os_dev, &st, 0, 1); + if (drive < 0) + { + grub_error (GRUB_ERR_UNKNOWN_DEVICE, + "no mapping exists for `%s'", os_dev); + return 0; + } + + return make_device_name (drive, -1, -1); + } + else + return 0; + } partname = NULL; grub_partition_iterate (disk, find_partition);