mirror of
https://github.com/libguestfs/libguestfs.git
synced 2026-03-22 07:03:38 +00:00
298 lines
7.8 KiB
Perl
Executable File
298 lines
7.8 KiB
Perl
Executable File
#!/usr/bin/perl -w
|
|
# virt-rescue
|
|
# Copyright (C) 2009-2010 Red Hat Inc.
|
|
#
|
|
# This program is free software; you can redistribute it and/or modify
|
|
# it under the terms of the GNU General Public License as published by
|
|
# the Free Software Foundation; either version 2 of the License, or
|
|
# (at your option) any later version.
|
|
#
|
|
# This program is distributed in the hope that it will be useful,
|
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
# GNU General Public License for more details.
|
|
#
|
|
# You should have received a copy of the GNU General Public License
|
|
# along with this program; if not, write to the Free Software
|
|
# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
|
|
|
|
use warnings;
|
|
use strict;
|
|
|
|
use Errno;
|
|
use Sys::Guestfs;
|
|
use Sys::Guestfs::Lib qw(open_guest);
|
|
use Pod::Usage;
|
|
use Getopt::Long;
|
|
use Locale::TextDomain 'libguestfs';
|
|
|
|
=encoding utf8
|
|
|
|
=head1 NAME
|
|
|
|
virt-rescue - Run a rescue shell on a virtual machine
|
|
|
|
=head1 SYNOPSIS
|
|
|
|
virt-rescue [--options] domname
|
|
|
|
virt-rescue [--options] disk.img [disk.img ...]
|
|
|
|
=head1 WARNING
|
|
|
|
You must I<not> use C<virt-rescue> on live virtual machines. Doing so
|
|
will probably result in disk corruption in the VM. C<virt-rescue>
|
|
tries to stop you from doing this, but doesn't catch all cases.
|
|
|
|
However if you use the I<--ro> (read only) option, then you can attach
|
|
a shell to a live virtual machine. The results might be strange or
|
|
inconsistent at times but you won't get disk corruption.
|
|
|
|
=head1 DESCRIPTION
|
|
|
|
virt-rescue is like a Rescue CD, but for virtual machines, and without
|
|
the need for a CD. virt-rescue gives you a rescue shell and some
|
|
simple recovery tools which you can use to examine or rescue a virtual
|
|
machine or disk image.
|
|
|
|
You can run virt-rescue on any virtual machine known to libvirt, or
|
|
directly on disk image(s):
|
|
|
|
virt-rescue GuestName
|
|
|
|
virt-rescue --ro /path/to/disk.img
|
|
|
|
virt-rescue /dev/sdc
|
|
|
|
For live VMs you I<must> use the --ro option.
|
|
|
|
When you run virt-rescue on a virtual machine or disk image, you are
|
|
placed in an interactive bash shell where you can use many ordinary
|
|
Linux commands. What you see in C</> (C</bin>, C</lib> etc) is the
|
|
rescue appliance. You must mount the virtual machine's filesystems by
|
|
hand. There is an empty directory called C</sysroot> where you can
|
|
mount filesystems.
|
|
|
|
In the example below, we list logical volumes, then choose one to
|
|
mount under C</sysroot>:
|
|
|
|
><rescue> lvs
|
|
LV VG Attr LSize Origin Snap% Move Log Copy% Convert
|
|
lv_root vg_f11x64 -wi-a- 8.83G
|
|
lv_swap vg_f11x64 -wi-a- 992.00M
|
|
><rescue> mount /dev/vg_f11x64/lv_root /sysroot
|
|
><rescue> ls /sysroot
|
|
|
|
If you don't know what filesystems are available on the virtual
|
|
machine then you can use commands such as L<parted(8)> and L<lvs(8)>
|
|
to find out.
|
|
|
|
=head2 NOTES
|
|
|
|
Virt-rescue can be used on I<any> disk image file or device, not just
|
|
a virtual machine. For example you can use it on a blank file if you
|
|
want to partition that file (although we would recommend using
|
|
L<guestfish(1)> instead as it is more suitable for this purpose). You
|
|
can even use virt-rescue on things like SD cards.
|
|
|
|
This tool is just designed for quick interactive hacking on a virtual
|
|
machine. For more structured access to a virtual machine disk image,
|
|
you should use L<guestfs(3)>. To get a structured shell that you can
|
|
use to make scripted changes to guests, use L<guestfish(1)>.
|
|
|
|
=head1 OPTIONS
|
|
|
|
=over 4
|
|
|
|
=cut
|
|
|
|
my $help;
|
|
|
|
=item B<--help>
|
|
|
|
Display brief help.
|
|
|
|
=cut
|
|
|
|
my $version;
|
|
|
|
=item B<--version>
|
|
|
|
Display version number and exit.
|
|
|
|
=cut
|
|
|
|
my $append;
|
|
|
|
=item B<--append kernelopts>
|
|
|
|
Pass additional options to the rescue kernel.
|
|
|
|
=cut
|
|
|
|
my $uri;
|
|
|
|
=item B<--connect URI> | B<-c URI>
|
|
|
|
If using libvirt, connect to the given I<URI>. If omitted, then we
|
|
connect to the default libvirt hypervisor.
|
|
|
|
If you specify guest block devices directly, then libvirt is not used
|
|
at all.
|
|
|
|
=cut
|
|
|
|
my $format;
|
|
|
|
=item B<--format> raw
|
|
|
|
Specify the format of disk images given on the command line. If this
|
|
is omitted then the format is autodetected from the content of the
|
|
disk image.
|
|
|
|
If disk images are requested from libvirt, then this program asks
|
|
libvirt for this information. In this case, the value of the format
|
|
parameter is ignored.
|
|
|
|
If working with untrusted raw-format guest disk images, you should
|
|
ensure the format is always specified.
|
|
|
|
=cut
|
|
|
|
my $memsize;
|
|
|
|
=item B<--memsize MB> | B<-m MB>
|
|
|
|
Change the amount of memory allocated to the rescue system. The
|
|
default is set by libguestfs and is small but adequate for running
|
|
system tools. The occasional program might need more memory. The
|
|
parameter is specified in megabytes.
|
|
|
|
=cut
|
|
|
|
my $network;
|
|
|
|
=item B<--network>
|
|
|
|
Enable QEMU user networking in the guest.
|
|
|
|
=cut
|
|
|
|
my $readonly;
|
|
|
|
=item B<--ro> | B<-r>
|
|
|
|
Open the image read-only.
|
|
|
|
The option must always be used if the disk image or virtual machine
|
|
might be running, and is generally recommended in cases where you
|
|
don't need write access to the disk.
|
|
|
|
=cut
|
|
|
|
my $selinux;
|
|
|
|
=item B<--selinux>
|
|
|
|
Enable SELinux in the rescue appliance. You should read
|
|
L<guestfs(3)/SELINUX> before using this option.
|
|
|
|
=back
|
|
|
|
=cut
|
|
|
|
GetOptions ("help|?" => \$help,
|
|
"version" => \$version,
|
|
"append=s" => \$append,
|
|
"connect|c=s" => \$uri,
|
|
"format=s" => \$format,
|
|
"memsize|m=i" => \$memsize,
|
|
"network" => \$network,
|
|
"ro|r" => \$readonly,
|
|
"selinux" => \$selinux,
|
|
) or pod2usage (2);
|
|
pod2usage (1) if $help;
|
|
if ($version) {
|
|
my $g = Sys::Guestfs->new ();
|
|
my %h = $g->version ();
|
|
print "$h{major}.$h{minor}.$h{release}$h{extra}\n";
|
|
exit
|
|
}
|
|
|
|
pod2usage (__"virt-rescue: no image or VM names rescue given")
|
|
if @ARGV == 0;
|
|
|
|
my @args = (\@ARGV);
|
|
push @args, address => $uri if $uri;
|
|
push @args, rw => 1 unless $readonly;
|
|
push @args, format => $format if defined $format;
|
|
my $g = open_guest (@args);
|
|
|
|
# Setting "direct mode" is required for the rescue appliance.
|
|
$g->set_direct (1);
|
|
|
|
# Set other features.
|
|
$g->set_selinux (1) if $selinux;
|
|
$g->set_memsize ($memsize) if defined $memsize;
|
|
$g->set_network (1) if $network;
|
|
|
|
# Set the kernel command line, which must include guestfs_rescue=1
|
|
# (see appliance/init).
|
|
my $str = "guestfs_rescue=1";
|
|
$str .= " $append" if defined $append;
|
|
$g->set_append ($str);
|
|
|
|
# Run the appliance. This won't return until the user quits the
|
|
# appliance.
|
|
eval { $g->launch (); };
|
|
|
|
# launch() expects guestfsd to start. However, virt-rescue doesn't run guestfsd,
|
|
# so this will always fail with ECHILD when the appliance exits unexpectedly.
|
|
die $@ unless $!{ECHILD};
|
|
|
|
exit 0;
|
|
|
|
=head1 ENVIRONMENT VARIABLES
|
|
|
|
Several environment variables affect virt-rescue. See
|
|
L<guestfs(3)/ENVIRONMENT VARIABLES> for the complete list.
|
|
|
|
=head1 SHELL QUOTING
|
|
|
|
Libvirt guest names can contain arbitrary characters, some of which
|
|
have meaning to the shell such as C<#> and space. You may need to
|
|
quote or escape these characters on the command line. See the shell
|
|
manual page L<sh(1)> for details.
|
|
|
|
=head1 SEE ALSO
|
|
|
|
L<guestfs(3)>,
|
|
L<guestfish(1)>,
|
|
L<virt-cat(1)>,
|
|
L<Sys::Guestfs(3)>,
|
|
L<Sys::Guestfs::Lib(3)>,
|
|
L<Sys::Virt(3)>,
|
|
L<http://libguestfs.org/>.
|
|
|
|
=head1 AUTHOR
|
|
|
|
Richard W.M. Jones L<http://people.redhat.com/~rjones/>
|
|
|
|
=head1 COPYRIGHT
|
|
|
|
Copyright (C) 2009-2010 Red Hat Inc.
|
|
|
|
This program is free software; you can redistribute it and/or modify
|
|
it under the terms of the GNU General Public License as published by
|
|
the Free Software Foundation; either version 2 of the License, or
|
|
(at your option) any later version.
|
|
|
|
This program is distributed in the hope that it will be useful,
|
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
GNU General Public License for more details.
|
|
|
|
You should have received a copy of the GNU General Public License
|
|
along with this program; if not, write to the Free Software
|
|
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
|