[Libguestfs] [PATCH] Don't assume grub is on a separate boot filesystem
Richard W.M. Jones
rjones at redhat.com
Thu Aug 13 11:39:15 UTC 2009
On Thu, Aug 13, 2009 at 12:21:16PM +0100, Matthew Booth wrote:
> Paths in grub.conf are relative to the filesystem containing it. grub parsing
> currently assumes that it is on /boot, and will fail if it isn't, for example
> because a guest only has a single partition.
>
> This patch makes grub parsing work harder to work out what grub paths are
> relative to. Firstly, it looks for a previous detected 'linux-grub' filesystem.
> If this isn't found, it tries to work out which filesystem contains
> /boot/grub/menu.lst and uses that.
> ---
> perl/lib/Sys/Guestfs/Lib.pm | 56 +++++++++++++++++++++++++++++++++++++++++-
> 1 files changed, 54 insertions(+), 2 deletions(-)
>
> diff --git a/perl/lib/Sys/Guestfs/Lib.pm b/perl/lib/Sys/Guestfs/Lib.pm
> index 72b0f7d..89f2aa6 100644
> --- a/perl/lib/Sys/Guestfs/Lib.pm
> +++ b/perl/lib/Sys/Guestfs/Lib.pm
> @@ -1435,6 +1435,56 @@ sub _check_for_applications
> $os->{apps} = \@apps;
> }
>
> +# Find the path which needs to be prepended to paths in grub.conf to make them
> +# absolute
> +sub _find_grub_prefix
> +{
> + my ($g, $os) = @_;
> +
> + my $fses = $os->{filesystems};
> + die("filesystems undefined") unless(defined($fses));
> +
> + # Look for the filesystem which contains grub
> + my $grubdev;
> + foreach my $dev (keys(%$fses)) {
> + my $fsinfo = $fses->{$dev};
> + if(exists($fsinfo->{content}) && $fsinfo->{content} eq "linux-grub") {
> + $grubdev = $dev;
> + last;
> + }
> + }
> +
> + my $mounts = $os->{mounts};
> + die("mounts undefined") unless(defined($mounts));
> +
> + # Find where the filesystem is mounted
> + if(defined($grubdev)) {
> + foreach my $mount (keys(%$mounts)) {
> + if($mounts->{$mount} eq $grubdev) {
> + return "" if($mount eq '/');
> + return $mount;
> + }
> + }
> +
> + die("$grubdev defined in filesystems, but not in mounts");
> + }
> +
> + # If we didn't find it, look for /boot/grub/menu.lst, then try to work out
> + # what filesystem it's on. We use menu.lst rather than grub.conf because
> + # debian only uses menu.lst, and anaconda creates a symlink for it.
> + die(__"Can't find grub on guest") unless($g->exists('/boot/grub/menu.lst'));
> +
> + # Look for the most specific mount point in mounts
> + foreach my $path qw(/boot/grub /boot /) {
> + if(exists($mounts->{$path})) {
> + return "" if($path eq '/');
> + return $path;
> + }
> + }
> +
> + die("Couldn't determine which filesystem holds /boot/grub/menu.lst");
> +}
> +
> sub _check_for_kernels
> {
> my ($g, $os) = @_;
> @@ -1443,6 +1493,8 @@ sub _check_for_kernels
> # Iterate over entries in grub.conf, populating $os->{boot}
> # For every kernel we find, inspect it and add to $os->{kernels}
>
> + my $grub = _find_grub_prefix($g, $os);
> +
> my @boot_configs;
>
> # We want
> @@ -1474,7 +1526,7 @@ sub _check_for_kernels
>
> # Check we've got a kernel entry
> if(defined($grub_kernel)) {
> - my $path = "/boot$grub_kernel";
> + my $path = "$grub$grub_kernel";
>
> # Reconstruct the kernel command line
> my @args = ();
> @@ -1508,7 +1560,7 @@ sub _check_for_kernels
>
> unless($@) {
> $config{initrd} =
> - _inspect_initrd($g, $os, "/boot$initrd",
> + _inspect_initrd($g, $os, "$grub$initrd",
> $kernel->{version});
> } else {
> warn __x("Grub entry {title} does not specify an ".
> --
> 1.6.2.5
>
> _______________________________________________
> Libguestfs mailing list
> Libguestfs at redhat.com
> https://www.redhat.com/mailman/listinfo/libguestfs
Can't see any problem with that, ACK.
Rich.
--
Richard Jones, Emerging Technologies, Red Hat http://et.redhat.com/~rjones
virt-df lists disk usage of guests without needing to install any
software inside the virtual machine. Supports Linux and Windows.
http://et.redhat.com/~rjones/virt-df/
More information about the Libguestfs
mailing list