summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJulian Andres Klode <jak@debian.org>2021-11-23 15:33:54 +0000
committerJulian Andres Klode <jak@debian.org>2021-11-23 15:33:54 +0000
commit383d168b70706facfef5c8736300112cbe08a03e (patch)
tree72dab24369cf26bc9d7a4e30986b25a18a2f002a
parentd08b87a711e4aad3e0c9b8777262cba6bd755099 (diff)
parentdd81b736095f244454c7f179e67f21c08f3fbce9 (diff)
Merge branch 'pu/reltagmatchforsource' into 'main'
Support more than exact release matches in 'source' See merge request apt-team/apt!201
-rw-r--r--apt-pkg/versionmatch.cc100
-rw-r--r--apt-pkg/versionmatch.h1
-rw-r--r--apt-private/private-source.cc9
-rwxr-xr-xtest/integration/test-bug-998444-regex-as-target-release65
4 files changed, 127 insertions, 48 deletions
diff --git a/apt-pkg/versionmatch.cc b/apt-pkg/versionmatch.cc
index 82590edfe..83a969c4a 100644
--- a/apt-pkg/versionmatch.cc
+++ b/apt-pkg/versionmatch.cc
@@ -228,64 +228,80 @@ bool pkgVersionMatch::ExpressionMatches(const std::string& pattern, const char *
/*}}}*/
// VersionMatch::FileMatch - Match against an index file /*{{{*/
// ---------------------------------------------------------------------
-/* This matcher checks against the release file and the origin location
+/* This matcher checks against the release file and the origin location
to see if the constraints are met. */
-bool pkgVersionMatch::FileMatch(pkgCache::PkgFileIterator File)
+bool pkgVersionMatch::FileMatch(pkgCache::RlsFileIterator const &File)
{
if (Type == Release)
{
- if (MatchAll == true)
+ if (MatchAll)
return true;
-/* cout << RelVerStr << ',' << RelOrigin << ',' << RelArchive << ',' << RelLabel << endl;
- cout << File.Version() << ',' << File.Origin() << ',' << File.Archive() << ',' << File.Label() << endl;*/
-
- if (RelVerStr.empty() == true && RelOrigin.empty() == true &&
- RelArchive.empty() == true && RelLabel.empty() == true &&
- RelRelease.empty() == true && RelCodename.empty() == true &&
- RelComponent.empty() == true && RelArchitecture.empty() == true)
+ if (RelVerStr.empty() && RelOrigin.empty() &&
+ RelArchive.empty() && RelLabel.empty() &&
+ RelRelease.empty() && RelCodename.empty() &&
+ RelComponent.empty() && RelArchitecture.empty())
return false;
- if (RelVerStr.empty() == false)
- if (MatchVer(File.Version(),RelVerStr,RelVerPrefixMatch) == false &&
- ExpressionMatches(RelVerStr, File.Version()) == false)
- return false;
- if (RelOrigin.empty() == false)
- if (!ExpressionMatches(RelOrigin,File.Origin()))
- return false;
- if (RelArchive.empty() == false)
- if (!ExpressionMatches(RelArchive,File.Archive()))
- return false;
- if (RelCodename.empty() == false)
- if (!ExpressionMatches(RelCodename,File.Codename()))
- return false;
- if (RelRelease.empty() == false)
- if (!ExpressionMatches(RelRelease,File.Archive()) &&
- !ExpressionMatches(RelRelease,File.Codename()))
- return false;
- if (RelLabel.empty() == false)
- if (!ExpressionMatches(RelLabel,File.Label()))
- return false;
- if (RelComponent.empty() == false)
- if (!ExpressionMatches(RelComponent,File.Component()))
- return false;
- if (RelArchitecture.empty() == false)
- if (!ExpressionMatches(RelArchitecture,File.Architecture()))
- return false;
+ if (not RelVerStr.empty() && not MatchVer(File.Version(), RelVerStr, RelVerPrefixMatch) &&
+ not ExpressionMatches(RelVerStr, File.Version()))
+ return false;
+ if (not RelOrigin.empty() && not ExpressionMatches(RelOrigin, File.Origin()))
+ return false;
+ if (not RelArchive.empty() && not ExpressionMatches(RelArchive, File.Archive()))
+ return false;
+ if (not RelCodename.empty() && not ExpressionMatches(RelCodename, File.Codename()))
+ return false;
+ if (not RelRelease.empty() && not ExpressionMatches(RelRelease, File.Archive()) &&
+ not ExpressionMatches(RelRelease, File.Codename()))
+ return false;
+ if (not RelLabel.empty() && not ExpressionMatches(RelLabel, File.Label()))
+ return false;
return true;
}
if (Type == Origin)
{
- if (OrSite.empty() == false) {
- if (File.Site() == NULL)
- return false;
- }
- else if (File->Release == 0)// only 'bad' files like dpkg.status file has no release file
+ if (not OrSite.empty() && File.Site() == nullptr)
return false;
- return (ExpressionMatches(OrSite, File.Site())); /* both strings match */
+ return ExpressionMatches(OrSite, File.Site()); /* both strings match */
}
return false;
}
+bool pkgVersionMatch::FileMatch(pkgCache::PkgFileIterator File)
+{
+ if (auto const RlsFile = File.ReleaseFile(); not RlsFile.end())
+ {
+ if (not FileMatch(RlsFile))
+ return false;
+ }
+ else if (Type == Release)
+ {
+ // only 'bad' files like dpkg.status file have no release file
+ // those reuse the Component of te PkgFile to store the Archive "now".
+ if (not RelArchive.empty() && not ExpressionMatches(RelArchive, File.Component()))
+ return false;
+ if (not RelRelease.empty() && not ExpressionMatches(RelRelease, File.Component()))
+ return false;
+ if (not RelOrigin.empty() || not RelLabel.empty() ||
+ not RelVerStr.empty() || not RelCodename.empty())
+ return false;
+ }
+ else
+ return false;
+
+ if (Type == Release)
+ {
+ if (MatchAll)
+ return true;
+
+ if (not RelComponent.empty() && not ExpressionMatches(RelComponent, File.Component()))
+ return false;
+ if (not RelArchitecture.empty() && not ExpressionMatches(RelArchitecture, File.Architecture()))
+ return false;
+ }
+
+ return true;
+}
/*}}}*/
diff --git a/apt-pkg/versionmatch.h b/apt-pkg/versionmatch.h
index 0f84f8dfa..faf1fd436 100644
--- a/apt-pkg/versionmatch.h
+++ b/apt-pkg/versionmatch.h
@@ -68,6 +68,7 @@ class APT_PUBLIC pkgVersionMatch
static bool ExpressionMatches(const char *pattern, const char *string);
static bool ExpressionMatches(const std::string& pattern, const char *string);
bool FileMatch(pkgCache::PkgFileIterator File);
+ bool FileMatch(pkgCache::RlsFileIterator const &File);
pkgCache::VerIterator Find(pkgCache::PkgIterator Pkg);
bool VersionMatches(pkgCache::VerIterator Ver);
diff --git a/apt-private/private-source.cc b/apt-private/private-source.cc
index db96cb17f..f3ee0e594 100644
--- a/apt-private/private-source.cc
+++ b/apt-private/private-source.cc
@@ -243,6 +243,7 @@ static pkgSrcRecords::Parser *FindSrc(const char *Name,
unsigned long Offset = 0;
std::string Version;
pkgSourceList const * const SrcList = Cache.GetSourceList();
+ pkgVersionMatch RelTagMatch{RelTag, pkgVersionMatch::Release};
/* Iterate over all of the hits, which includes the resulting
binary packages in the search */
@@ -258,12 +259,8 @@ static pkgSrcRecords::Parser *FindSrc(const char *Name,
if (RelTag.empty() == false && UserRequestedVerTag.empty() == true)
{
pkgCache::RlsFileIterator const Rls = GetReleaseFileForSourceRecord(Cache, SrcList, Parse);
- if (Rls.end() == false)
- {
- if ((Rls->Archive != 0 && RelTag != Rls.Archive()) &&
- (Rls->Codename != 0 && RelTag != Rls.Codename()))
- continue;
- }
+ if (not Rls.end() && not RelTagMatch.FileMatch(Rls))
+ continue;
}
// Ignore all versions which doesn't fit
diff --git a/test/integration/test-bug-998444-regex-as-target-release b/test/integration/test-bug-998444-regex-as-target-release
new file mode 100755
index 000000000..97970bccd
--- /dev/null
+++ b/test/integration/test-bug-998444-regex-as-target-release
@@ -0,0 +1,65 @@
+#!/bin/sh
+set -e
+
+TESTDIR="$(readlink -f "$(dirname "$0")")"
+. "$TESTDIR/framework"
+setupenvironment
+configarchitecture 'amd64'
+
+addpackage() {
+ insertpackage "$@"
+ insertsource "$@"
+}
+
+addpackage 'stable' 'foo' 'all' '1'
+addpackage 'stable-security' 'foo' 'all' '1.1~security.1'
+addpackage 'stable-updates' 'foo' 'all' '2~stable.1'
+addpackage 'unstable' 'foo' 'all' '2'
+addpackage 'experimental' 'foo' 'all' '3'
+addpackage 'external' 'foo' 'all' '4'
+
+cat > rootdir/etc/apt/preferences <<EOF
+Package: *
+Pin: release a=external
+Pin-Priority: -10
+EOF
+
+setupaptarchive
+
+APTARCHIVE="file:${TMPWORKINGDIRECTORY}/aptarchive"
+
+testfoo() {
+ testsuccessequal "foo:
+ Installed: (none)
+ Candidate: $1
+ Version table:
+ 4 $2
+ $(printf '%3s' "$2") ${APTARCHIVE} external/main all Packages
+ 3 $3
+ $(printf '%3s' "$3") ${APTARCHIVE} experimental/main all Packages
+ 2 $4
+ $(printf '%3s' "$4") ${APTARCHIVE} unstable/main all Packages
+ 2~stable.1 $5
+ $(printf '%3s' "$5") ${APTARCHIVE} stable-updates/main all Packages
+ 1.1~security.1 $6
+ $(printf '%3s' "$6") ${APTARCHIVE} stable-security/main all Packages
+ 1 $7
+ $(printf '%3s' "$7") ${APTARCHIVE} stable/main all Packages" apt policy foo -t "$8"
+ testsuccessequal "'${APTARCHIVE}/pool/main/foo/foo_$(apthelper quote-string "${1}" '+~ ')_all.deb' foo_${1}_all.deb 42 SHA256:0000000000000000000000000000000000000000000000000000000000000000" apt download foo --print-uris -t "$8"
+ testsuccess apt source -t "$8" --print-uris foo
+ tail -n 2 rootdir/tmp/testsuccess.output | cut -d' ' -f 2 > aptsource.output
+ testfileequal 'aptsource.output' "foo_${9:-$1}.dsc
+foo_${9:-$1}.tar.gz"
+}
+testfoo '2' '-10' '1' '500' '500' '500' '500' '' '4'
+testfoo '2' '-10' '1' '990' '500' '500' '500' 'unstable' '2'
+testfoo '1' '-10' '1' '500' '500' '500' '990' 'stable'
+testfoo '2~stable.1' '-10' '1' '500' '990' '500' '500' 'stable-updates'
+testfoo '1.1~security.1' '-10' '1' '500' '500' '990' '500' 'stable-security'
+testfoo '4' '990' '1' '500' '500' '500' '500' 'a=external'
+testfoo '2' '-10' '1' '990' '990' '990' '990' '/stable/'
+testfoo '2~stable.1' '-10' '1' '500' '990' '990' '990' '/^stable/'
+testfoo '1.1~security.1' '-10' '1' '500' '500' '990' '990' '/^stable(|-security)$/'
+testfoo '2~stable.1' '-10' '1' '500' '990' '990' '500' '/^stable(-security|-updates)$/'
+testfoo '2~stable.1' '-10' '1' '500' '990' '990' '990' '/^stable(|-security|-updates)$/'
+testfoo '4' '990' '990' '990' '990' '990' '990' '/./'