summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMarc Espie <espie@cvs.openbsd.org>2004-12-19 14:47:34 +0000
committerMarc Espie <espie@cvs.openbsd.org>2004-12-19 14:47:34 +0000
commit161132942c7ffc3eaa5e23d828f5d9c0215fe9b8 (patch)
tree1f35ce618aea780d81b6cfd89f16811b585e91a4
parent9acb838f9be01dfdf751e853c93dd7a2f5d4134f (diff)
simplify solve_dependencies: always compute to_install array (it is
reasonably cheap). Remove else conditions, use next: after all, it's a simple pattern, try one solution after the other until one succeeds. Pass state to access replace: in that case, first try the list of packages to install/update so that we force them into proper order. Add a mark to handles for finished packages: with -r, we can no longer rely on installed packages to avoid doing the work twice.
-rw-r--r--usr.sbin/pkg_add/TODO6
-rw-r--r--usr.sbin/pkg_add/pkg_add90
2 files changed, 53 insertions, 43 deletions
diff --git a/usr.sbin/pkg_add/TODO b/usr.sbin/pkg_add/TODO
index 0cc58203730..4c41ec9dab8 100644
--- a/usr.sbin/pkg_add/TODO
+++ b/usr.sbin/pkg_add/TODO
@@ -1,11 +1,5 @@
- smart handling of .libs-*: pkg_add correctly discards potential conflicts.
It doesn't handle yet actual conflicts with .libs-*.
-- `global' replacement through pkg_add -r: the dependency solver needs
-to look into the command-line to figure out ways to solve dependencies:
-in effect, packages updated through -r must be sorted in dependency order.
-This does break pkg_add -n -r very thoroughly for complicated cases.
-And this is needed for 3.7 updates, if we don't want to have to update
-each package manually, in order.
- handle n-to-1 updates: mostly need to allow for a list of replaced packages.
The tricky part is that the replaced packages will often have
inter-dependencies, and we must ignore those inter-dependencies.
diff --git a/usr.sbin/pkg_add/pkg_add b/usr.sbin/pkg_add/pkg_add
index 2cc86fd8e92..6da3c84fbd4 100644
--- a/usr.sbin/pkg_add/pkg_add
+++ b/usr.sbin/pkg_add/pkg_add
@@ -1,7 +1,7 @@
#! /usr/bin/perl
# ex:ts=8 sw=4:
-# $OpenBSD: pkg_add,v 1.151 2004/12/19 14:09:53 espie Exp $
+# $OpenBSD: pkg_add,v 1.152 2004/12/19 14:47:33 espie Exp $
#
# Copyright (c) 2003-2004 Marc Espie <espie@openbsd.org>
#
@@ -167,10 +167,15 @@ sub pre_add($$)
sub solve_dependencies
{
- my ($verbose, $handle, @extra) = @_;
+ my ($state, $handle, @extra) = @_;
my $plist = $handle->{plist};
+ my $verbose = $state->{verbose};
my $to_register = $handle->{solved_dependencies} = {};
- my $to_install;
+ my $to_install = {};
+ for my $fullname (@extra) {
+ $to_install->{OpenBSD::PackageName::url2pkgname($fullname)} =
+ $fullname;
+ }
# do simple old style pkgdep first
my @deps = ();
@@ -182,46 +187,53 @@ sub solve_dependencies
}
for my $dep (@{$plist->{depend}}, @{$plist->{newdepend}}, @{$plist->{libdepend}}) {
next if defined $dep->{name} and $dep->{name} ne $plist->pkgname();
- my @candidates = OpenBSD::PkgSpec::match($dep->{pattern}, installed_packages());
- if (@candidates >= 1) {
+
+ my @candidates;
+ if ($state->{replace}) {
+ # try against list of packages to install
+ @candidates = OpenBSD::PkgSpec::match($dep->{pattern}, keys %{$to_install});
+ if (@candidates >= 1) {
+ push(@deps, $to_install->{$candidates[0]});
$to_register->{$candidates[0]} = 1;
- } else {
- if (!defined $to_install) {
- $to_install = {};
- for my $fullname (@extra) {
- $to_install->{OpenBSD::PackageName::url2pkgname($fullname)} = $fullname;
- }
+ next;
}
- # try against list of packages to install
- my @candidates = OpenBSD::PkgSpec::match($dep->{pattern}, keys %{$to_install});
+ }
+ @candidates = OpenBSD::PkgSpec::match($dep->{pattern}, installed_packages());
+ if (@candidates >= 1) {
+ $to_register->{$candidates[0]} = 1;
+ next;
+ }
+ if (!$state->{replace}) {
+ # try against list of packages to install
+ @candidates = OpenBSD::PkgSpec::match($dep->{pattern}, keys %{$to_install});
if (@candidates >= 1) {
push(@deps, $to_install->{$candidates[0]});
$to_register->{$candidates[0]} = 1;
- } else {
- # try with list of packages
- my @candidates = OpenBSD::PkgSpec::match($dep->{pattern}, OpenBSD::PackageLocator::available());
- # one single choice
- if (@candidates == 1) {
- push(@deps, $candidates[0]);
- $to_register->{$candidates[0]} = 1;
- } elsif (@candidates > 1) {
- # grab default if available
- if (grep {$_ eq $dep->{def}} @candidates) {
- push(@deps, $dep->{def});
- $to_register->{$dep->{def}} = 1;
- # grab first one otherwise
- } else {
- push(@deps, $candidates[0]);
- $to_register->{$candidates[0]} = 1;
- }
- } else {
- # can't get a list of packages, assume default
- # will be there.
- push(@deps, $dep->{def});
- $to_register->{$dep->{def}} = 1;
- }
+ next;
}
}
+ # try with list of available packages
+ @candidates = OpenBSD::PkgSpec::match($dep->{pattern}, OpenBSD::PackageLocator::available());
+ # one single choice
+ if (@candidates == 1) {
+ push(@deps, $candidates[0]);
+ $to_register->{$candidates[0]} = 1;
+ next;
+ }
+ if (@candidates > 1) {
+ # grab default if available
+ if (grep {$_ eq $dep->{def}} @candidates) {
+ push(@deps, $dep->{def});
+ $to_register->{$dep->{def}} = 1;
+ next;
+ }
+ push(@deps, $candidates[0]);
+ $to_register->{$candidates[0]} = 1;
+ }
+ # can't get a list of packages, assume default
+ # will be there.
+ push(@deps, $dep->{def});
+ $to_register->{$dep->{def}} = 1;
}
if ($verbose && %$to_register) {
@@ -558,6 +570,9 @@ sub install_package
return ();
}
}
+ if (defined $handle->{finished}) {
+ return ();
+ }
if ($plist->has('arch')) {
unless ($plist->{arch}->check($state->{arch})) {
print "$pkg is not for the right architecture\n";
@@ -565,7 +580,7 @@ sub install_package
}
}
if (!defined $handle->{solved_dependencies}) {
- my @deps = solve_dependencies($state->{verbose}, $handle, @todo);
+ my @deps = solve_dependencies($state, $handle, @todo);
if (@deps > 0) {
build_deptree($state, $pkg, @deps);
return (@deps, $pkg);
@@ -606,6 +621,7 @@ sub install_package
}
really_add($handle, $state);
OpenBSD::PkgCfl::register($plist, $state);
+ $handle->{finished} = 1;
return ();
}