summaryrefslogtreecommitdiff
path: root/sys-boot/grub/files/ubuntu-upstream-1.98
diff options
context:
space:
mode:
Diffstat (limited to 'sys-boot/grub/files/ubuntu-upstream-1.98')
-rw-r--r--sys-boot/grub/files/ubuntu-upstream-1.98/01_uuids_and_lvm_dont_play_along_nicely.diff14
-rw-r--r--sys-boot/grub/files/ubuntu-upstream-1.98/902_boot_blocklist_hack.diff20
-rw-r--r--sys-boot/grub/files/ubuntu-upstream-1.98/904_disable_floppies.diff28
-rw-r--r--sys-boot/grub/files/ubuntu-upstream-1.98/956_loopback_root.diff139
-rw-r--r--sys-boot/grub/files/ubuntu-upstream-1.98/957_handle_loopback.diff45
-rw-r--r--sys-boot/grub/files/ubuntu-upstream-1.98/958_linux_no_loopmount.diff20
-rw-r--r--sys-boot/grub/files/ubuntu-upstream-1.98/960_raid_virtio.diff158
-rw-r--r--sys-boot/grub/files/ubuntu-upstream-1.98/961_dmraid_probe.diff650
-rw-r--r--sys-boot/grub/files/ubuntu-upstream-1.98/962_no_device_map.diff112
-rw-r--r--sys-boot/grub/files/ubuntu-upstream-1.98/968_hostdisk_speedup.diff310
-rw-r--r--sys-boot/grub/files/ubuntu-upstream-1.98/969_lvm_raid_probe.diff227
-rw-r--r--sys-boot/grub/files/ubuntu-upstream-1.98/970_fix_locale_installation.diff55
-rw-r--r--sys-boot/grub/files/ubuntu-upstream-1.98/971_langpacks.diff30
-rw-r--r--sys-boot/grub/files/ubuntu-upstream-1.98/974_drive_probe.diff23
-rw-r--r--sys-boot/grub/files/ubuntu-upstream-1.98/975_hostdisk_hd.diff114
15 files changed, 1945 insertions, 0 deletions
diff --git a/sys-boot/grub/files/ubuntu-upstream-1.98/01_uuids_and_lvm_dont_play_along_nicely.diff b/sys-boot/grub/files/ubuntu-upstream-1.98/01_uuids_and_lvm_dont_play_along_nicely.diff
new file mode 100644
index 00000000..c997b845
--- /dev/null
+++ b/sys-boot/grub/files/ubuntu-upstream-1.98/01_uuids_and_lvm_dont_play_along_nicely.diff
@@ -0,0 +1,14 @@
+diff --git a/util/grub.d/10_linux.in b/util/grub.d/10_linux.in
+index c2da413..cbd9d6b 100644
+--- a/util/grub.d/10_linux.in
++++ b/util/grub.d/10_linux.in
+@@ -36,7 +36,8 @@ case ${GRUB_DEVICE} in
+ esac
+
+ if [ "x${GRUB_DEVICE_UUID}" = "x" ] || [ "x${GRUB_DISABLE_LINUX_UUID}" = "xtrue" ] \
+- || ! test -e "/dev/disk/by-uuid/${GRUB_DEVICE_UUID}" ; then
++ || ! test -e "/dev/disk/by-uuid/${GRUB_DEVICE_UUID}" \
++ || [ "`grub-probe -t abstraction --device ${GRUB_DEVICE} | sed -e 's,.*\(lvm\).*,\1,'`" = "lvm" ] ; then
+ LINUX_ROOT_DEVICE=${GRUB_DEVICE}
+ else
+ LINUX_ROOT_DEVICE=UUID=${GRUB_DEVICE_UUID}
diff --git a/sys-boot/grub/files/ubuntu-upstream-1.98/902_boot_blocklist_hack.diff b/sys-boot/grub/files/ubuntu-upstream-1.98/902_boot_blocklist_hack.diff
new file mode 100644
index 00000000..63caf45e
--- /dev/null
+++ b/sys-boot/grub/files/ubuntu-upstream-1.98/902_boot_blocklist_hack.diff
@@ -0,0 +1,20 @@
+Index: util/i386/pc/grub-setup.c
+===================================================================
+--- util/i386/pc/grub-setup.c (revision 1836)
++++ util/i386/pc/grub-setup.c (working copy)
+@@ -383,6 +383,15 @@
+ grub_disk_cache_invalidate_all ();
+
+ file = grub_file_open (core_path_dev);
++
++ if (grub_errno == GRUB_ERR_FILE_NOT_FOUND)
++ {
++ /* Clean the previous grub_errno */
++ grub_errno = GRUB_ERR_NONE;
++ strcpy (core_path_dev, "/grub/core.img");
++ file = grub_file_open (core_path_dev);
++ }
++
+ if (file)
+ {
+ if (grub_file_size (file) != core_size)
diff --git a/sys-boot/grub/files/ubuntu-upstream-1.98/904_disable_floppies.diff b/sys-boot/grub/files/ubuntu-upstream-1.98/904_disable_floppies.diff
new file mode 100644
index 00000000..66a41cdc
--- /dev/null
+++ b/sys-boot/grub/files/ubuntu-upstream-1.98/904_disable_floppies.diff
@@ -0,0 +1,28 @@
+
+Author: Robert Millan
+
+An ugly kludge. Should this be merged upstream?
+
+Index: util/hostdisk.c
+===================================================================
+--- util/hostdisk.c (revision 1832)
++++ util/hostdisk.c (working copy)
+@@ -544,6 +544,18 @@
+ continue;
+ }
+
++ if (! strncmp (p, "/dev/fd", sizeof ("/dev/fd") - 1))
++ {
++ char *q = p + sizeof ("/dev/fd") - 1;
++ if (*q >= '0' && *q <= '9')
++ {
++ free (map[drive].drive);
++ map[drive].drive = NULL;
++ grub_util_info ("`%s' looks like a floppy drive, skipping", p);
++ continue;
++ }
++ }
++
+ #ifdef __linux__
+ /* On Linux, the devfs uses symbolic links horribly, and that
+ confuses the interface very much, so use realpath to expand
diff --git a/sys-boot/grub/files/ubuntu-upstream-1.98/956_loopback_root.diff b/sys-boot/grub/files/ubuntu-upstream-1.98/956_loopback_root.diff
new file mode 100644
index 00000000..ce54872e
--- /dev/null
+++ b/sys-boot/grub/files/ubuntu-upstream-1.98/956_loopback_root.diff
@@ -0,0 +1,139 @@
+Upstream: http://lists.gnu.org/archive/html/grub-devel/2009-09/msg00210.html
+Description: If you set root after running loopback, any attempts to open
+ files on the loopback device resolve the loopback file name relative to the
+ *new* root, not the root at the time loopback was invoked, and so the above
+ recurses until it runs out of stack. This causes problems for Wubi. I think
+ it's fairly clear that only the root that was in place when you ran
+ loopback should be relevant to the loopback file name.
+
+diff -Nur -x '*.orig' -x '*~' grub2-1.97~beta2/disk/loopback.c grub2-1.97~beta2.new/disk/loopback.c
+--- grub2-1.97~beta2/disk/loopback.c 2009-06-10 22:04:23.000000000 +0100
++++ grub2-1.97~beta2.new/disk/loopback.c 2009-09-10 21:42:56.000000000 +0100
+@@ -28,6 +28,7 @@
+ {
+ char *devname;
+ char *filename;
++ grub_file_t file;
+ int has_partitions;
+ struct grub_loopback *next;
+ };
+@@ -61,6 +62,7 @@
+ /* Remove the device from the list. */
+ *prev = dev->next;
+
++ grub_file_close (dev->file);
+ grub_free (dev->devname);
+ grub_free (dev->filename);
+ grub_free (dev);
+@@ -90,9 +92,6 @@
+ if (! file)
+ return grub_errno;
+
+- /* Close the file, the only reason for opening it is validation. */
+- grub_file_close (file);
+-
+ /* First try to replace the old device. */
+ for (newdev = loopback_list; newdev; newdev = newdev->next)
+ if (grub_strcmp (newdev->devname, args[0]) == 0)
+@@ -102,10 +101,12 @@
+ {
+ char *newname = grub_strdup (args[1]);
+ if (! newname)
+- return grub_errno;
++ goto fail;
+
+ grub_free (newdev->filename);
+ newdev->filename = newname;
++ grub_file_close (newdev->file);
++ newdev->file = file;
+
+ /* Set has_partitions when `--partitions' was used. */
+ newdev->has_partitions = state[1].set;
+@@ -116,13 +117,13 @@
+ /* Unable to replace it, make a new entry. */
+ newdev = grub_malloc (sizeof (struct grub_loopback));
+ if (! newdev)
+- return grub_errno;
++ goto fail;
+
+ newdev->devname = grub_strdup (args[0]);
+ if (! newdev->devname)
+ {
+ grub_free (newdev);
+- return grub_errno;
++ goto fail;
+ }
+
+ newdev->filename = grub_strdup (args[1]);
+@@ -130,9 +131,11 @@
+ {
+ grub_free (newdev->devname);
+ grub_free (newdev);
+- return grub_errno;
++ goto fail;
+ }
+
++ newdev->file = file;
++
+ /* Set has_partitions when `--partitions' was used. */
+ newdev->has_partitions = state[1].set;
+
+@@ -141,6 +144,10 @@
+ loopback_list = newdev;
+
+ return 0;
++
++fail:
++ grub_file_close (file);
++ return grub_errno;
+ }
+
+
+@@ -159,7 +166,6 @@
+ static grub_err_t
+ grub_loopback_open (const char *name, grub_disk_t disk)
+ {
+- grub_file_t file;
+ struct grub_loopback *dev;
+
+ for (dev = loopback_list; dev; dev = dev->next)
+@@ -169,29 +175,17 @@
+ if (! dev)
+ return grub_error (GRUB_ERR_UNKNOWN_DEVICE, "Can't open device");
+
+- file = grub_file_open (dev->filename);
+- if (! file)
+- return grub_errno;
+-
+ /* Use the filesize for the disk size, round up to a complete sector. */
+- disk->total_sectors = ((file->size + GRUB_DISK_SECTOR_SIZE - 1)
++ disk->total_sectors = ((dev->file->size + GRUB_DISK_SECTOR_SIZE - 1)
+ / GRUB_DISK_SECTOR_SIZE);
+ disk->id = (unsigned long) dev;
+
+ disk->has_partitions = dev->has_partitions;
+- disk->data = file;
++ disk->data = dev->file;
+
+ return 0;
+ }
+
+-static void
+-grub_loopback_close (grub_disk_t disk)
+-{
+- grub_file_t file = (grub_file_t) disk->data;
+-
+- grub_file_close (file);
+-}
+-
+ static grub_err_t
+ grub_loopback_read (grub_disk_t disk, grub_disk_addr_t sector,
+ grub_size_t size, char *buf)
+@@ -233,7 +227,6 @@
+ .id = GRUB_DISK_DEVICE_LOOPBACK_ID,
+ .iterate = grub_loopback_iterate,
+ .open = grub_loopback_open,
+- .close = grub_loopback_close,
+ .read = grub_loopback_read,
+ .write = grub_loopback_write,
+ .next = 0
diff --git a/sys-boot/grub/files/ubuntu-upstream-1.98/957_handle_loopback.diff b/sys-boot/grub/files/ubuntu-upstream-1.98/957_handle_loopback.diff
new file mode 100644
index 00000000..0ee868fd
--- /dev/null
+++ b/sys-boot/grub/files/ubuntu-upstream-1.98/957_handle_loopback.diff
@@ -0,0 +1,45 @@
+Ubuntu: needed for Wubi
+Description: Change prepare_grub_to_access_device to handle filesystems
+ loop-mounted on file images.
+UbuntuSpecific: Not inherently. losetup and /proc/mounts are Linux-specific,
+ though, so we might need to refine this before sending it upstream.
+
+diff -Nur -x '*.orig' -x '*~' grub2-1.97~beta3/util/grub-mkconfig_lib.in grub2-1.97~beta3.new/util/grub-mkconfig_lib.in
+--- grub2-1.97~beta3/util/grub-mkconfig_lib.in 2009-09-15 00:23:50.000000000 +0100
++++ grub2-1.97~beta3.new/util/grub-mkconfig_lib.in 2009-09-15 00:31:31.000000000 +0100
+@@ -142,6 +142,20 @@
+ {
+ device=$1
+
++ loop_file=
++ case ${device} in
++ /dev/loop/*|/dev/loop[0-9])
++ loop_file=`losetup ${device} | sed -e "s/^[^(]*(\([^)]\+\)).*/\1/"`
++ case $loop_file in
++ /dev/*) ;;
++ *)
++ loop_device=${device}
++ device=`${grub_probe} --target=device "${loop_file}"`
++ ;;
++ esac
++ ;;
++ esac
++
+ # Abstraction modules aren't auto-loaded.
+ abstraction="`${grub_probe} --device ${device} --target=abstraction`"
+ for module in ${abstraction} ; do
+@@ -159,6 +173,14 @@
+ if fs_uuid="`${grub_probe} --device ${device} --target=fs_uuid 2> /dev/null`" ; then
+ echo "search --no-floppy --fs-uuid --set ${fs_uuid}"
+ fi
++
++ if [ "x${loop_file}" != x ]; then
++ loop_mountpoint="$(awk '"'${loop_file}'" ~ "^"$2 && $2 != "/" { print $2 }' /proc/mounts | tail -n1)"
++ if [ "x${loop_mountpoint}" != x ]; then
++ echo "loopback loop0 ${loop_file#$loop_mountpoint}"
++ echo "set root=(loop0)"
++ fi
++ fi
+ }
+
+ grub_file_is_not_garbage ()
diff --git a/sys-boot/grub/files/ubuntu-upstream-1.98/958_linux_no_loopmount.diff b/sys-boot/grub/files/ubuntu-upstream-1.98/958_linux_no_loopmount.diff
new file mode 100644
index 00000000..9e0dfda9
--- /dev/null
+++ b/sys-boot/grub/files/ubuntu-upstream-1.98/958_linux_no_loopmount.diff
@@ -0,0 +1,20 @@
+Ubuntu: needed for Wubi
+Description: Ignore devices loop-mounted from files in 10_linux.
+UbuntuSpecific: Not inherently, but perhaps we should integrate 10_lupin
+ properly instead.
+
+diff -Nur -x '*.orig' -x '*~' grub2-1.97~beta3/util/grub.d/10_linux.in grub2-1.97~beta3.new/util/grub.d/10_linux.in
+--- grub2-1.97~beta3/util/grub.d/10_linux.in 2009-09-16 17:41:06.000000000 +0100
++++ grub2-1.97~beta3.new/util/grub.d/10_linux.in 2009-09-16 17:44:52.000000000 +0100
+@@ -32,6 +32,11 @@
+ case ${GRUB_DEVICE} in
+ /dev/loop/*|/dev/loop[0-9])
+ GRUB_DEVICE=`losetup ${GRUB_DEVICE} | sed -e "s/^[^(]*(\([^)]\+\)).*/\1/"`
++ # We can't cope with devices loop-mounted from files here.
++ case ${GRUB_DEVICE} in
++ /dev/*) ;;
++ *) exit 0 ;;
++ esac
+ ;;
+ esac
+
diff --git a/sys-boot/grub/files/ubuntu-upstream-1.98/960_raid_virtio.diff b/sys-boot/grub/files/ubuntu-upstream-1.98/960_raid_virtio.diff
new file mode 100644
index 00000000..3b060ba0
--- /dev/null
+++ b/sys-boot/grub/files/ubuntu-upstream-1.98/960_raid_virtio.diff
@@ -0,0 +1,158 @@
+diff -Nur -x '*.orig' -x '*~' grub2/include/grub/util/getroot.h grub2.new/include/grub/util/getroot.h
+--- grub2/include/grub/util/getroot.h 2009-11-29 18:42:14.000000000 -0800
++++ grub2.new/include/grub/util/getroot.h 2010-02-03 14:38:02.000000000 -0800
+@@ -19,12 +19,15 @@
+ #ifndef GRUB_UTIL_GETROOT_HEADER
+ #define GRUB_UTIL_GETROOT_HEADER 1
+
++#include <sys/types.h>
++
+ enum grub_dev_abstraction_types {
+ GRUB_DEV_ABSTRACTION_NONE,
+ GRUB_DEV_ABSTRACTION_LVM,
+ GRUB_DEV_ABSTRACTION_RAID,
+ };
+
++char *grub_find_device (const char *dir, dev_t dev);
+ char *grub_guess_root_device (const char *dir);
+ char *grub_get_prefix (const char *dir);
+ int grub_util_get_dev_abstraction (const char *os_dev);
+diff -Nur -x '*.orig' -x '*~' grub2/util/getroot.c grub2.new/util/getroot.c
+--- grub2/util/getroot.c 2010-02-01 14:33:16.000000000 -0800
++++ grub2.new/util/getroot.c 2010-02-03 14:38:02.000000000 -0800
+@@ -178,8 +178,8 @@
+
+ #ifdef __MINGW32__
+
+-static char *
+-find_root_device (const char *dir __attribute__ ((unused)),
++char *
++grub_find_device (const char *dir __attribute__ ((unused)),
+ dev_t dev __attribute__ ((unused)))
+ {
+ return 0;
+@@ -187,13 +187,22 @@
+
+ #elif ! defined(__CYGWIN__)
+
+-static char *
+-find_root_device (const char *dir, dev_t dev)
++char *
++grub_find_device (const char *dir, dev_t dev)
+ {
+ DIR *dp;
+ char *saved_cwd;
+ struct dirent *ent;
+
++ if (! dir)
++ {
++#ifdef __CYGWIN__
++ return NULL;
++#else
++ dir = "/dev";
++#endif
++ }
++
+ dp = opendir (dir);
+ if (! dp)
+ return 0;
+@@ -231,7 +240,7 @@
+ /* Find it recursively. */
+ char *res;
+
+- res = find_root_device (ent->d_name, dev);
++ res = grub_find_device (ent->d_name, dev);
+
+ if (res)
+ {
+@@ -334,8 +343,8 @@
+ return serial;
+ }
+
+-static char *
+-find_cygwin_root_device (const char *path, dev_t dev)
++char *
++grub_find_device (const char *path, dev_t dev)
+ {
+ /* No root device for /cygdrive. */
+ if (dev == (DEV_CYGDRIVE_MAJOR << 16))
+@@ -356,7 +365,7 @@
+
+ /* Cygwin returns the partition serial number in stat.st_dev.
+ This is never identical to the device number of the emulated
+- /dev/sdXN device, so above find_root_device () does not work.
++ /dev/sdXN device, so above grub_find_device () does not work.
+ Search the partition with the same serial in boot sector instead. */
+ char devpath[sizeof ("/dev/sda15") + 13]; /* Size + Paranoia. */
+ int d;
+@@ -449,12 +458,12 @@
+
+ #ifdef __CYGWIN__
+ /* Cygwin specific function. */
+- os_dev = find_cygwin_root_device (dir, st.st_dev);
++ os_dev = grub_find_device (dir, st.st_dev);
+
+ #else
+
+ /* This might be truly slow, but is there any better way? */
+- os_dev = find_root_device ("/dev", st.st_dev);
++ os_dev = grub_find_device ("/dev", st.st_dev);
+ #endif
+ #endif /* !__GNU__ */
+
+diff -Nur -x '*.orig' -x '*~' grub2/util/raid.c grub2.new/util/raid.c
+--- grub2/util/raid.c 2010-02-01 14:33:15.000000000 -0800
++++ grub2.new/util/raid.c 2010-02-03 14:39:38.000000000 -0800
+@@ -21,40 +21,19 @@
+ #ifdef __linux__
+ #include <grub/util/misc.h>
+ #include <grub/util/raid.h>
++#include <grub/util/getroot.h>
+
+ #include <string.h>
+ #include <fcntl.h>
+ #include <sys/ioctl.h>
+ #include <errno.h>
++#include <sys/types.h>
+
+ #include <linux/types.h>
+ #include <linux/major.h>
+ #include <linux/raid/md_p.h>
+ #include <linux/raid/md_u.h>
+
+-static char *
+-grub_util_getdiskname (int major, int minor)
+-{
+- char *name = xmalloc (15);
+-
+- if (major == LOOP_MAJOR)
+- sprintf (name, "/dev/loop%d", minor);
+- else if (major == IDE0_MAJOR)
+- sprintf (name, "/dev/hd%c", 'a' + minor / 64);
+- else if (major == IDE1_MAJOR)
+- sprintf (name, "/dev/hd%c", 'c' + minor / 64);
+- else if (major == IDE2_MAJOR)
+- sprintf (name, "/dev/hd%c", 'e' + minor / 64);
+- else if (major == IDE3_MAJOR)
+- sprintf (name, "/dev/hd%c", 'g' + minor / 64);
+- else if (major == SCSI_DISK0_MAJOR)
+- sprintf (name, "/dev/sd%c", 'a' + minor / 16);
+- else
+- grub_util_error ("unknown device number: %d, %d", major, minor);
+-
+- return name;
+-}
+-
+ char **
+ grub_util_raid_getmembers (char *name)
+ {
+@@ -99,7 +78,8 @@
+
+ if (disk.state & (1 << MD_DISK_ACTIVE))
+ {
+- devicelist[j] = grub_util_getdiskname (disk.major, disk.minor);
++ devicelist[j] = grub_find_device (NULL,
++ makedev (disk.major, disk.minor));
+ j++;
+ }
+ }
diff --git a/sys-boot/grub/files/ubuntu-upstream-1.98/961_dmraid_probe.diff b/sys-boot/grub/files/ubuntu-upstream-1.98/961_dmraid_probe.diff
new file mode 100644
index 00000000..8bc94707
--- /dev/null
+++ b/sys-boot/grub/files/ubuntu-upstream-1.98/961_dmraid_probe.diff
@@ -0,0 +1,650 @@
+Description: Add DM-RAID probing support.
+Upstream: Maintained in an upstream branch,
+ sftp://bzr.sv.gnu.org/srv/bzr/grub/branches/dmraid-probe/; see
+ http://lists.gnu.org/archive/html/grub-devel/2010-01/msg00345.html
+
+diff -Nur -x '*.orig' -x '*~' grub2/ChangeLog.dmraid-probe grub2.new/ChangeLog.dmraid-probe
+--- grub2/ChangeLog.dmraid-probe 1969-12-31 16:00:00.000000000 -0800
++++ grub2.new/ChangeLog.dmraid-probe 2010-02-06 10:33:54.000000000 -0800
+@@ -0,0 +1,26 @@
++2010-01-31 Colin Watson <cjwatson@ubuntu.com>
++
++ * configure.ac: Check for Linux device-mapper support.
++
++ * util/hostdisk.c (device_is_mapped): New function.
++ (find_partition_start): New function, partly broken out from
++ linux_find_partition and grub_util_biosdisk_get_grub_dev but with
++ device-mapper support added.
++ (linux_find_partition): Use find_partition_start.
++ (convert_system_partition_to_system_disk): Add `st' argument.
++ Support Linux /dev/mapper/* devices if device-mapper support is
++ available; only DM-RAID devices are understood at present.
++ (find_system_device): Add `st' argument. Pass it to
++ convert_system_partition_to_system_disk.
++ (grub_util_biosdisk_get_grub_dev): Pass stat result to
++ find_system_device and convert_system_partition_to_system_disk. Use
++ find_partition_start.
++
++ * conf/common.rmk (grub_mkdevicemap_SOURCES): Add kern/env.c,
++ kern/err.c, kern/list.c, and kern/misc.c.
++ * util/deviceiter.c [__linux__]: Define MINOR.
++ (grub_util_iterate_devices): Add support for DM-RAID disk devices.
++ * util/mkdevicemap.c (grub_putchar): New function.
++ (grub_getkey): New function.
++ (grub_refresh): New function.
++ (main): Set debug=all if -v -v is used.
+diff -Nur -x '*.orig' -x '*~' grub2/conf/common.rmk grub2.new/conf/common.rmk
+--- grub2/conf/common.rmk 2010-02-06 10:32:37.000000000 -0800
++++ grub2.new/conf/common.rmk 2010-02-06 10:33:54.000000000 -0800
+@@ -3,7 +3,8 @@
+ sbin_UTILITIES += grub-mkdevicemap
+ grub_mkdevicemap_SOURCES = gnulib/progname.c util/grub-mkdevicemap.c \
+ util/deviceiter.c \
+- util/misc.c
++ util/misc.c \
++ kern/env.c kern/err.c kern/list.c kern/misc.c
+
+ ifeq ($(target_cpu)-$(platform), sparc64-ieee1275)
+ grub_mkdevicemap_SOURCES += util/ieee1275/ofpath.c util/ieee1275/devicemap.c
+diff -Nur -x '*.orig' -x '*~' grub2/configure.ac grub2.new/configure.ac
+--- grub2/configure.ac 2010-02-06 10:32:49.000000000 -0800
++++ grub2.new/configure.ac 2010-02-06 10:33:54.000000000 -0800
+@@ -660,6 +660,22 @@
+ AC_SUBST([freetype_cflags])
+ AC_SUBST([freetype_libs])
+
++AC_ARG_ENABLE([device-mapper],
++ [AS_HELP_STRING([--enable-device-mapper],
++ [enable Linux device-mapper support (default=guessed)])])
++if test x"$enable_device_mapper" = xno ; then
++ device_mapper_excuse="explicitly disabled"
++fi
++
++if test x"$device_mapper_excuse" = x ; then
++ # Check for device-mapper library.
++ AC_CHECK_LIB([devmapper], [dm_task_create],
++ [LDFLAGS="$LDFLAGS -ldevmapper"
++ AC_DEFINE([HAVE_DEVICE_MAPPER], [1],
++ [Define to 1 if you have the devmapper library.])],
++ [device_mapper_excuse="need devmapper library"])
++fi
++
+ AC_SUBST(ASFLAGS)
+
+ # Output files.
+diff -Nur -x '*.orig' -x '*~' grub2/util/deviceiter.c grub2.new/util/deviceiter.c
+--- grub2/util/deviceiter.c 2010-02-06 10:32:37.000000000 -0800
++++ grub2.new/util/deviceiter.c 2010-02-06 10:33:54.000000000 -0800
+@@ -31,6 +31,8 @@
+
+ #include <grub/util/misc.h>
+ #include <grub/util/deviceiter.h>
++#include <grub/list.h>
++#include <grub/misc.h>
+
+ #ifdef __linux__
+ # if !defined(__GLIBC__) || \
+@@ -62,12 +64,23 @@
+ | ((unsigned int) (__dev >> 32) & ~0xfff); \
+ })
+ # endif /* ! MAJOR */
++# ifndef MINOR
++# define MINOR(dev) \
++ ({ \
++ unsigned long long __dev = (dev); \
++ (unsigned) (__dev & 0xff) | ((unsigned int) (__dev >> 12) & ~0xff); \
++ })
++# endif /* ! MINOR */
+ # ifndef CDROM_GET_CAPABILITY
+ # define CDROM_GET_CAPABILITY 0x5331 /* get capabilities */
+ # endif /* ! CDROM_GET_CAPABILITY */
+ # ifndef BLKGETSIZE
+ # define BLKGETSIZE _IO(0x12,96) /* return device size */
+ # endif /* ! BLKGETSIZE */
++
++#ifdef HAVE_DEVICE_MAPPER
++# include <libdevmapper.h>
++#endif
+ #endif /* __linux__ */
+
+ /* Use __FreeBSD_kernel__ instead of __FreeBSD__ for compatibility with
+@@ -411,6 +424,16 @@
+ return 1;
+ }
+
++#ifdef __linux__
++# ifdef HAVE_DEVICE_MAPPER
++struct dmraid_seen
++{
++ struct dmraid_seen *next;
++ const char *name;
++};
++# endif /* HAVE_DEVICE_MAPPER */
++#endif /* __linux__ */
++
+ void
+ grub_util_iterate_devices (int NESTED_FUNC_ATTR (*hook) (const char *, int),
+ int floppy_disks)
+@@ -643,6 +666,123 @@
+ return;
+ }
+ }
++
++# ifdef HAVE_DEVICE_MAPPER
++# define dmraid_check(cond, ...) \
++ if (! (cond)) \
++ { \
++ grub_dprintf ("deviceiter", __VA_ARGS__); \
++ goto dmraid_end; \
++ }
++
++ /* DM-RAID. */
++ {
++ struct dm_tree *tree = NULL;
++ struct dm_task *task = NULL;
++ struct dm_names *names = NULL;
++ unsigned int next = 0;
++ void *top_handle, *second_handle;
++ struct dm_tree_node *root, *top, *second;
++ struct dmraid_seen *seen = NULL;
++
++ /* Build DM tree for all devices. */
++ tree = dm_tree_create ();
++ dmraid_check (tree, "dm_tree_create failed\n");
++ task = dm_task_create (DM_DEVICE_LIST);
++ dmraid_check (task, "dm_task_create failed\n");
++ dmraid_check (dm_task_run (task), "dm_task_run failed\n");
++ names = dm_task_get_names (task);
++ dmraid_check (names, "dm_task_get_names failed\n");
++ dmraid_check (names->dev, "No DM devices found\n");
++ do
++ {
++ names = (void *) names + next;
++ dmraid_check (dm_tree_add_dev (tree, MAJOR (names->dev),
++ MINOR (names->dev)),
++ "dm_tree_add_dev (%s) failed\n", names->name);
++ next = names->next;
++ }
++ while (next);
++
++ /* Walk the second-level children of the inverted tree; that is, devices
++ which are directly composed of non-DM devices such as hard disks.
++ This class includes all DM-RAID disks and excludes all DM-RAID
++ partitions. */
++ root = dm_tree_find_node (tree, 0, 0);
++ top_handle = NULL;
++ top = dm_tree_next_child (&top_handle, root, 1);
++ while (top)
++ {
++ second_handle = NULL;
++ second = dm_tree_next_child (&second_handle, top, 1);
++ while (second)
++ {
++ const char *node_name, *node_uuid;
++ char *name;
++ struct dmraid_seen *seen_elt;
++
++ node_name = dm_tree_node_get_name (second);
++ dmraid_check (node_name, "dm_tree_node_get_name failed\n");
++ node_uuid = dm_tree_node_get_uuid (second);
++ dmraid_check (node_uuid, "dm_tree_node_get_uuid failed\n");
++ if (strncmp (node_uuid, "DMRAID-", 7) != 0)
++ {
++ grub_dprintf ("deviceiter", "%s is not DM-RAID\n", node_name);
++ goto dmraid_next_child;
++ }
++
++ /* Have we already seen this node? There are typically very few
++ DM-RAID disks, so a list should be fast enough. */
++ if (grub_named_list_find (GRUB_AS_NAMED_LIST (seen), node_name))
++ {
++ grub_dprintf ("deviceiter", "Already seen DM device %s\n",
++ node_name);
++ goto dmraid_next_child;
++ }
++
++ name = xasprintf ("/dev/mapper/%s", node_name);
++ if (check_device (name))
++ {
++ if (hook (name, 0))
++ {
++ free (name);
++ while (seen)
++ {
++ struct dmraid_seen *seen_elt =
++ grub_list_pop (GRUB_AS_LIST_P (&seen));
++ free (seen_elt);
++ }
++ if (task)
++ dm_task_destroy (task);
++ if (tree)
++ dm_tree_free (tree);
++ return;
++ }
++ }
++ free (name);
++
++ seen_elt = xmalloc (sizeof *seen_elt);
++ seen_elt->name = node_name;
++ grub_list_push (GRUB_AS_LIST_P (&seen), GRUB_AS_LIST (seen_elt));
++
++dmraid_next_child:
++ second = dm_tree_next_child (&second_handle, top, 1);
++ }
++ top = dm_tree_next_child (&top_handle, root, 1);
++ }
++
++dmraid_end:
++ while (seen)
++ {
++ struct dmraid_seen *seen_elt = grub_list_pop (GRUB_AS_LIST_P (&seen));
++ free (seen_elt);
++ }
++ if (task)
++ dm_task_destroy (task);
++ if (tree)
++ dm_tree_free (tree);
++ }
++# endif /* HAVE_DEVICE_MAPPER */
+ #endif /* __linux__ */
+ }
+
+diff -Nur -x '*.orig' -x '*~' grub2/util/grub-mkdevicemap.c grub2.new/util/grub-mkdevicemap.c
+--- grub2/util/grub-mkdevicemap.c 2010-02-06 10:32:37.000000000 -0800
++++ grub2.new/util/grub-mkdevicemap.c 2010-02-06 10:33:54.000000000 -0800
+@@ -31,6 +31,7 @@
+
+ #include <grub/util/misc.h>
+ #include <grub/util/deviceiter.h>
++#include <grub/env.h>
+ #include <grub/i18n.h>
+
+ #define _GNU_SOURCE 1
+@@ -38,6 +39,24 @@
+
+ #include "progname.h"
+
++void
++grub_putchar (int c)
++{
++ putchar (c);
++}
++
++int
++grub_getkey (void)
++{
++ return -1;
++}
++
++void
++grub_refresh (void)
++{
++ fflush (stdout);
++}
++
+ static void
+ make_device_map (const char *device_map, int floppy_disks)
+ {
+@@ -158,6 +177,9 @@
+ }
+ }
+
++ if (verbosity > 1)
++ grub_env_set ("debug", "all");
++
+ make_device_map (dev_map ? : DEFAULT_DEVICE_MAP, floppy_disks);
+
+ free (dev_map);
+diff -Nur -x '*.orig' -x '*~' grub2/util/hostdisk.c grub2.new/util/hostdisk.c
+--- grub2/util/hostdisk.c 2010-02-06 10:32:55.000000000 -0800
++++ grub2.new/util/hostdisk.c 2010-02-06 10:33:54.000000000 -0800
+@@ -97,6 +97,10 @@
+ # include <sys/disk.h>
+ #endif
+
++#ifdef HAVE_DEVICE_MAPPER
++# include <libdevmapper.h>
++#endif
++
+ struct
+ {
+ char *drive;
+@@ -253,6 +257,115 @@
+ return GRUB_ERR_NONE;
+ }
+
++#ifdef HAVE_DEVICE_MAPPER
++static int
++device_is_mapped (const char *dev)
++{
++ struct stat st;
++
++ if (stat (dev, &st) < 0)
++ return 0;
++
++ return dm_is_dm_major (major (st.st_rdev));
++}
++#endif /* HAVE_DEVICE_MAPPER */
++
++#if defined(__linux__) || defined(__CYGWIN__)
++static grub_disk_addr_t
++find_partition_start (const char *dev)
++{
++ int fd;
++ struct hd_geometry hdg;
++
++#ifdef HAVE_DEVICE_MAPPER
++ if (device_is_mapped (dev)) {
++ struct dm_task *task = NULL;
++ grub_uint64_t start, length;
++ char *target_type, *params, *space;
++ grub_disk_addr_t partition_start;
++
++ /* If any device-mapper operation fails, we fall back silently to
++ HDIO_GETGEO. */
++ task = dm_task_create (DM_DEVICE_TABLE);
++ if (! task)
++ {
++ grub_dprintf ("hostdisk", "dm_task_create failed\n");
++ goto devmapper_fail;
++ }
++
++ if (! dm_task_set_name (task, dev))
++ {
++ grub_dprintf ("hostdisk", "dm_task_set_name failed\n");
++ goto devmapper_fail;
++ }
++
++ if (! dm_task_run (task))
++ {
++ grub_dprintf ("hostdisk", "dm_task_run failed\n");
++ goto devmapper_fail;
++ }
++
++ dm_get_next_target (task, NULL, &start, &length, &target_type, &params);
++ if (! target_type)
++ {
++ grub_dprintf ("hostdisk", "no dm target\n");
++ goto devmapper_fail;
++ }
++ if (strcmp (target_type, "linear") != 0)
++ {
++ grub_dprintf ("hostdisk", "ignoring dm target %s (not linear)\n",
++ target_type);
++ goto devmapper_fail;
++ }
++ if (! params)
++ {
++ grub_dprintf ("hostdisk", "no dm params\n");
++ goto devmapper_fail;
++ }
++
++ /* The params string for a linear target looks like this:
++ DEVICE-NAME START-SECTOR
++ Parse this out. */
++ space = strchr (params, ' ');
++ if (! space)
++ goto devmapper_fail;
++ errno = 0;
++ partition_start = strtoull (space + 1, NULL, 10);
++ if (errno == 0)
++ {
++ grub_dprintf ("hostdisk", "dm %s starts at %llu\n",
++ dev, partition_start);
++ dm_task_destroy (task);
++ return partition_start;
++ }
++
++devmapper_fail:
++ if (task)
++ dm_task_destroy (task);
++ }
++#endif /* HAVE_DEVICE_MAPPER */
++
++ fd = open (dev, O_RDONLY);
++ if (fd == -1)
++ {
++ grub_error (GRUB_ERR_BAD_DEVICE, "cannot open `%s' while attempting to get disk geometry", dev);
++ return 0;
++ }
++
++ if (ioctl (fd, HDIO_GETGEO, &hdg))
++ {
++ grub_error (GRUB_ERR_BAD_DEVICE,
++ "cannot get geometry of `%s'", dev);
++ close (fd);
++ return 0;
++ }
++
++ close (fd);
++
++ return hdg.start;
++}
++#endif /* __linux__ || __CYGWIN__ */
++
+ #ifdef __linux__
+ static int
+ linux_find_partition (char *dev, unsigned long sector)
+@@ -284,22 +397,20 @@
+ for (i = 1; i < 10000; i++)
+ {
+ int fd;
+- struct hd_geometry hdg;
++ grub_disk_addr_t start;
+
+ sprintf (p, format, i);
++
+ fd = open (real_dev, O_RDONLY);
+ if (fd == -1)
+ return 0;
+-
+- if (ioctl (fd, HDIO_GETGEO, &hdg))
+- {
+- close (fd);
+- return 0;
+- }
+-
+ close (fd);
+
+- if (hdg.start == sector)
++ start = find_partition_start (real_dev);
++ /* We don't care about errors here. */
++ grub_errno = GRUB_ERR_NONE;
++
++ if (start == sector)
+ {
+ strcpy (dev, real_dev);
+ return 1;
+@@ -711,7 +822,7 @@
+ }
+
+ static char *
+-convert_system_partition_to_system_disk (const char *os_dev)
++convert_system_partition_to_system_disk (const char *os_dev, struct stat *st)
+ {
+ #if defined(__linux__)
+ char *path = xmalloc (PATH_MAX);
+@@ -829,6 +940,96 @@
+ p[4] = '\0';
+ return path;
+ }
++
++#ifdef HAVE_DEVICE_MAPPER
++ /* If this is a DM-RAID device. */
++ if ((strncmp ("mapper/", p, 7) == 0))
++ {
++ static struct dm_tree *tree = NULL;
++ uint32_t maj, min;
++ struct dm_tree_node *node, *child;
++ void *handle;
++ const char *node_uuid, *mapper_name, *child_uuid, *child_name;
++
++ if (! tree)
++ tree = dm_tree_create ();
++
++ if (! tree)
++ {
++ grub_dprintf ("hostdisk", "dm_tree_create failed\n");
++ return NULL;
++ }
++
++ maj = major (st->st_rdev);
++ min = minor (st->st_rdev);
++ if (! dm_tree_add_dev (tree, maj, min))
++ {
++ grub_dprintf ("hostdisk", "dm_tree_add_dev failed\n");
++ return NULL;
++ }
++
++ node = dm_tree_find_node (tree, maj, min);
++ if (! node)
++ {
++ grub_dprintf ("hostdisk", "dm_tree_find_node failed\n");
++ return NULL;
++ }
++ node_uuid = dm_tree_node_get_uuid (node);
++ if (! node_uuid)
++ {
++ grub_dprintf ("hostdisk", "%s has no DM uuid\n", path);
++ return NULL;
++ }
++ else if (strncmp (node_uuid, "DMRAID-", 7) != 0)
++ {
++ grub_dprintf ("hostdisk", "%s is not DM-RAID\n", path);
++ return NULL;
++ }
++
++ handle = NULL;
++ mapper_name = NULL;
++ /* Counter-intuitively, device-mapper refers to the disk-like
++ device containing a DM-RAID partition device as a "child" of
++ the partition device. */
++ child = dm_tree_next_child (&handle, node, 0);
++ if (! child)
++ {
++ grub_dprintf ("hostdisk", "%s has no DM children\n", path);
++ goto devmapper_out;
++ }
++ child_uuid = dm_tree_node_get_uuid (child);
++ if (! child_uuid)
++ {
++ grub_dprintf ("hostdisk", "%s child has no DM uuid\n", path);
++ goto devmapper_out;
++ }
++ else if (strncmp (child_uuid, "DMRAID-", 7) != 0)
++ {
++ grub_dprintf ("hostdisk", "%s child is not DM-RAID\n", path);
++ goto devmapper_out;
++ }
++ child_name = dm_tree_node_get_name (child);
++ if (! child_name)
++ {
++ grub_dprintf ("hostdisk", "%s child has no DM name\n", path);
++ goto devmapper_out;
++ }
++ mapper_name = child_name;
++
++devmapper_out:
++ if (! mapper_name)
++ {
++ /* This is a DM-RAID disk, not a partition. */
++ mapper_name = dm_tree_node_get_name (node);
++ if (! mapper_name)
++ {
++ grub_dprintf ("hostdisk", "%s has no DM name\n", path);
++ return NULL;
++ }
++ }
++ return xasprintf ("/dev/mapper/%s", mapper_name);
++ }
++#endif /* HAVE_DEVICE_MAPPER */
+ }
+
+ return path;
+@@ -884,12 +1085,12 @@
+ #endif
+
+ static int
+-find_system_device (const char *os_dev)
++find_system_device (const char *os_dev, struct stat *st)
+ {
+ unsigned int i;
+ char *os_disk;
+
+- os_disk = convert_system_partition_to_system_disk (os_dev);
++ os_disk = convert_system_partition_to_system_disk (os_dev, st);
+ if (! os_disk)
+ return -1;
+
+@@ -923,7 +1124,7 @@
+ return 0;
+ }
+
+- drive = find_system_device (os_dev);
++ drive = find_system_device (os_dev, &st);
+ if (drive < 0)
+ {
+ grub_error (GRUB_ERR_BAD_DEVICE,
+@@ -931,8 +1132,8 @@
+ return 0;
+ }
+
+- if (grub_strcmp (os_dev, convert_system_partition_to_system_disk (os_dev))
+- == 0)
++ if (grub_strcmp (os_dev,
++ convert_system_partition_to_system_disk (os_dev, &st)) == 0)
+ return make_device_name (drive, -1, -1);
+
+ #if defined(__FreeBSD__) || defined(__FreeBSD_kernel__) || defined(__APPLE__)
+@@ -954,8 +1155,7 @@
+ {
+ char *name;
+ grub_disk_t disk;
+- int fd;
+- struct hd_geometry hdg;
++ grub_disk_addr_t start;
+ int dos_part = -1;
+ int bsd_part = -1;
+ auto int find_partition (grub_disk_t disk,
+@@ -985,7 +1185,7 @@
+ partition->index, partition->start);
+ }
+
+- if (hdg.start == partition->start)
++ if (start == partition->start)
+ {
+ if (pcdata)
+ {
+@@ -1008,28 +1208,16 @@
+ if (MAJOR (st.st_rdev) == FLOPPY_MAJOR)
+ return name;
+
+- fd = open (os_dev, O_RDONLY);
+- if (fd == -1)
+- {
+- grub_error (GRUB_ERR_BAD_DEVICE, "cannot open `%s' while attempting to get disk geometry", os_dev);
+- free (name);
+- return 0;
+- }
+-
+- if (ioctl (fd, HDIO_GETGEO, &hdg))
++ start = find_partition_start (os_dev);
++ if (grub_errno != GRUB_ERR_NONE)
+ {
+- grub_error (GRUB_ERR_BAD_DEVICE,
+- "cannot get geometry of `%s'", os_dev);
+- close (fd);
+ free (name);
+ return 0;
+ }
+
+- close (fd);
+-
+- grub_util_info ("%s starts from %lu", os_dev, hdg.start);
++ grub_util_info ("%s starts from %lu", os_dev, start);
+
+- if (hdg.start == 0 && device_is_wholedisk (os_dev))
++ if (start == 0 && device_is_wholedisk (os_dev))
+ return name;
+
+ grub_util_info ("opening the device %s", name);
diff --git a/sys-boot/grub/files/ubuntu-upstream-1.98/962_no_device_map.diff b/sys-boot/grub/files/ubuntu-upstream-1.98/962_no_device_map.diff
new file mode 100644
index 00000000..c129254a
--- /dev/null
+++ b/sys-boot/grub/files/ubuntu-upstream-1.98/962_no_device_map.diff
@@ -0,0 +1,112 @@
+Ubuntu: Don't generate a device map by default.
+
+diff -Nur -x '*.orig' -x '*~' grub2/util/grub-install.in grub2.new/util/grub-install.in
+--- grub2/util/grub-install.in 2010-03-22 14:11:42.000000000 +0000
++++ grub2.new/util/grub-install.in 2010-03-22 16:23:14.000000000 +0000
+@@ -39,7 +39,6 @@
+ else
+ grub_mkimage=${bindir}/`echo grub-mkelfimage | sed ${transform}`
+ fi
+-grub_mkdevicemap=${sbindir}/`echo grub-mkdevicemap | sed ${transform}`
+ grub_probe=${sbindir}/`echo grub-probe | sed ${transform}`
+ grub_editenv=${bindir}/`echo grub-editenv | sed ${transform}`
+ rootdir=
+@@ -74,7 +73,6 @@
+ instead of the root directory
+ --grub-setup=FILE use FILE as grub-setup
+ --grub-mkimage=FILE use FILE as grub-mkimage
+- --grub-mkdevicemap=FILE use FILE as grub-mkdevicemap
+ --grub-probe=FILE use FILE as grub-probe
+ --no-floppy do not probe any floppy drive
+ --recheck probe a device map even if it already exists
+@@ -124,7 +122,7 @@
+ --grub-mkimage=*)
+ grub_mkimage=`echo "$option" | sed 's/--grub-mkimage=//'` ;;
+ --grub-mkdevicemap=*)
+- grub_mkdevicemap=`echo "$option" | sed 's/--grub-mkdevicemap=//'` ;;
++ : ;; # compatibility only
+ --grub-probe=*)
+ grub_probe=`echo "$option" | sed 's/--grub-probe=//'` ;;
+ --no-floppy)
+@@ -209,14 +207,6 @@
+ exit 1
+ fi
+
+-set $grub_mkdevicemap dummy
+-if test -f "$1"; then
+- :
+-else
+- echo "$1: Not found." 1>&2
+- exit 1
+-fi
+-
+ # Create the GRUB directory if it is not present.
+ test -d "$bootdir" || mkdir "$bootdir" || exit 1
+ test -d "$grubdir" || mkdir "$grubdir" || exit 1
+@@ -226,22 +216,14 @@
+ rm -f $device_map
+ fi
+
+-# Create the device map file if it is not present.
++# Make sure that there is no duplicated entry in the device map.
+ if test -f "$device_map"; then
+- :
+-else
+- # Create a safe temporary file.
+- test -n "$mklog" && log_file=`$mklog`
+-
+- $grub_mkdevicemap --device-map=$device_map $no_floppy || exit 1
+-fi
+-
+-# Make sure that there is no duplicated entry.
+-tmp=`sed -n '/^([fh]d[0-9]*)/s/\(^(.*)\).*/\1/p' $device_map \
+- | sort | uniq -d | sed -n 1p`
+-if test -n "$tmp"; then
+- echo "The drive $tmp is defined multiple times in the device map $device_map" 1>&2
+- exit 1
++ tmp=`sed -n '/^([fh]d[0-9]*)/s/\(^(.*)\).*/\1/p' $device_map \
++ | sort | uniq -d | sed -n 1p`
++ if test -n "$tmp"; then
++ echo "The drive $tmp is defined multiple times in the device map $device_map" 1>&2
++ exit 1
++ fi
+ fi
+
+ # Copy the GRUB images to the GRUB directory.
+diff -Nur -x '*.orig' -x '*~' grub2/util/grub-mkconfig.in grub2.new/util/grub-mkconfig.in
+--- grub2/util/grub-mkconfig.in 2010-03-22 16:23:13.000000000 +0000
++++ grub2.new/util/grub-mkconfig.in 2010-03-22 16:23:57.000000000 +0000
+@@ -31,7 +31,6 @@
+ grub_cfg=""
+ grub_mkconfig_dir=${sysconfdir}/grub.d
+
+-grub_mkdevicemap=${sbindir}/`echo grub-mkdevicemap | sed ${transform}`
+ grub_probe=${sbindir}/`echo grub-probe | sed ${transform}`
+
+ # Usage: usage
+@@ -96,14 +95,6 @@
+ fi
+ fi
+
+-set $grub_mkdevicemap dummy
+-if test -f "$1"; then
+- :
+-else
+- echo "$1: Not found." 1>&2
+- exit 1
+-fi
+-
+ set $grub_probe dummy
+ if test -f "$1"; then
+ :
+@@ -114,10 +105,6 @@
+
+ mkdir -p ${grub_prefix}
+
+-if test -e ${grub_prefix}/device.map ; then : ; else
+- ${grub_mkdevicemap}
+-fi
+-
+ # Device containing our userland. Typically used for root= parameter.
+ GRUB_DEVICE="`${grub_probe} --target=device /`"
+ GRUB_DEVICE_UUID="`${grub_probe} --device ${GRUB_DEVICE} --target=fs_uuid 2> /dev/null`" || true
diff --git a/sys-boot/grub/files/ubuntu-upstream-1.98/968_hostdisk_speedup.diff b/sys-boot/grub/files/ubuntu-upstream-1.98/968_hostdisk_speedup.diff
new file mode 100644
index 00000000..30ebcbea
--- /dev/null
+++ b/sys-boot/grub/files/ubuntu-upstream-1.98/968_hostdisk_speedup.diff
@@ -0,0 +1,310 @@
+Upstream: http://lists.gnu.org/archive/html/grub-devel/2010-03/msg00008.html
+Description: Optimise hostdisk device handling
+ This substantially speeds up grub-probe filesystem reads.
+
+diff -Nur -x '*.orig' -x '*~' grub2/ChangeLog.hostdisk-speedup grub2.new/ChangeLog.hostdisk-speedup
+--- grub2/ChangeLog.hostdisk-speedup 1970-01-01 01:00:00.000000000 +0100
++++ grub2.new/ChangeLog.hostdisk-speedup 2010-03-03 10:43:43.000000000 +0000
+@@ -0,0 +1,18 @@
++2010-03-03 Colin Watson <cjwatson@ubuntu.com>
++
++ * util/hostdisk.c (struct grub_util_biosdisk_data): New structure.
++ (grub_util_biosdisk_open): Initialise disk->data.
++ (struct linux_partition_cache): New structure.
++ (linux_find_partition): Cache partition start positions; these are
++ expensive to compute on every read and write.
++ (open_device): Cache open file descriptor in disk->data, so that we
++ don't have to reopen it and flush the buffer cache for consecutive
++ operations on the same device.
++ (grub_util_biosdisk_close): New function.
++ (grub_util_biosdisk_dev): Set `close' member.
++
++ * conf/common.rmk (grub_probe_SOURCES): Add kern/list.c.
++ * conf/i386-efi.rmk (grub_setup_SOURCES): Likewise.
++ * conf/i386-pc.rmk (grub_setup_SOURCES): Likewise.
++ * conf/sparc64-ieee1275.rmk (grub_setup_SOURCES): Likewise.
++ * conf/x86_64-efi.rmk (grub_setup_SOURCES): Likewise.
+diff -Nur -x '*.orig' -x '*~' grub2/conf/common.rmk grub2.new/conf/common.rmk
+--- grub2/conf/common.rmk 2010-03-03 20:11:04.000000000 +0000
++++ grub2.new/conf/common.rmk 2010-03-03 20:11:05.000000000 +0000
+@@ -25,7 +25,7 @@
+ grub_probe_SOURCES = gnulib/progname.c util/grub-probe.c \
+ util/hostdisk.c util/misc.c util/getroot.c \
+ kern/device.c kern/disk.c kern/err.c kern/misc.c \
+- kern/parser.c kern/partition.c kern/file.c \
++ kern/parser.c kern/partition.c kern/file.c kern/list.c \
+ \
+ fs/affs.c fs/cpio.c fs/fat.c fs/ext2.c fs/hfs.c \
+ fs/hfsplus.c fs/iso9660.c fs/udf.c fs/jfs.c fs/minix.c \
+diff -Nur -x '*.orig' -x '*~' grub2/conf/i386-efi.rmk grub2.new/conf/i386-efi.rmk
+--- grub2/conf/i386-efi.rmk 2010-03-03 20:08:04.000000000 +0000
++++ grub2.new/conf/i386-efi.rmk 2010-03-03 20:11:05.000000000 +0000
+@@ -21,7 +21,7 @@
+ # kern/err.c kern/misc.c fs/fat.c fs/ext2.c fs/xfs.c fs/affs.c \
+ # fs/sfs.c kern/parser.c kern/partition.c partmap/msdos.c \
+ # fs/ufs.c fs/ufs2.c fs/minix.c fs/hfs.c fs/jfs.c fs/hfsplus.c kern/file.c \
+-# kern/fs.c kern/env.c fs/fshelp.c
++# kern/fs.c kern/env.c kern/list.c fs/fshelp.c
+
+ # Scripts.
+ sbin_SCRIPTS = grub-install
+diff -Nur -x '*.orig' -x '*~' grub2/conf/i386-pc.rmk grub2.new/conf/i386-pc.rmk
+--- grub2/conf/i386-pc.rmk 2010-03-03 20:08:04.000000000 +0000
++++ grub2.new/conf/i386-pc.rmk 2010-03-03 20:11:05.000000000 +0000
+@@ -96,7 +96,8 @@
+ util/i386/pc/grub-setup.c util/hostdisk.c \
+ util/misc.c util/getroot.c kern/device.c kern/disk.c \
+ kern/err.c kern/misc.c kern/parser.c kern/partition.c \
+- kern/file.c kern/fs.c kern/env.c fs/fshelp.c \
++ kern/file.c kern/fs.c kern/env.c kern/list.c \
++ fs/fshelp.c \
+ \
+ fs/affs.c fs/cpio.c fs/ext2.c fs/fat.c fs/hfs.c \
+ fs/hfsplus.c fs/iso9660.c fs/udf.c fs/jfs.c fs/minix.c \
+diff -Nur -x '*.orig' -x '*~' grub2/conf/sparc64-ieee1275.rmk grub2.new/conf/sparc64-ieee1275.rmk
+--- grub2/conf/sparc64-ieee1275.rmk 2010-03-03 20:08:04.000000000 +0000
++++ grub2.new/conf/sparc64-ieee1275.rmk 2010-03-03 20:11:05.000000000 +0000
+@@ -70,7 +70,8 @@
+ grub_setup_SOURCES = util/sparc64/ieee1275/grub-setup.c util/hostdisk.c \
+ util/misc.c util/getroot.c kern/device.c kern/disk.c \
+ kern/err.c kern/misc.c kern/parser.c kern/partition.c \
+- kern/file.c kern/fs.c kern/env.c fs/fshelp.c \
++ kern/file.c kern/fs.c kern/env.c kern/list.c \
++ fs/fshelp.c \
+ \
+ fs/affs.c fs/cpio.c fs/ext2.c fs/fat.c fs/hfs.c \
+ fs/hfsplus.c fs/iso9660.c fs/udf.c fs/jfs.c fs/minix.c \
+diff -Nur -x '*.orig' -x '*~' grub2/conf/x86_64-efi.rmk grub2.new/conf/x86_64-efi.rmk
+--- grub2/conf/x86_64-efi.rmk 2010-03-03 20:08:04.000000000 +0000
++++ grub2.new/conf/x86_64-efi.rmk 2010-03-03 20:11:05.000000000 +0000
+@@ -20,7 +20,7 @@
+ # kern/err.c kern/misc.c fs/fat.c fs/ext2.c fs/xfs.c fs/affs.c \
+ # fs/sfs.c kern/parser.c kern/partition.c partmap/msdos.c \
+ # fs/ufs.c fs/ufs2.c fs/minix.c fs/hfs.c fs/jfs.c fs/hfsplus.c kern/file.c \
+-# kern/fs.c kern/env.c fs/fshelp.c
++# kern/fs.c kern/env.c kern/list.c fs/fshelp.c
+
+ # Scripts.
+ sbin_SCRIPTS = grub-install
+diff -Nur -x '*.orig' -x '*~' grub2/util/hostdisk.c grub2.new/util/hostdisk.c
+--- grub2/util/hostdisk.c 2010-03-03 20:11:04.000000000 +0000
++++ grub2.new/util/hostdisk.c 2010-03-03 20:11:05.000000000 +0000
+@@ -26,6 +26,7 @@
+ #include <grub/util/hostdisk.h>
+ #include <grub/misc.h>
+ #include <grub/i18n.h>
++#include <grub/list.h>
+
+ #include <stdio.h>
+ #include <stdlib.h>
+@@ -107,6 +108,13 @@
+ char *device;
+ } map[256];
+
++struct grub_util_biosdisk_data
++{
++ char *dev;
++ int access_mode;
++ int fd;
++};
++
+ #ifdef __linux__
+ /* Check if we have devfs support. */
+ static int
+@@ -169,6 +177,7 @@
+ {
+ int drive;
+ struct stat st;
++ struct grub_util_biosdisk_data *data;
+
+ drive = find_grub_drive (name);
+ if (drive < 0)
+@@ -177,6 +186,10 @@
+
+ disk->has_partitions = 1;
+ disk->id = drive;
++ disk->data = data = xmalloc (sizeof (struct grub_util_biosdisk_data));
++ data->dev = NULL;
++ data->access_mode = 0;
++ data->fd = -1;
+
+ /* Get the size. */
+ #if defined(__MINGW32__)
+@@ -367,6 +380,17 @@
+ #endif /* __linux__ || __CYGWIN__ */
+
+ #ifdef __linux__
++/* Cache of partition start sectors for each disk. */
++struct linux_partition_cache
++{
++ struct linux_partition_cache *next;
++ char *dev;
++ unsigned long start;
++ int partno;
++};
++
++struct linux_partition_cache *linux_partition_cache_list;
++
+ static int
+ linux_find_partition (char *dev, unsigned long sector)
+ {
+@@ -375,6 +399,7 @@
+ char *p;
+ int i;
+ char real_dev[PATH_MAX];
++ struct linux_partition_cache *cache;
+
+ strcpy(real_dev, dev);
+
+@@ -394,6 +419,16 @@
+ format = "%d";
+ }
+
++ for (cache = linux_partition_cache_list; cache; cache = cache->next)
++ {
++ if (strcmp (cache->dev, dev) == 0 && cache->start == sector)
++ {
++ sprintf (p, format, cache->partno);
++ strcpy (dev, real_dev);
++ return 1;
++ }
++ }
++
+ for (i = 1; i < 10000; i++)
+ {
+ int fd;
+@@ -412,6 +447,15 @@
+
+ if (start == sector)
+ {
++ struct linux_partition_cache *new_cache_item;
++
++ new_cache_item = xmalloc (sizeof *new_cache_item);
++ new_cache_item->dev = xstrdup (dev);
++ new_cache_item->start = start;
++ new_cache_item->partno = i;
++ grub_list_push (GRUB_AS_LIST_P (&linux_partition_cache_list),
++ GRUB_AS_LIST (new_cache_item));
++
+ strcpy (dev, real_dev);
+ return 1;
+ }
+@@ -425,6 +469,7 @@
+ open_device (const grub_disk_t disk, grub_disk_addr_t sector, int flags)
+ {
+ int fd;
++ struct grub_util_biosdisk_data *data = disk->data;
+
+ #ifdef O_LARGEFILE
+ flags |= O_LARGEFILE;
+@@ -451,18 +496,35 @@
+ && strncmp (map[disk->id].device, "/dev/", 5) == 0)
+ is_partition = linux_find_partition (dev, disk->partition->start);
+
+- /* Open the partition. */
+- grub_dprintf ("hostdisk", "opening the device `%s' in open_device()\n", dev);
+- fd = open (dev, flags);
+- if (fd < 0)
++ if (data->dev && strcmp (data->dev, dev) == 0 &&
++ data->access_mode == (flags & O_ACCMODE))
+ {
+- grub_error (GRUB_ERR_BAD_DEVICE, "cannot open `%s'", dev);
+- return -1;
++ grub_dprintf ("hostdisk", "reusing open device `%s'\n", dev);
++ fd = data->fd;
+ }
++ else
++ {
++ free (data->dev);
++ if (data->fd != -1)
++ close (data->fd);
++
++ /* Open the partition. */
++ grub_dprintf ("hostdisk", "opening the device `%s' in open_device()\n", dev);
++ fd = open (dev, flags);
++ if (fd < 0)
++ {
++ grub_error (GRUB_ERR_BAD_DEVICE, "cannot open `%s'", dev);
++ return -1;
++ }
+
+- /* Flush the buffer cache to the physical disk.
+- XXX: This also empties the buffer cache. */
+- ioctl (fd, BLKFLSBUF, 0);
++ /* Flush the buffer cache to the physical disk.
++ XXX: This also empties the buffer cache. */
++ ioctl (fd, BLKFLSBUF, 0);
++
++ data->dev = xstrdup (dev);
++ data->access_mode = (flags & O_ACCMODE);
++ data->fd = fd;
++ }
+
+ if (is_partition)
+ sector -= disk->partition->start;
+@@ -486,7 +548,26 @@
+ }
+ #endif
+
+- fd = open (map[disk->id].device, flags);
++ if (data->dev && strcmp (data->dev, map[disk->id].device) == 0 &&
++ data->access_mode == (flags & O_ACCMODE))
++ {
++ grub_dprintf ("hostdisk", "reusing open device `%s'\n", data->dev);
++ fd = data->fd;
++ }
++ else
++ {
++ free (data->dev);
++ if (data->fd != -1)
++ close (data->fd);
++
++ fd = open (map[disk->id].device, flags);
++ if (fd >= 0)
++ {
++ data->dev = xstrdup (map[disk->id].device);
++ data->access_mode = (flags & O_ACCMODE);
++ data->fd = fd;
++ }
++ }
+
+ #if defined(__FreeBSD__) || defined(__FreeBSD_kernel__)
+ if (! (sysctl_oldflags & 0x10)
+@@ -646,7 +727,6 @@
+ != (ssize_t) (size << GRUB_DISK_SECTOR_BITS))
+ grub_error (GRUB_ERR_READ_ERROR, "cannot read from `%s'", map[disk->id].device);
+
+- close (fd);
+ return grub_errno;
+ }
+
+@@ -681,17 +761,27 @@
+ != (ssize_t) (size << GRUB_DISK_SECTOR_BITS))
+ grub_error (GRUB_ERR_WRITE_ERROR, "cannot write to `%s'", map[disk->id].device);
+
+- close (fd);
+ return grub_errno;
+ }
+
++static void
++grub_util_biosdisk_close (struct grub_disk *disk)
++{
++ struct grub_util_biosdisk_data *data = disk->data;
++
++ free (data->dev);
++ if (data->fd != -1)
++ close (data->fd);
++ free (data);
++}
++
+ static struct grub_disk_dev grub_util_biosdisk_dev =
+ {
+ .name = "biosdisk",
+ .id = GRUB_DISK_DEVICE_BIOSDISK_ID,
+ .iterate = grub_util_biosdisk_iterate,
+ .open = grub_util_biosdisk_open,
+- .close = 0,
++ .close = grub_util_biosdisk_close,
+ .read = grub_util_biosdisk_read,
+ .write = grub_util_biosdisk_write,
+ .next = 0
diff --git a/sys-boot/grub/files/ubuntu-upstream-1.98/969_lvm_raid_probe.diff b/sys-boot/grub/files/ubuntu-upstream-1.98/969_lvm_raid_probe.diff
new file mode 100644
index 00000000..52a5c44b
--- /dev/null
+++ b/sys-boot/grub/files/ubuntu-upstream-1.98/969_lvm_raid_probe.diff
@@ -0,0 +1,227 @@
+Description: Fix LVM/RAID probing without device.map
+ When probing LVM or RAID without a device.map, probe all devices in order
+ that we will know about the underlying physical volumes.
+Bug-Ubuntu: https://bugs.launchpad.net/bugs/525085
+Forwarded: http://lists.gnu.org/archive/html/grub-devel/2010-03/msg00084.html
+Last-Update: 2010-03-22
+
+diff -Nur -x '*.orig' -x '*~' grub2/conf/common.rmk grub2.new/conf/common.rmk
+--- grub2/conf/common.rmk 2010-03-22 13:49:14.000000000 +0000
++++ grub2.new/conf/common.rmk 2010-03-22 13:53:20.000000000 +0000
+@@ -24,6 +24,7 @@
+ util/grub-probe.c_DEPENDENCIES = grub_probe_init.h
+ grub_probe_SOURCES = gnulib/progname.c util/grub-probe.c \
+ util/hostdisk.c util/misc.c util/getroot.c \
++ util/deviceiter.c \
+ kern/device.c kern/disk.c kern/err.c kern/misc.c \
+ kern/parser.c kern/partition.c kern/file.c kern/list.c \
+ \
+diff -Nur -x '*.orig' -x '*~' grub2/conf/i386-pc.rmk grub2.new/conf/i386-pc.rmk
+--- grub2/conf/i386-pc.rmk 2010-03-22 13:49:14.000000000 +0000
++++ grub2.new/conf/i386-pc.rmk 2010-03-22 13:49:17.000000000 +0000
+@@ -94,7 +94,8 @@
+ util/i386/pc/grub-setup.c_DEPENDENCIES = grub_setup_init.h
+ grub_setup_SOURCES = gnulib/progname.c \
+ util/i386/pc/grub-setup.c util/hostdisk.c \
+- util/misc.c util/getroot.c kern/device.c kern/disk.c \
++ util/misc.c util/getroot.c util/deviceiter.c \
++ kern/device.c kern/disk.c \
+ kern/err.c kern/misc.c kern/parser.c kern/partition.c \
+ kern/file.c kern/fs.c kern/env.c kern/list.c \
+ fs/fshelp.c \
+diff -Nur -x '*.orig' -x '*~' grub2/conf/sparc64-ieee1275.rmk grub2.new/conf/sparc64-ieee1275.rmk
+--- grub2/conf/sparc64-ieee1275.rmk 2010-03-22 13:49:14.000000000 +0000
++++ grub2.new/conf/sparc64-ieee1275.rmk 2010-03-22 13:49:17.000000000 +0000
+@@ -68,7 +68,8 @@
+ # For grub-setup.
+ util/sparc64/ieee1275/grub-setup.c_DEPENDENCIES = grub_setup_init.h
+ grub_setup_SOURCES = util/sparc64/ieee1275/grub-setup.c util/hostdisk.c \
+- util/misc.c util/getroot.c kern/device.c kern/disk.c \
++ util/misc.c util/getroot.c util/deviceiter.c \
++ kern/device.c kern/disk.c \
+ kern/err.c kern/misc.c kern/parser.c kern/partition.c \
+ kern/file.c kern/fs.c kern/env.c kern/list.c \
+ fs/fshelp.c \
+diff -Nur -x '*.orig' -x '*~' grub2/include/grub/util/hostdisk.h grub2.new/include/grub/util/hostdisk.h
+--- grub2/include/grub/util/hostdisk.h 2010-03-22 13:47:27.000000000 +0000
++++ grub2.new/include/grub/util/hostdisk.h 2010-03-22 13:51:33.000000000 +0000
+@@ -22,6 +22,7 @@
+
+ void grub_util_biosdisk_init (const char *dev_map);
+ void grub_util_biosdisk_fini (void);
++int grub_util_biosdisk_probe_device (const char *name, int is_floppy);
+ char *grub_util_biosdisk_get_grub_dev (const char *os_dev);
+
+ #endif /* ! GRUB_BIOSDISK_MACHINE_UTIL_HEADER */
+diff -Nur -x '*.orig' -x '*~' grub2/util/grub-probe.c grub2.new/util/grub-probe.c
+--- grub2/util/grub-probe.c 2010-03-22 13:47:27.000000000 +0000
++++ grub2.new/util/grub-probe.c 2010-03-22 13:53:10.000000000 +0000
+@@ -28,6 +28,7 @@
+ #include <grub/msdos_partition.h>
+ #include <grub/util/hostdisk.h>
+ #include <grub/util/getroot.h>
++#include <grub/util/deviceiter.h>
+ #include <grub/term.h>
+ #include <grub/env.h>
+ #include <grub/raid.h>
+@@ -106,13 +107,14 @@
+ }
+
+ static void
+-probe (const char *path, char *device_name)
++probe (const char *path, char *device_name, const char *dev_map)
+ {
+ char *drive_name = NULL;
+ char *grub_path = NULL;
+ char *filebuf_via_grub = NULL, *filebuf_via_sys = NULL;
+ grub_device_t dev = NULL;
+ grub_fs_t fs;
++ struct stat dev_map_stat;
+
+ if (path == NULL)
+ {
+@@ -136,6 +138,22 @@
+ goto end;
+ }
+
++ if (stat (dev_map, &dev_map_stat) == -1 &&
++ grub_util_get_dev_abstraction (device_name) != GRUB_DEV_ABSTRACTION_NONE)
++ {
++ /* If we don't have a device map, then we won't yet know about the
++ physical volumes underlying this device, so probe all devices. */
++ grub_util_iterate_devices (grub_util_biosdisk_probe_device, 0);
++
++ /* Now reinitialise the higher layers. */
++ grub_lvm_fini ();
++ grub_mdraid_fini ();
++ grub_raid_fini ();
++ grub_raid_init ();
++ grub_mdraid_init ();
++ grub_lvm_init ();
++ }
++
+ drive_name = grub_util_get_grub_dev (device_name);
+ if (! drive_name)
+ grub_util_error ("cannot find a GRUB drive for %s. Check your device.map", device_name);
+@@ -428,9 +446,9 @@
+
+ /* Do it. */
+ if (argument_is_device)
+- probe (NULL, argument);
++ probe (NULL, argument, dev_map ? : DEFAULT_DEVICE_MAP);
+ else
+- probe (argument, NULL);
++ probe (argument, NULL, dev_map ? : DEFAULT_DEVICE_MAP);
+
+ /* Free resources. */
+ grub_fini_all ();
+diff -Nur -x '*.orig' -x '*~' grub2/util/hostdisk.c grub2.new/util/hostdisk.c
+--- grub2/util/hostdisk.c 2010-03-22 13:49:14.000000000 +0000
++++ grub2.new/util/hostdisk.c 2010-03-22 13:51:53.000000000 +0000
+@@ -1237,6 +1237,48 @@
+ return i;
+ }
+
++static void
++store_grub_dev (const char *grub_disk, const char *os_disk)
++{
++ unsigned int i;
++
++ for (i = 0; i < ARRAY_SIZE (map); i++)
++ if (! map[i].device)
++ break;
++ else if (strcmp (map[i].drive, grub_disk) == 0)
++ {
++ if (strcmp (map[i].device, os_disk) == 0)
++ return;
++ grub_util_error (_("drive `%s' already mapped to `%s'"),
++ map[i].drive, map[i].device);
++ }
++
++ if (i == ARRAY_SIZE (map))
++ grub_util_error (_("device count exceeds limit"));
++
++ map[i].drive = xstrdup (grub_disk);
++ map[i].device = xstrdup (os_disk);
++}
++
++static int num_hd = 0;
++static int num_fd = 0;
++
++int
++grub_util_biosdisk_probe_device (const char *name, int is_floppy)
++{
++ char *grub_disk;
++
++ if (is_floppy)
++ grub_disk = xasprintf ("fd%d", num_fd++);
++ else
++ grub_disk = xasprintf ("hd%d", num_hd++);
++
++ store_grub_dev (grub_disk, name);
++ free (grub_disk);
++
++ return 0;
++}
++
+ char *
+ grub_util_biosdisk_get_grub_dev (const char *os_dev)
+ {
+diff -Nur -x '*.orig' -x '*~' grub2/util/i386/pc/grub-setup.c grub2.new/util/i386/pc/grub-setup.c
+--- grub2/util/i386/pc/grub-setup.c 2010-03-22 13:49:13.000000000 +0000
++++ grub2.new/util/i386/pc/grub-setup.c 2010-03-22 13:53:10.000000000 +0000
+@@ -36,6 +36,7 @@
+ #include <grub/util/raid.h>
+ #include <grub/util/lvm.h>
+ #include <grub/util/getroot.h>
++#include <grub/util/deviceiter.h>
+
+ static const grub_gpt_part_type_t grub_gpt_partition_type_bios_boot = GRUB_GPT_PARTITION_TYPE_BIOS_BOOT;
+
+@@ -646,6 +647,7 @@
+ char *core_file = 0;
+ char *dir = 0;
+ char *dev_map = 0;
++ struct stat dev_map_stat;
+ char *root_dev = 0;
+ char *dest_dev;
+ int must_embed = 0, force = 0, fs_probe = 1;
+@@ -744,6 +746,9 @@
+ /* Initialize the emulated biosdisk driver. */
+ grub_util_biosdisk_init (dev_map ? : DEFAULT_DEVICE_MAP);
+
++ if (stat (dev_map ? : DEFAULT_DEVICE_MAP, &dev_map_stat) == -1)
++ grub_util_iterate_devices (grub_util_biosdisk_probe_device, 0);
++
+ /* Initialize all modules. */
+ grub_init_all ();
+
+diff -Nur -x '*.orig' -x '*~' grub2/util/sparc64/ieee1275/grub-setup.c grub2.new/util/sparc64/ieee1275/grub-setup.c
+--- grub2/util/sparc64/ieee1275/grub-setup.c 2010-03-22 13:47:27.000000000 +0000
++++ grub2.new/util/sparc64/ieee1275/grub-setup.c 2010-03-22 13:53:10.000000000 +0000
+@@ -46,6 +46,7 @@
+ #include <sys/stat.h>
+ #include <dirent.h>
+ #include <grub/util/getroot.h>
++#include <grub/util/deviceiter.h>
+
+ #define _GNU_SOURCE 1
+ #include <getopt.h>
+@@ -618,6 +619,7 @@
+ main (int argc, char *argv[])
+ {
+ struct grub_setup_info ginfo;
++ struct stat dev_map_stat;
+
+ set_program_name (argv[0]);
+
+@@ -630,6 +632,9 @@
+ /* Initialize the emulated biosdisk driver. */
+ grub_util_biosdisk_init (ginfo.dev_map ? ginfo.dev_map : DEFAULT_DEVICE_MAP);
+
++ if (stat (ginfo.dev_map ? : DEFAULT_DEVICE_MAP, &dev_map_stat) == -1)
++ grub_util_iterate_devices (grub_util_biosdisk_probe_device, 0);
++
+ /* Initialize all modules. */
+ grub_init_all ();
+
diff --git a/sys-boot/grub/files/ubuntu-upstream-1.98/970_fix_locale_installation.diff b/sys-boot/grub/files/ubuntu-upstream-1.98/970_fix_locale_installation.diff
new file mode 100644
index 00000000..ab202885
--- /dev/null
+++ b/sys-boot/grub/files/ubuntu-upstream-1.98/970_fix_locale_installation.diff
@@ -0,0 +1,55 @@
+Description: Copy .mo files from @datadir@/locale
+ This matches where 'make install' puts them.
+Origin: upstream, http://bazaar.launchpad.net/~vcs-imports/grub/grub2-bzr/revision/2265
+Bug-Ubuntu: https://bugs.launchpad.net/bugs/537998
+Forwarded: http://lists.gnu.org/archive/html/grub-devel/2010-03/msg00074.html
+Last-Update: 2010-03-22
+
+diff -Nur -x '*.orig' -x '*~' grub2/util/grub-install.in grub2.new/util/grub-install.in
+--- grub2/util/grub-install.in 2010-03-22 15:49:32.000000000 +0000
++++ grub2.new/util/grub-install.in 2010-03-22 15:54:31.000000000 +0000
+@@ -32,6 +32,7 @@
+ host_os=@host_os@
+ font=@datadir@/@PACKAGE_TARNAME@/ascii.pf2
+ pkglibdir=${libdir}/`echo ${PACKAGE_TARNAME}/${target_cpu}-${platform} | sed ${transform}`
++localedir=@datadir@/locale
+
+ grub_setup=${sbindir}/`echo grub-setup | sed ${transform}`
+ if [ "${target_cpu}-${platform}" = "i386-pc" ] || [ "${target_cpu}-${platform}" = "sparc64-ieee1275" ] || [ "${target_cpu}-${platform}" = "mips-yeeloong" ] ; then
+@@ -245,9 +246,9 @@
+
+ # Copy gettext files
+ mkdir -p ${grubdir}/locale/
+-for file in ${grubdir}/locale/*.mo ${pkglibdir}/locale/*.mo; do
+- if test -f "$file"; then
+- cp -f "$file" ${grubdir}/locale/
++for dir in ${localedir}/*; do
++ if test -f "$dir/LC_MESSAGES/grub.mo"; then
++ cp -f "$dir/LC_MESSAGES/grub.mo" "${grubdir}/locale/${dir##*/}.mo"
+ fi
+ done
+
+diff -Nur -x '*.orig' -x '*~' grub2/util/i386/efi/grub-install.in grub2.new/util/i386/efi/grub-install.in
+--- grub2/util/i386/efi/grub-install.in 2010-03-09 16:14:00.000000000 +0000
++++ grub2.new/util/i386/efi/grub-install.in 2010-03-22 15:54:31.000000000 +0000
+@@ -31,6 +31,7 @@
+ platform=@platform@
+ host_os=@host_os@
+ pkglibdir=${libdir}/`echo ${PACKAGE_TARNAME}/${target_cpu}-${platform} | sed ${transform}`
++localedir=@datadir@/locale
+
+ grub_mkimage=${bindir}/`echo grub-mkimage | sed ${transform}`
+ grub_mkdevicemap=${sbindir}/`echo grub-mkdevicemap | sed ${transform}`
+@@ -182,9 +183,9 @@
+
+ # Copy gettext files
+ mkdir -p ${grubdir}/locale/
+-for file in ${grubdir}/locale/*.mo ${pkglibdir}/locale/*.mo; do
+- if test -f "$file"; then
+- cp -f "$file" ${grubdir}/locale/
++for dir in ${localedir}/*; do
++ if test -f "$dir/LC_MESSAGES/grub.mo"; then
++ cp -f "$dir/LC_MESSAGES/grub.mo" "${grubdir}/locale/${dir##*/}.mo"
+ fi
+ done
+
diff --git a/sys-boot/grub/files/ubuntu-upstream-1.98/971_langpacks.diff b/sys-boot/grub/files/ubuntu-upstream-1.98/971_langpacks.diff
new file mode 100644
index 00000000..7e1cb897
--- /dev/null
+++ b/sys-boot/grub/files/ubuntu-upstream-1.98/971_langpacks.diff
@@ -0,0 +1,30 @@
+Description: Prefer translations from language packs
+Author: Colin Watson <cjwatson@ubuntu.com>
+Bug-Ubuntu: https://bugs.launchpad.net/bugs/537998
+Forwarded: not-needed
+Last-Update: 2010-03-22
+
+diff -Nur -x '*.orig' -x '*~' grub2/util/grub-install.in grub2.new/util/grub-install.in
+--- grub2/util/grub-install.in 2010-03-22 15:58:16.000000000 +0000
++++ grub2.new/util/grub-install.in 2010-03-22 15:59:04.000000000 +0000
+@@ -246,7 +246,7 @@
+
+ # Copy gettext files
+ mkdir -p ${grubdir}/locale/
+-for dir in ${localedir}/*; do
++for dir in ${localedir}/* ${localedir}-langpack/*; do
+ if test -f "$dir/LC_MESSAGES/grub.mo"; then
+ cp -f "$dir/LC_MESSAGES/grub.mo" "${grubdir}/locale/${dir##*/}.mo"
+ fi
+diff -Nur -x '*.orig' -x '*~' grub2/util/i386/efi/grub-install.in grub2.new/util/i386/efi/grub-install.in
+--- grub2/util/i386/efi/grub-install.in 2010-03-22 15:58:16.000000000 +0000
++++ grub2.new/util/i386/efi/grub-install.in 2010-03-22 15:59:17.000000000 +0000
+@@ -183,7 +183,7 @@
+
+ # Copy gettext files
+ mkdir -p ${grubdir}/locale/
+-for dir in ${localedir}/*; do
++for dir in ${localedir}/* ${localedir}-langpack/*; do
+ if test -f "$dir/LC_MESSAGES/grub.mo"; then
+ cp -f "$dir/LC_MESSAGES/grub.mo" "${grubdir}/locale/${dir##*/}.mo"
+ fi
diff --git a/sys-boot/grub/files/ubuntu-upstream-1.98/974_drive_probe.diff b/sys-boot/grub/files/ubuntu-upstream-1.98/974_drive_probe.diff
new file mode 100644
index 00000000..0c9f3646
--- /dev/null
+++ b/sys-boot/grub/files/ubuntu-upstream-1.98/974_drive_probe.diff
@@ -0,0 +1,23 @@
+Description: Probe all devices if we've been asked for a drive name
+ This allows --target=drive to work properly even without a device.map.
+ .
+ Depends on 969_lvm_raid_probe.diff.
+Author: Colin Watson <cjwatson@ubuntu.com>
+Bug-Ubuntu: https://bugs.launchpad.net/bugs/549980
+Forwarded: no
+Last-Update: 2010-04-08
+
+diff -Nur -x '*.orig' -x '*~' grub2/util/grub-probe.c grub2.new/util/grub-probe.c
+--- grub2/util/grub-probe.c 2010-04-08 12:02:36.000000000 +0100
++++ grub2.new/util/grub-probe.c 2010-04-08 12:04:05.000000000 +0100
+@@ -139,7 +139,9 @@
+ }
+
+ if (stat (dev_map, &dev_map_stat) == -1 &&
+- grub_util_get_dev_abstraction (device_name) != GRUB_DEV_ABSTRACTION_NONE)
++ (print == PRINT_DRIVE ||
++ grub_util_get_dev_abstraction (device_name) !=
++ GRUB_DEV_ABSTRACTION_NONE))
+ {
+ /* If we don't have a device map, then we won't yet know about the
+ physical volumes underlying this device, so probe all devices. */
diff --git a/sys-boot/grub/files/ubuntu-upstream-1.98/975_hostdisk_hd.diff b/sys-boot/grub/files/ubuntu-upstream-1.98/975_hostdisk_hd.diff
new file mode 100644
index 00000000..7ea7f5f8
--- /dev/null
+++ b/sys-boot/grub/files/ubuntu-upstream-1.98/975_hostdisk_hd.diff
@@ -0,0 +1,114 @@
+Description: Adjust hostdisk id for hard disks
+ This allows grub-setup to use its standard workaround for broken BIOSes.
+Author: Colin Watson <cjwatson@ubuntu.com>
+Bug: http://savannah.gnu.org/bugs/?29464
+Bug-Ubuntu: https://bugs.launchpad.net/bugs/555500
+Forwarded: http://savannah.gnu.org/bugs/?29464
+Last-Update: 2010-04-08
+
+diff -Nur -x '*.orig' -x '*~' grub2/util/hostdisk.c grub2.new/util/hostdisk.c
+--- grub2/util/hostdisk.c 2010-04-08 17:09:02.000000000 +0100
++++ grub2.new/util/hostdisk.c 2010-04-08 17:10:18.000000000 +0100
+@@ -186,6 +186,8 @@
+
+ disk->has_partitions = 1;
+ disk->id = drive;
++ if (strncmp (map[drive].drive, "hd", 2) == 0)
++ disk->id += 0x80;
+ disk->data = data = xmalloc (sizeof (struct grub_util_biosdisk_data));
+ data->dev = NULL;
+ data->access_mode = 0;
+@@ -491,9 +493,9 @@
+ int is_partition = 0;
+ char dev[PATH_MAX];
+
+- strcpy (dev, map[disk->id].device);
++ strcpy (dev, map[disk->id & 0x7f].device);
+ if (disk->partition && sector >= disk->partition->start
+- && strncmp (map[disk->id].device, "/dev/", 5) == 0)
++ && strncmp (map[disk->id & 0x7f].device, "/dev/", 5) == 0)
+ is_partition = linux_find_partition (dev, disk->partition->start);
+
+ if (data->dev && strcmp (data->dev, dev) == 0 &&
+@@ -548,7 +550,7 @@
+ }
+ #endif
+
+- if (data->dev && strcmp (data->dev, map[disk->id].device) == 0 &&
++ if (data->dev && strcmp (data->dev, map[disk->id & 0x7f].device) == 0 &&
+ data->access_mode == (flags & O_ACCMODE))
+ {
+ grub_dprintf ("hostdisk", "reusing open device `%s'\n", data->dev);
+@@ -560,10 +562,10 @@
+ if (data->fd != -1)
+ close (data->fd);
+
+- fd = open (map[disk->id].device, flags);
++ fd = open (map[disk->id & 0x7f].device, flags);
+ if (fd >= 0)
+ {
+- data->dev = xstrdup (map[disk->id].device);
++ data->dev = xstrdup (map[disk->id & 0x7f].device);
+ data->access_mode = (flags & O_ACCMODE);
+ data->fd = fd;
+ }
+@@ -581,12 +583,12 @@
+ #if defined(__APPLE__)
+ /* If we can't have exclusive access, try shared access */
+ if (fd < 0)
+- fd = open(map[disk->id].device, flags | O_SHLOCK);
++ fd = open(map[disk->id & 0x7f].device, flags | O_SHLOCK);
+ #endif
+
+ if (fd < 0)
+ {
+- grub_error (GRUB_ERR_BAD_DEVICE, "cannot open `%s' in open_device()", map[disk->id].device);
++ grub_error (GRUB_ERR_BAD_DEVICE, "cannot open `%s' in open_device()", map[disk->id & 0x7f].device);
+ return -1;
+ }
+ #endif /* ! __linux__ */
+@@ -604,7 +606,7 @@
+ offset = (loff_t) sector << GRUB_DISK_SECTOR_BITS;
+ if (_llseek (fd, offset >> 32, offset & 0xffffffff, &result, SEEK_SET))
+ {
+- grub_error (GRUB_ERR_BAD_DEVICE, "cannot seek `%s'", map[disk->id].device);
++ grub_error (GRUB_ERR_BAD_DEVICE, "cannot seek `%s'", map[disk->id & 0x7f].device);
+ close (fd);
+ return -1;
+ }
+@@ -615,7 +617,7 @@
+
+ if (lseek (fd, offset, SEEK_SET) != offset)
+ {
+- grub_error (GRUB_ERR_BAD_DEVICE, "cannot seek `%s'", map[disk->id].device);
++ grub_error (GRUB_ERR_BAD_DEVICE, "cannot seek `%s'", map[disk->id & 0x7f].device);
+ close (fd);
+ return -1;
+ }
+@@ -713,7 +715,7 @@
+ parts. -jochen */
+ if (nread (fd, buf, GRUB_DISK_SECTOR_SIZE) != GRUB_DISK_SECTOR_SIZE)
+ {
+- grub_error (GRUB_ERR_READ_ERROR, "cannot read `%s'", map[disk->id].device);
++ grub_error (GRUB_ERR_READ_ERROR, "cannot read `%s'", map[disk->id & 0x7f].device);
+ close (fd);
+ return grub_errno;
+ }
+@@ -725,7 +727,7 @@
+
+ if (nread (fd, buf, size << GRUB_DISK_SECTOR_BITS)
+ != (ssize_t) (size << GRUB_DISK_SECTOR_BITS))
+- grub_error (GRUB_ERR_READ_ERROR, "cannot read from `%s'", map[disk->id].device);
++ grub_error (GRUB_ERR_READ_ERROR, "cannot read from `%s'", map[disk->id & 0x7f].device);
+
+ return grub_errno;
+ }
+@@ -759,7 +761,7 @@
+
+ if (nwrite (fd, buf, size << GRUB_DISK_SECTOR_BITS)
+ != (ssize_t) (size << GRUB_DISK_SECTOR_BITS))
+- grub_error (GRUB_ERR_WRITE_ERROR, "cannot write to `%s'", map[disk->id].device);
++ grub_error (GRUB_ERR_WRITE_ERROR, "cannot write to `%s'", map[disk->id & 0x7f].device);
+
+ return grub_errno;
+ }