--- a/is Sun Jan 31 01:17:32 2010 +0100
+++ b/is Sun Jan 31 23:58:01 2010 +0100
@@ -14,6 +14,8 @@
use SI::system;
use SI::ptable;
use SI::lvm;
+use SI::dumper;
+use SI::grub;
my $ME = basename $0;
my $opt_base = "..";
@@ -43,10 +45,13 @@
do "$src/info/devices";
my %devices = %$VAR1;
-# SI::ptable::restore(%devices);
-# SI::ptable::mkfs(%devices);
- SI::lvm::pvcreate(%devices);
- SI::lvm::vgcfgrestore("$src/lvm/vg.*", %devices);
+ #SI::ptable::restore(%devices);
+ #SI::ptable::mkfs(%devices);
+ #SI::lvm::pvcreate(%devices);
+ #SI::lvm::vgcfgrestore("$src/lvm/vg.*", %devices);
+ #SI::lvm::mkfs(%devices);
+ #SI::dumper::restore("$src/dump/*", %devices);
+ SI::grub::restore(%devices);
exit;
--- a/lib/SI/dumper.pm Sun Jan 31 01:17:32 2010 +0100
+++ b/lib/SI/dumper.pm Sun Jan 31 23:58:01 2010 +0100
@@ -5,6 +5,8 @@
use warnings;
use SI::tools;
use File::Basename;
+use File::Temp qw(tempdir);
+use File::Find;
sub dump($\%) {
my ($file, $devs) = @_;
@@ -24,6 +26,39 @@
}
}
+sub restore($\%) {
+ my @dumps = glob(shift);
+ my $devs = shift;
+
+ my $tmpdir = tempdir (CLEANUP => 1);
+
+ foreach my $dump (@dumps) {
+ # suppose it's gzipped
+ # find the device
+ my $dev;
+ my $base = basename($dump);
+ find(sub {
+ return if defined $dev;
+ if ($_ eq $base) {
+ $dev = $File::Find::name;
+ return;
+ } }, "/dev");
+ my $fs = $devs->{volume}{$dev}{type};
+
+ verbose("restore $dump -> $dev : $fs\n");
+ run("mount -t $fs $dev $tmpdir");
+ my $pid = fork or do {
+ open(STDIN, $dump) or die "Can't open $dump as STDIN: $!\n";
+ chdir $tmpdir or die "Can't chdir to $tmpdir: $!\n";
+ exec restore => "-orf-";
+ die "Can't exec restore: $!\n";
+ };
+ waitpid($pid, 0);
+ run("umount $tmpdir");
+ }
+}
+
+
1;
# vim:sts=4 sw=4 aw ai sm:
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/lib/SI/grub.pm Sun Jan 31 23:58:01 2010 +0100
@@ -0,0 +1,72 @@
+package SI::grub;
+
+use if $ENV{DEBUG} ~~ /grub|all/ => "Smart::Comments";
+use strict;
+use warnings;
+use File::Temp qw(tempdir);
+use IO::File;
+
+use SI::tools;
+
+sub restore(\%) {
+ my $devs = shift;
+
+ # assume the first ext is the boot device (should have
+ # been labeled
+
+ my ($boot, undef) = grep { $devs->{volume}{$_}{type} =~ /^ext/ }
+ grep { $devs->{volume}{$_}{origin} eq "ptable" }
+ grep { defined $devs->{volume}{$_}{type} }
+ sort keys %{$devs->{volume}};
+
+ # now find the partition containing the fstab, it should
+ # be the root file system
+ my $tmpdir = tempdir(CLEANUP => 0);
+
+ my @fs =
+ grep { $devs->{volume}{$_}{type} =~ /^ext/ }
+ grep { defined $devs->{volume}{$_}{type} }
+ keys %{$devs->{volume}};
+
+
+ my @mounted;
+ eval {
+
+ foreach (@fs) {
+ run("mount -oro -t $devs->{volume}{$_}{type} $_ $tmpdir");
+ last if -f "$tmpdir/etc/fstab";
+ run("umount $tmpdir");
+ push @mounted, $tmpdir;
+ }
+
+ # and now try to mount the rest
+
+
+ my $fstab = new IO::File "$tmpdir/etc/fstab";
+ foreach (grep { /^\// } <$fstab>) {
+ my ($dev, $mp, $type, $options, undef) = split;
+ next if $options =~ /noauto/
+ or $mp eq "/"
+ or $mp !~ /^\//;
+ run("mount -t $type $dev $tmpdir/$mp");
+ push @mounted, "$tmpdir/$mp";
+ }
+ close($fstab);
+
+ run("mount -o bind /dev $tmpdir/dev");
+ push @mounted, "$tmpdir/dev";
+
+ run("chroot $tmpdir grub-mkdevicemap");
+ run("chroot $tmpdir /usr/sbin/grub-install '(hd0)'");
+ #system("/bin/bash --login");
+ };
+ if ($@) {
+ warn "** EVAL: $@\n";
+ }
+ map { system("umount $_") } reverse @mounted;
+ rmdir($tmpdir);
+
+}
+
+1;
+# vim:sts=4 sw=4 aw ai sm:
--- a/lib/SI/lvm.pm Sun Jan 31 01:17:32 2010 +0100
+++ b/lib/SI/lvm.pm Sun Jan 31 23:58:01 2010 +0100
@@ -84,10 +84,12 @@
my $devs = shift;
foreach (@cfgs) {
- my $vg = basename($_);
- next if $vg eq "vg.*";
- print $vg, "\n";
+ my $vg = (split /\./, basename($_))[1];
+ next if $vg eq "*";
+ run("vgcfgrestore -f $_ $vg");
+ run("vgchange -ay $vg");
}
+ run("udevadm settle");
}
sub mkfs(\%) {
@@ -97,15 +99,15 @@
next if $v->{origin} ne "lvm"
or not defined $v->{type};
- my $label = default("" => $v->{label});
- my $uuid = default("" => $v->{uuid});
+ my $label = defined $v->{label} ? "-L '$v->{label}'" : "";
+ my $uuid = defined $v->{uuid} ? "-U '$v->{uuid}'" : "";
given($v->{type}) {
when(/ext/) {
- run("mkfs -t $v->{type} -L '$label' -U '$uuid' $volume");
+ run("mkfs -t $v->{type} $label $uuid $volume");
};
when(/swap/) {
- run("mkswap -L '$label' -U '$uuid' $volume");
+ run("mkswap $label $uuid $volume");
};
}
}
--- a/lib/SI/ptable.pm Sun Jan 31 01:17:32 2010 +0100
+++ b/lib/SI/ptable.pm Sun Jan 31 23:58:01 2010 +0100
@@ -75,11 +75,12 @@
die "I won't use the disk ($disk) I'm running on!"
if (stat $0)[0] ~~ [ map { (stat)[6] } map { "/dev/" . basename dirname $_ } glob ("/sys/block/" . basename($disk) . "/*/partition")];
- my $sfdisk = new IO::File "|sfdisk $disk >/dev/null"
+ my $sfdisk = new IO::File "|sfdisk --force $disk >/dev/null"
or die "Can't open |sfdisk $disk: $!\n";
print {$sfdisk} @{$devs->{disk}{$disk}{pt}};
$sfdisk->close or die $? >> 8;
run("partprobe $disk");
+ run("udevadm settle");
}
}
--- a/lib/SI/tools.pm Sun Jan 31 01:17:32 2010 +0100
+++ b/lib/SI/tools.pm Sun Jan 31 23:58:01 2010 +0100
@@ -8,7 +8,7 @@
use Data::Dumper;
use base "Exporter";
-our @EXPORT = qw(&run &verbose &find_by_devid &cat &barf &default);
+our @EXPORT = qw(&run &verbose &find_by_devid &cat &barf &def);
sub run(@) {
system(@_);
@@ -16,7 +16,7 @@
if $?;
}
-sub default($$) {
+sub def($$) {
return defined $_[1] ? $_[1] : $_[0];
}