summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorRafael Garcia-Suarez <rgarciasuarez@mandriva.org>2004-06-23 07:52:31 +0000
committerRafael Garcia-Suarez <rgarciasuarez@mandriva.org>2004-06-23 07:52:31 +0000
commitca1fb73b4ccf0ff0fe0f8c54e2d5db923f8bba6a (patch)
tree974cf3a86811ed554ac6bcf0db83a992100c9448
parente351b9bfbcabf0cdb14e7e5a1fd9a607a1fbb00d (diff)
downloaddrakx-ca1fb73b4ccf0ff0fe0f8c54e2d5db923f8bba6a.tar
drakx-ca1fb73b4ccf0ff0fe0f8c54e2d5db923f8bba6a.tar.gz
drakx-ca1fb73b4ccf0ff0fe0f8c54e2d5db923f8bba6a.tar.bz2
drakx-ca1fb73b4ccf0ff0fe0f8c54e2d5db923f8bba6a.tar.xz
drakx-ca1fb73b4ccf0ff0fe0f8c54e2d5db923f8bba6a.zip
Support for supplementary CDs during installation (from the 10.0
update branch.)
-rw-r--r--perl-install/install_any.pm109
-rw-r--r--perl-install/pkgs.pm49
2 files changed, 137 insertions, 21 deletions
diff --git a/perl-install/install_any.pm b/perl-install/install_any.pm
index f64da8589..aaf820648 100644
--- a/perl-install/install_any.pm
+++ b/perl-install/install_any.pm
@@ -1,6 +1,5 @@
package install_any; # $Id$
-use diagnostics;
use strict;
use vars qw(@ISA %EXPORT_TAGS @EXPORT_OK $boot_medium $current_medium $asked_medium @advertising_images);
@@ -39,6 +38,13 @@ $asked_medium = $boot_medium;
my $postinstall_rpms = '';
my $cdrom;
my %iso_images;
+
+sub mountCdrom($;$) {
+ my ($mountpoint, $cdrom_) = @_;
+ $cdrom_ = $cdrom if !defined $cdrom_;
+ eval { fs::mount($cdrom_, $mountpoint, "iso9660", 'readonly') };
+}
+
sub useMedium($) {
#- before ejecting the first CD, there are some files to copy!
#- does nothing if the function has already been called.
@@ -64,6 +70,7 @@ sub askChangeMedium($$) {
my ($method, $medium) = @_;
my $allow;
do {
+ local $::o->{method} = $method = 'cdrom' if $medium =~ /^\d+s$/; #- Suppl CD
eval { $allow = changeMedium($method, $medium) };
} while $@; #- really it is not allowed to die in changeMedium!!! or install will cores with rpmlib!!!
log::l($allow ? "accepting medium $medium" : "refusing medium $medium");
@@ -137,7 +144,7 @@ sub errorOpeningFile($) {
ejectCdrom($cdrom);
while ($max > 0 && askChangeMedium($::o->{method}, $asked_medium)) {
$current_medium = $asked_medium;
- eval { fs::mount($cdrom, "/tmp/image", "iso9660", 'readonly') };
+ mountCdrom("/tmp/image");
my $getFile = getFile($file);
$getFile && @advertising_images and copy_advertising($::o);
$getFile and return $getFile;
@@ -154,6 +161,9 @@ sub errorOpeningFile($) {
}
}
+ #- Don't unselect supplementary CDs.
+ return if $asked_medium =~ /^\d+s$/;
+
#- keep in mind the asked medium has been refused on this way.
#- this means it is no more selected.
$::o->{packages}{mediums}{$asked_medium}{selected} = undef;
@@ -165,7 +175,7 @@ sub errorOpeningFile($) {
return;
}
sub getFile {
- my ($f, $o_method) = @_;
+ my ($f, $o_method, $altroot) = @_;
log::l("getFile $f:$o_method");
my $rel = relGetFile($f);
do {
@@ -182,11 +192,13 @@ sub getFile {
require http;
http::getFile("$ENV{URLPREFIX}/$rel");
} else {
- #- try to open the file, but examine if it is present in the repository, this allow
- #- handling changing a media when some of the file on the first CD has been copied
- #- to other to avoid media change...
+ #- try to open the file, but examine if it is present in the repository,
+ #- this allows handling changing a media when some of the files on the
+ #- first CD have been copied to other to avoid media change...
my $f2 = "$postinstall_rpms/$f";
- $f2 = "/tmp/image/$rel" if !$postinstall_rpms || !-e $f2;
+ $altroot = '/tmp/image' unless $altroot;
+ $f2 = "$altroot/$rel" if !$postinstall_rpms || !-e $f2;
+ $f2 = $rel if $rel =~ m!^/! && !-e $f2; #- not a relative path
my $F; open($F, $f2) && $F;
}
} || errorOpeningFile($f);
@@ -343,7 +355,53 @@ sub setPackages {
require pkgs;
if (!$o->{packages} || is_empty_array_ref($o->{packages}{depslist})) {
- $o->{packages} = pkgs::psUsingHdlists($o->{prefix}, $o->{method});
+ my $cdrom;
+ ($o->{packages}, my $suppl_CDs) = pkgs::psUsingHdlists($o->{prefix}, $o->{method});
+
+ #- ask whether there are supplementary CDs
+ SUPPL: {
+ if ($suppl_CDs && !$o->{isUpgrade}
+ && $o->ask_yesorno('', N("Do you have a supplementary CD to install?"), 0))
+ {
+ #- by convention, the media names for suppl. CDs match /^\d+s$/
+ my $medium = '1s'; #- supplement 1
+ local $::isWizard = 0;
+ local $o->{method} = 'cdrom';
+ (my $cdromdev) = detect_devices::cdroms();
+ last SUPPL if !$cdromdev;
+ $cdrom = $cdromdev->{device};
+ my $dev = devices::make($cdrom);
+ ejectCdrom($cdrom);
+ if ($o->ask_okcancel('', N("Insert the CD"), 1)) {
+ mountCdrom("/mnt/cdrom", $cdrom);
+ log::l($@) if $@;
+ useMedium($medium);
+ my $supplmedium = pkgs::psUsingHdlist(
+ $o->{prefix}, # /mnt
+ 'cdrom',
+ $o->{packages},
+ "hdlist$medium.cz",
+ $medium,
+ 'Mandrake/RPMS',
+ "Supplementary CD $medium",
+ 1, # selected
+ "/mnt/cdrom/Mandrake/base/hdlist$medium.cz",
+ );
+ if ($supplmedium) {
+ log::l("read suppl hdlist");
+ $supplmedium->{prefix} = "removable://mnt/cdrom"; #- pour install_urpmi
+ $supplmedium->{selected} = 1;
+ $supplmedium->{method} = 'cdrom';
+ } else {
+ log::l("no suppl hdlist");
+ }
+ #- TODO loop if there are several supplementary CDs
+ # ++$medium; $medium .= "s";
+ }
+ } else {
+ $suppl_CDs = 0;
+ }
+ }
#- open rpm db according to right mode needed.
$o->{packages}{rpmdb} ||= pkgs::rpmDbOpen($o->{prefix}, $rebuild_needed);
@@ -357,12 +415,36 @@ sub setPackages {
pkgs::packageByName($o->{packages}, 'basesystem') || die("missing basesystem package"), 1);
#- must be done after getProvides
- pkgs::read_rpmsrate($o->{packages}, getFile("Mandrake/base/rpmsrate"));
- ($o->{compssUsers}, $o->{compssUsersSorted}) = pkgs::readCompssUsers($o->{meta_class});
+ #- if there is a supplementary CD, override the rpmsrate/compssUsers
+ pkgs::read_rpmsrate(
+ $o->{packages},
+ getFile($suppl_CDs ? "/mnt/cdrom/Mandrake/base/rpmsrate" : "Mandrake/base/rpmsrate")
+ );
+ ($o->{compssUsers}, $o->{compssUsersSorted}) = pkgs::readCompssUsers(
+ $o->{meta_class},
+ $suppl_CDs ? "/mnt/cdrom/Mandrake/base/compssUsers" : "",
+ );
#- preselect default_packages and compssUsersChoices.
setDefaultPackages($o);
pkgs::selectPackage($o->{packages}, pkgs::packageByName($o->{packages}, $_) || next) foreach @{$o->{default_packages}};
+
+ #- umount supplementary CD. Will re-ask for it later
+ if ($suppl_CDs) {
+ getFile("XXX"); #- close still opened filehandles
+ log::l("Umounting suppl. CD");
+ eval { fs::umount("/mnt/cdrom") };
+ #- re-mount CD 1 if this was a cdrom install
+ if ($o->{method} eq 'cdrom') {
+ eval {
+ my $dev = detect_devices::tryOpen($cdrom);
+ ioctl($dev, c::CDROMEJECT(), 1);
+ };
+ $o->ask_warn('', N("Insert the CD 1 again"));
+ mountCdrom("/tmp/image", $cdrom);
+ $asked_medium = 1;
+ }
+ }
} else {
#- this has to be done to make sure necessary files for urpmi are
#- present.
@@ -588,7 +670,8 @@ sub install_urpmi {
cdrom => "removable://mnt/cdrom" }}{$method} ||
#- for live_update or live_install script.
readlink("/tmp/image/Mandrake") =~ m,^(/.*)/Mandrake/*$, && "removable:/$1") . "/$_->{rpmsdir}";
- my $need_list = $dir =~ m,^(?:[^:]*://[^/:\@]*:[^/:\@]+\@|.*%{),; #- use list file only if visible password or macro.
+ #- use list file only if visible password or macro.
+ my $need_list = $dir =~ m,^(?:[^:]*://[^/:\@]*:[^/:\@]+\@|.*%{),; #- }
#- build a list file if needed.
if ($need_list) {
@@ -596,7 +679,7 @@ sub install_urpmi {
open(my $LIST, ">$prefix/var/lib/urpmi/list.$name") or log::l("failed to write list.$name");
umask $mask;
- #- build list file using internal data, synthesis file should exists.
+ #- build list file using internal data, synthesis file should exist.
if ($_->{end} > $_->{start}) {
#- WARNING this method of build only works because synthesis (or hdlist)
#- has been read.
@@ -640,7 +723,7 @@ sub install_urpmi {
} else {
$with = $_->{rpmsdir};
$with =~ s|/[^/]*%{ARCH}.*||;
- $with =~ s|/+|/|g; $with =~ s|/$||; $with =~ s|[^/]||g; $with =~ s|/|../|g;
+ $with =~ s|/+|/|g; $with =~ s|/$||; $with =~ s|[^/]||g; $with =~ s!/!../!g;
$with .= "../Mandrake/base/$_->{hdlist}";
}
diff --git a/perl-install/pkgs.pm b/perl-install/pkgs.pm
index 618ef63b9..815ce25bc 100644
--- a/perl-install/pkgs.pm
+++ b/perl-install/pkgs.pm
@@ -1,6 +1,5 @@
package pkgs; # $Id$
-use diagnostics;
use strict;
use MDK::Common::System;
@@ -85,6 +84,11 @@ sub extractHeaders {
}
}
+sub isSupplCDMedium($) {
+ my ($medium) = @_;
+ $medium->{method} eq 'cdrom' && $medium->{medium} =~ /^\d+s$/;
+}
+
#- TODO BEFORE TODO
#- size and correction size functions for packages.
my $B = 1.20873;
@@ -371,6 +375,7 @@ sub psUsingHdlists {
my ($prefix, $method) = @_;
my $listf = install_any::getFile('Mandrake/base/hdlists') or die "no hdlists found";
my $packages = new URPM;
+ my $suppl_CDs = 0;
#- add additional fields used by DrakX.
@$packages{qw(count mediums)} = (0, {});
@@ -381,6 +386,9 @@ sub psUsingHdlists {
chomp;
s/\s*#.*$//;
/^\s*$/ and next;
+ #- we'll ask afterwards for supplementary CDs, if the hdlists file contains
+ #- a line that begins with "suppl"
+ if (/^suppl/) { $suppl_CDs = 1; next }
m/^\s*(noauto:)?(hdlist\S*\.cz2?)\s+(\S+)\s*(.*)$/ or die qq(invalid hdlist description "$_" in hdlists file);
#- make sure the first medium is always selected!
@@ -393,7 +401,7 @@ sub psUsingHdlists {
log::l("psUsingHdlists read " . int(@{$packages->{depslist}}) .
" headers on " . int(keys %{$packages->{mediums}}) . " hdlists");
- $packages;
+ return ($packages, $suppl_CDs);
}
sub psUsingHdlist {
@@ -448,7 +456,10 @@ sub psUsingHdlist {
#- avoid using more than one medium if Cd is not ejectable.
#- but keep all medium here so that urpmi has the whole set.
- $m->{ignored} ||= install_any::method_allows_medium_change($method) && $medium > 1 && !common::usingRamdisk();
+ $m->{ignored} ||= (
+ install_any::method_allows_medium_change($method) && $medium > 1 #- first cdrom
+ && $medium !~ /^\d+s/ #- not a suppl. CD
+ && !common::usingRamdisk());
#- parse synthesis (if available) of directly hdlist (with packing).
if ($m->{ignored}) {
@@ -560,9 +571,9 @@ sub read_rpmsrate {
}
sub readCompssUsers {
- my ($meta_class) = @_;
+ my ($meta_class, $file) = @_;
- my $file = 'Mandrake/base/compssUsers';
+ $file = 'Mandrake/base/compssUsers' if !$file;
my $f = $meta_class && install_any::getFile("$file.$meta_class") || install_any::getFile($file) or die "can't find $file";
readCompssUsers_raw($f);
}
@@ -920,13 +931,28 @@ sub installTransactionClosure {
$medium or return (); #- no more medium usable -> end of installation by returning empty list.
($min_id, $max_id) = ($medium->{start}, $medium->{end});
+ #- Supplementary CD : switch temporarily to "cdrom" method
+ my $suppl_CD = isSupplCDMedium($medium);
+ local $::o->{method} = do {
+ my $cdrom;
+ cat_("/proc/mounts") =~ m,(/(?:dev|tmp)/\S+)\s+(?:/mnt/cdrom|/tmp/image), and $cdrom = $1;
+ if (!defined $cdrom) {
+ (my $cdromdev) = detect_devices::cdroms();
+ $cdrom = $cdromdev->{device};
+ log::l("cdrom redetected at $cdrom");
+ my $dev = devices::make($cdrom);
+ install_any::ejectCdrom($cdrom) if $::o->{method} eq 'cdrom'; # will umount /tmp/image
+ install_any::mountCdrom("/mnt/cdrom", $cdrom);
+ } else { log::l("cdrom already found at $cdrom") }
+ 'cdrom';
+ } if $suppl_CD;
#- it is sure at least one package will be installed according to medium chosen.
install_any::useMedium($medium->{medium});
if (install_any::method_allows_medium_change($medium->{method})) {
my $pkg = $packages->{depslist}[$l[0]];
#- force changeCD callback to be called from main process.
- install_any::getFile($pkg->filename, $medium->{descr});
+ install_any::getFile($pkg->filename, $medium->{descr}, $suppl_CD ? '/mnt/cdrom' : undef);
#- close opened handle above.
install_any::getFile('XXX');
}
@@ -1062,7 +1088,8 @@ sub install($$$;$$) {
my $trans = $db->create_transaction($prefix);
if ($retry_pkg) {
log::l("opened rpm database for retry transaction of 1 package only");
- $trans->add($retry_pkg, $isUpgrade && allowedToUpgrade($retry_pkg->name));
+ $trans->add($retry_pkg, $isUpgrade && allowedToUpgrade($retry_pkg->name))
+ or log::l("add failed for ".$retry_pkg->fullname);
} else {
log::l("opened rpm database for transaction of " . int(@transToInstall) .
" new packages, still $nb after that to do");
@@ -1082,7 +1109,12 @@ sub install($$$;$$) {
my $medium = packageMedium($packages, $pkg);
my $f = $pkg && $pkg->filename;
print $LOG "$f\n";
- $fd = install_any::getFile($f, $medium->{descr});
+ if (isSupplCDMedium($medium)) {
+ #- supplementary CD already mounted in /mnt/cdrom
+ $fd = install_any::getFile($f, $medium->{descr}, '/mnt/cdrom');
+ } else {
+ $fd = install_any::getFile($f, $medium->{descr});
+ }
$fd ? fileno $fd : -1;
}, callback_close => sub {
my ($data, $_type, $id) = @_;
@@ -1176,6 +1208,7 @@ sub install($$$;$$) {
log::l("closing install.log file");
close $LOG;
+ eval { fs::umount("/mnt/cdrom") };
cleanHeaders($prefix);