From 1fc8e9eee4d6a81f907b399034f6f82da2e98140 Mon Sep 17 00:00:00 2001 From: Julian Andres Klode Date: Mon, 10 Mar 2025 18:37:55 +0100 Subject: edsp: Set Forbid-New-Install/Forbid-Remove: no if other is set The upgrade code may also set Upgrade: yes, and this sets both to yes, so `apt upgrade` dumps behave like `apt-get upgrade` ones, which of course is not intentional. moo --- .../test-external-dependency-solver-protocol | 37 ++++++++++++++++++++++ 1 file changed, 37 insertions(+) (limited to 'test/integration') diff --git a/test/integration/test-external-dependency-solver-protocol b/test/integration/test-external-dependency-solver-protocol index bc32886c5..cbfd7b739 100755 --- a/test/integration/test-external-dependency-solver-protocol +++ b/test/integration/test-external-dependency-solver-protocol @@ -136,6 +136,43 @@ testsuccess test -s "$APT_EDSP_DUMP_FILENAME" testequal 'Install: awesomecoolstuff:i386' grep :i386 "$APT_EDSP_DUMP_FILENAME" testfailure grep -e ':amd64' -e 'Architecture: any' "$APT_EDSP_DUMP_FILENAME" +rm -f "$APT_EDSP_DUMP_FILENAME" +testfailure apt upgrade --solver dump +testsuccess test -s "$APT_EDSP_DUMP_FILENAME" +testsuccessequal "Request: EDSP 0.5 +Architecture: amd64 +Architectures: amd64 i386 +Machine-ID: 912e43bd1c1d4ba481f9f8ccab25f9ee +Upgrade-All: yes +Upgrade: yes +Forbid-New-Install: no +Forbid-Remove: yes +Solver: dump" awk '/^$/ {exit} {print}' "$APT_EDSP_DUMP_FILENAME" + +rm -f "$APT_EDSP_DUMP_FILENAME" +testfailure aptget upgrade --solver dump +testsuccess test -s "$APT_EDSP_DUMP_FILENAME" +testsuccessequal "Request: EDSP 0.5 +Architecture: amd64 +Architectures: amd64 i386 +Machine-ID: 912e43bd1c1d4ba481f9f8ccab25f9ee +Upgrade-All: yes +Upgrade: yes +Forbid-New-Install: yes +Forbid-Remove: yes +Solver: dump" awk '/^$/ {exit} {print}' "$APT_EDSP_DUMP_FILENAME" + +rm -f "$APT_EDSP_DUMP_FILENAME" +testfailure aptget dist-upgrade --solver dump +testsuccess test -s "$APT_EDSP_DUMP_FILENAME" +testsuccessequal "Request: EDSP 0.5 +Architecture: amd64 +Architectures: amd64 i386 +Machine-ID: 912e43bd1c1d4ba481f9f8ccab25f9ee +Upgrade-All: yes +Dist-Upgrade: yes +Solver: dump" awk '/^$/ {exit} {print}' "$APT_EDSP_DUMP_FILENAME" + testsuccess aptget dist-upgrade -s testsuccess aptget dist-upgrade -s --solver apt -- cgit v1.2.3-70-g09d2 From 8a6b694108f41afd1e6cdba4c91481697f9b3004 Mon Sep 17 00:00:00 2001 From: Julian Andres Klode Date: Mon, 10 Mar 2025 22:05:52 +0100 Subject: solver3: Correctly determine 'same' or groups We incorrectly used the DependencyData of the first or group member, however that only checked that the first or group member was the same and that both either had a next member or not. --- apt-pkg/solver3.cc | 38 ++++++++++++++++++++------- test/integration/test-solver3-similar-depends | 18 +++++++++++++ 2 files changed, 47 insertions(+), 9 deletions(-) create mode 100755 test/integration/test-solver3-similar-depends (limited to 'test/integration') diff --git a/apt-pkg/solver3.cc b/apt-pkg/solver3.cc index fde1d192b..739309c59 100644 --- a/apt-pkg/solver3.cc +++ b/apt-pkg/solver3.cc @@ -634,6 +634,23 @@ bool APT::Solver::Propagate() return true; } +static bool SameOrGroup(pkgCache::DepIterator a, pkgCache::DepIterator b) +{ + while (1) + { + if (a->DependencyData != b->DependencyData) + return false; + + // At least one has reached the end, break + if (not(a->CompareOp & pkgCache::Dep::Or) || not(b->CompareOp & pkgCache::Dep::Or)) + break; + + ++a, ++b; + } + // Fully iterated over a and b + return not(a->CompareOp & pkgCache::Dep::Or) && not(b->CompareOp & pkgCache::Dep::Or); +} + const APT::Solver::Clause *APT::Solver::RegisterClause(Clause &&clause) { auto &clauses = (*this)[clause.reason].clauses; @@ -701,8 +718,8 @@ void APT::Solver::Discover(Var var) // This dependency is shared across all versions, skip it. if (auto &pkgClauses = (*this)[Ver.ParentPkg()].clauses; - std::any_of(pkgClauses.begin(), pkgClauses.end(), [start](auto &c) - { return c->dep && c->dep->DependencyData == start->DependencyData; })) + std::any_of(pkgClauses.begin(), pkgClauses.end(), [this, start](auto &c) + { return c->dep && SameOrGroup(start, pkgCache::DepIterator(cache, c->dep)); })) continue; auto clause = TranslateOrGroup(start, end, Var(Ver)); @@ -723,18 +740,21 @@ void APT::Solver::RegisterCommonDependencies(pkgCache::PkgIterator Pkg) { for (auto dep = Pkg.VersionList().DependsList(); not dep.end();) { - pkgCache::DepIterator start; - pkgCache::DepIterator end; + pkgCache::DepIterator start, end; dep.GlobOr(start, end); // advances dep bool allHaveDep = true; - for (auto ver = Pkg.VersionList()++; not ver.end(); ver++) + for (auto ver = Pkg.VersionList()++; allHaveDep && not ver.end(); ver++) { bool haveDep = false; - for (auto otherDep = ver.DependsList(); not haveDep && not otherDep.end(); otherDep++) - haveDep = otherDep->DependencyData == start->DependencyData; - if (!haveDep) - allHaveDep = haveDep; + for (auto otherDep = ver.DependsList(); not haveDep && not otherDep.end();) + { + pkgCache::DepIterator otherStart, otherEnd; + otherDep.GlobOr(otherStart, otherEnd); // advances other dep + haveDep = SameOrGroup(start, otherStart); + } + if (not haveDep) + allHaveDep = false; } if (not allHaveDep) continue; diff --git a/test/integration/test-solver3-similar-depends b/test/integration/test-solver3-similar-depends new file mode 100755 index 000000000..a301b9ac5 --- /dev/null +++ b/test/integration/test-solver3-similar-depends @@ -0,0 +1,18 @@ +#!/bin/sh +set -e + +TESTDIR="$(readlink -f "$(dirname "$0")")" +. "$TESTDIR/framework" +setupenvironment +configarchitecture 'amd64' + +insertpackage 'installed' 'a' 'all' '2' 'Depends: a|b' +insertpackage 'unstable' 'a' 'all' '3' 'Depends: a|c' + +setupaptarchive +testsuccess apt install -o debug::apt::solver=3 a -s --solver 3.0 +cp rootdir/tmp/testsuccess.output log +msgmsg "Test that æ|b and a|c are different or groups" +testsuccess grep "Found dependency critical a:amd64=2 -> a:amd64" log +testsuccess grep "Found dependency critical a:amd64=3 -> a:amd64" log + -- cgit v1.2.3-70-g09d2