2010-01-26 Colin Watson <cjwatson@ubuntu.com>
* 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.
This commit is contained in:
parent
7181e2281f
commit
b769a37b6e
4 changed files with 175 additions and 2 deletions
|
@ -1,6 +1,7 @@
|
|||
2010-01-25 Colin Watson <cjwatson@ubuntu.com>
|
||||
2010-01-26 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
|
||||
|
@ -14,3 +15,12 @@
|
|||
(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.
|
||||
|
|
|
@ -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
|
||||
|
|
|
@ -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 @@ struct hd_geometry
|
|||
| ((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 @@ check_device (const char *device)
|
|||
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 @@ grub_util_iterate_devices (int NESTED_FUNC_ATTR (*hook) (const char *, int),
|
|||
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__ */
|
||||
}
|
||||
|
||||
|
|
|
@ -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 @@ main (int argc, char *argv[])
|
|||
}
|
||||
}
|
||||
|
||||
if (verbosity > 1)
|
||||
grub_env_set ("debug", "all");
|
||||
|
||||
make_device_map (dev_map ? : DEFAULT_DEVICE_MAP, floppy_disks);
|
||||
|
||||
free (dev_map);
|
||||
|
|
Loading…
Reference in a new issue