From 1a22e16a1ebf08243c1836e1c593cb966cae4850 Mon Sep 17 00:00:00 2001 From: Michael Vogt Date: Tue, 3 Dec 2013 21:49:02 +0100 Subject: proof-of-concept for fixing debian #731102 --- apt-pkg/indexrecords.cc | 5 ++++ apt-pkg/indexrecords.h | 1 + apt-pkg/metaindex.h | 3 ++- cmdline/apt-get.cc | 66 +++++++++++++++++++++++++++++++++++++++---------- 4 files changed, 61 insertions(+), 14 deletions(-) diff --git a/apt-pkg/indexrecords.cc b/apt-pkg/indexrecords.cc index 8a72ca151..f8097c3c6 100644 --- a/apt-pkg/indexrecords.cc +++ b/apt-pkg/indexrecords.cc @@ -27,6 +27,11 @@ string indexRecords::GetDist() const return this->Dist; } +string indexRecords::GetSuite() const +{ + return this->Suite; +} + bool indexRecords::CheckDist(const string MaybeDist) const { return (this->Dist == MaybeDist diff --git a/apt-pkg/indexrecords.h b/apt-pkg/indexrecords.h index a98b939bc..d003ec0fa 100644 --- a/apt-pkg/indexrecords.h +++ b/apt-pkg/indexrecords.h @@ -46,6 +46,7 @@ class indexRecords virtual bool Load(std::string Filename); std::string GetDist() const; + std::string GetSuite() const; time_t GetValidUntil() const; virtual bool CheckDist(const std::string MaybeDist) const; std::string GetExpectedDist() const; diff --git a/apt-pkg/metaindex.h b/apt-pkg/metaindex.h index 5783735ff..0c2600c3a 100644 --- a/apt-pkg/metaindex.h +++ b/apt-pkg/metaindex.h @@ -48,7 +48,8 @@ class metaIndex virtual ~metaIndex() { if (Indexes == 0) return; - for (std::vector::iterator I = (*Indexes).begin(); I != (*Indexes).end(); ++I) + for (std::vector::iterator I = (*Indexes).begin(); + I != (*Indexes).end(); ++I) delete *I; delete Indexes; } diff --git a/cmdline/apt-get.cc b/cmdline/apt-get.cc index 912b2d609..2370318e8 100644 --- a/cmdline/apt-get.cc +++ b/cmdline/apt-get.cc @@ -50,6 +50,8 @@ #include #include #include +#include +#include #include #include @@ -135,11 +137,12 @@ bool TryToInstallBuildDep(pkgCache::PkgIterator Pkg,pkgCacheFile &Cache, /* */ pkgSrcRecords::Parser *FindSrc(const char *Name,pkgRecords &Recs, pkgSrcRecords &SrcRecs,string &Src, - pkgDepCache &Cache) + CacheFile &CacheFile) { string VerTag; string DefRel = _config->Find("APT::Default-Release"); string TmpSrc = Name; + pkgDepCache *Cache = CacheFile.GetDepCache(); // extract the version/release from the pkgname const size_t found = TmpSrc.find_last_of("/="); @@ -155,7 +158,7 @@ pkgSrcRecords::Parser *FindSrc(const char *Name,pkgRecords &Recs, install a version and determine the source package name, then look in the archive for a source package of the same name. */ bool MatchSrcOnly = _config->FindB("APT::Get::Only-Source"); - const pkgCache::PkgIterator Pkg = Cache.FindPkg(TmpSrc); + const pkgCache::PkgIterator Pkg = Cache->FindPkg(TmpSrc); if (MatchSrcOnly == false && Pkg.end() == false) { if(VerTag.empty() == false || DefRel.empty() == false) @@ -180,7 +183,7 @@ pkgSrcRecords::Parser *FindSrc(const char *Name,pkgRecords &Recs, } // We match against a concrete version (or a part of this version) if (VerTag.empty() == false && - (fuzzy == true || Cache.VS().CmpVersion(VerTag, Ver.VerStr()) != 0) && // exact match + (fuzzy == true || Cache->VS().CmpVersion(VerTag, Ver.VerStr()) != 0) && // exact match (fuzzy == false || strncmp(VerTag.c_str(), Ver.VerStr(), VerTag.size()) != 0)) // fuzzy match continue; @@ -217,22 +220,24 @@ pkgSrcRecords::Parser *FindSrc(const char *Name,pkgRecords &Recs, if (Src.empty() == false) break; } +#if 0 if (Src.empty() == true) { // Sources files have no codename information if (VerTag.empty() == true && DefRel.empty() == false) { - _error->Error(_("Ignore unavailable target release '%s' of package '%s'"), DefRel.c_str(), TmpSrc.c_str()); - return 0; + _error->Warning(_("Ignore unavailable target release '%s' of package '%s'"), DefRel.c_str(), TmpSrc.c_str()); + return 0; } } +#endif } if (Src.empty() == true) { // if we don't have found a fitting package yet so we will // choose a good candidate and proceed with that. // Maybe we will find a source later on with the right VerTag - pkgCache::VerIterator Ver = Cache.GetCandidateVer(Pkg); + pkgCache::VerIterator Ver = Cache->GetCandidateVer(Pkg); if (Ver.end() == false) { pkgRecords::Parser &Parse = Recs.Lookup(Ver.FileList()); @@ -262,6 +267,7 @@ pkgSrcRecords::Parser *FindSrc(const char *Name,pkgRecords &Recs, pkgSrcRecords::Parser *Last = 0; unsigned long Offset = 0; string Version; + string FoundRel; /* Iterate over all of the hits, which includes the resulting binary packages in the search */ @@ -273,26 +279,60 @@ pkgSrcRecords::Parser *FindSrc(const char *Name,pkgRecords &Recs, { const string Ver = Parse->Version(); + + // find release + const pkgIndexFile& SI = Parse->Index(); + pkgSourceList *SrcList = CacheFile.GetSourceList(); + for (pkgSourceList::const_iterator S = SrcList->begin(); + S != SrcList->end(); ++S) + { + vector *Indexes = (*S)->GetIndexFiles(); + for (vector::const_iterator IF = Indexes->begin(); + IF != Indexes->end(); ++IF) + { + if (&SI == (*IF)) + { + std::string dirname = _config->FindDir("Dir::State::lists"); + std::string path = dirname + URItoFileName((*S)->GetURI()) + "dists_" + (*S)->GetDist() + "_Release"; + indexRecords records; + records.Load(path); + if (records.GetSuite() == DefRel) + { + ioprintf(clog, "Selectied version '%s' (%s) for %s\n", + Ver.c_str(), DefRel.c_str(), Src.c_str()); + Last = Parse; + Offset = Parse->Offset(); + Version = Ver; + FoundRel = DefRel; + break; + } + } + } + } + if (DefRel.empty() == false && (DefRel == FoundRel)) + break; + // Ignore all versions which doesn't fit if (VerTag.empty() == false && - Cache.VS().CmpVersion(VerTag, Ver) != 0) // exact match + Cache->VS().CmpVersion(VerTag, Ver) != 0) // exact match continue; // Newer version or an exact match? Save the hit - if (Last == 0 || Cache.VS().CmpVersion(Version,Ver) < 0) { + if (Last == 0 || Cache->VS().CmpVersion(Version,Ver) < 0) { Last = Parse; Offset = Parse->Offset(); Version = Ver; } // was the version check above an exact match? If so, we don't need to look further - if (VerTag.empty() == false && VerTag.size() == Ver.size()) + if (VerTag.empty() == false && (VerTag == Ver)) + { + std::cerr << "meep" << std::endl; break; + } } if (Last != 0 || VerTag.empty() == true) break; - //if (VerTag.empty() == false && Last == 0) - _error->Error(_("Ignore unavailable version '%s' of package '%s'"), VerTag.c_str(), TmpSrc.c_str()); return 0; } @@ -628,7 +668,7 @@ bool DoSource(CommandLine &CmdL) for (const char **I = CmdL.FileList + 1; *I != 0; I++, J++) { string Src; - pkgSrcRecords::Parser *Last = FindSrc(*I,Recs,SrcRecs,Src,*Cache); + pkgSrcRecords::Parser *Last = FindSrc(*I,Recs,SrcRecs,Src,Cache); if (Last == 0) { delete[] Dsc; @@ -925,7 +965,7 @@ bool DoBuildDep(CommandLine &CmdL) for (const char **I = CmdL.FileList + 1; *I != 0; I++, J++) { string Src; - pkgSrcRecords::Parser *Last = FindSrc(*I,Recs,SrcRecs,Src,*Cache); + pkgSrcRecords::Parser *Last = FindSrc(*I,Recs,SrcRecs,Src,Cache); if (Last == 0) return _error->Error(_("Unable to find a source package for %s"),Src.c_str()); -- cgit v1.2.3