X-Git-Url: https://git.saurik.com/apt.git/blobdiff_plain/a9e5851b62cde2945fe3af44438b202c04c6703f..bebdca4bf63ae661c60bc1e0f4e03e6bbb7a7cc5:/apt-pkg/pkgcachegen.cc diff --git a/apt-pkg/pkgcachegen.cc b/apt-pkg/pkgcachegen.cc index 402d2e4ff..ee65c94d1 100644 --- a/apt-pkg/pkgcachegen.cc +++ b/apt-pkg/pkgcachegen.cc @@ -1,6 +1,6 @@ // -*- mode: cpp; mode: fold -*- // Description /*{{{*/ -// $Id: pkgcachegen.cc,v 1.30 1999/02/23 06:50:36 jgg Exp $ +// $Id: pkgcachegen.cc,v 1.35 1999/04/18 06:36:36 jgg Exp $ /* ###################################################################### Package Cache Generator - Generator for the cache structure. @@ -422,6 +422,13 @@ bool pkgSrcCacheCheck(pkgSourceList &List) int Missing = 0; for (pkgSourceList::const_iterator I = List.begin(); I != List.end(); I++) { + // Only cache deb source types. + if (I->Type != pkgSourceList::Item::Deb) + { + Missing++; + continue; + } + string File = ListDir + URItoFileName(I->PackagesURI()); struct stat Buf; if (stat(File.c_str(),&Buf) != 0) @@ -431,7 +438,7 @@ bool pkgSrcCacheCheck(pkgSourceList &List) Missing++; } } - + // Open the source package cache if (FileExists(CacheFile) == false) return false; @@ -462,12 +469,16 @@ bool pkgSrcCacheCheck(pkgSourceList &List) return false; for (pkgCache::PkgFileIterator F(Cache); F.end() == false; F++) - { + { // Search for a match in the source list bool Bad = true; for (pkgSourceList::const_iterator I = List.begin(); I != List.end(); I++) { + // Only cache deb source types. + if (I->Type != pkgSourceList::Item::Deb) + continue; + string File = ListDir + URItoFileName(I->PackagesURI()); if (F.FileName() == File) { @@ -604,6 +615,70 @@ static bool pkgMergeStatus(OpProgress &Progress,pkgCacheGenerator &Gen, Progress.Progress(Pkg.Size()); } + return true; +} + /*}}}*/ +// GenerateSrcCache - Write the source package lists to the map /*{{{*/ +// --------------------------------------------------------------------- +/* This puts the source package cache into the given generator. */ +bool pkgGenerateSrcCache(pkgSourceList &List,OpProgress &Progress, + pkgCacheGenerator &Gen, + unsigned long &CurrentSize,unsigned long TotalSize) +{ + string ListDir = _config->FindDir("Dir::State::lists"); + + // Prepare the progress indicator + TotalSize = 0; + struct stat Buf; + for (pkgSourceList::const_iterator I = List.begin(); I != List.end(); I++) + { + string File = ListDir + URItoFileName(I->PackagesURI()); + if (stat(File.c_str(),&Buf) != 0) + continue; + TotalSize += Buf.st_size; + } + + if (pkgAddSourcesSize(TotalSize) == false) + return false; + + // Generate the pkg source cache + CurrentSize = 0; + for (pkgSourceList::const_iterator I = List.begin(); I != List.end(); I++) + { + // Only cache deb source types. + if (I->Type != pkgSourceList::Item::Deb) + continue; + + string File = ListDir + URItoFileName(I->PackagesURI()); + + if (FileExists(File) == false) + continue; + + FileFd Pkg(File,FileFd::ReadOnly); + debListParser Parser(Pkg); + Progress.OverallProgress(CurrentSize,TotalSize,Pkg.Size(),"Reading Package Lists"); + if (_error->PendingError() == true) + return _error->Error("Problem opening %s",File.c_str()); + CurrentSize += Pkg.Size(); + + Progress.SubProgress(0,I->PackagesInfo()); + if (Gen.SelectFile(File) == false) + return _error->Error("Problem with SelectFile %s",File.c_str()); + + if (Gen.MergeList(Parser) == false) + return _error->Error("Problem with MergeList %s",File.c_str()); + + // Check the release file + string RFile = ListDir + URItoFileName(I->ReleaseURI()); + if (FileExists(RFile) == true) + { + FileFd Rel(RFile,FileFd::ReadOnly); + if (_error->PendingError() == true) + return false; + Parser.LoadReleaseInfo(Gen.GetCurFile(),Rel); + } + } + return true; } /*}}}*/ @@ -618,68 +693,23 @@ bool pkgMakeStatusCache(pkgSourceList &List,OpProgress &Progress) string CacheFile = _config->FindFile("Dir::Cache::pkgcache"); bool SrcOk = pkgSrcCacheCheck(List); bool PkgOk = SrcOk && pkgPkgCacheCheck(CacheFile); - + // Rebuild the source and package caches if (SrcOk == false) { string SCacheFile = _config->FindFile("Dir::Cache::srcpkgcache"); - string ListDir = _config->FindDir("Dir::State::lists"); FileFd SCacheF(SCacheFile,FileFd::WriteEmpty); FileFd CacheF(CacheFile,FileFd::WriteEmpty); DynamicMMap Map(CacheF,MMap::Public); if (_error->PendingError() == true) return false; - + pkgCacheGenerator Gen(Map,Progress); - - // Prepare the progress indicator + unsigned long CurrentSize = 0; unsigned long TotalSize = 0; - struct stat Buf; - for (pkgSourceList::const_iterator I = List.begin(); I != List.end(); I++) - { - string File = ListDir + URItoFileName(I->PackagesURI()); - if (stat(File.c_str(),&Buf) != 0) - continue; - TotalSize += Buf.st_size; - } - - if (pkgAddSourcesSize(TotalSize) == false) + if (pkgGenerateSrcCache(List,Progress,Gen,CurrentSize,TotalSize) == false) return false; - // Generate the pkg source cache - unsigned long CurrentSize = 0; - for (pkgSourceList::const_iterator I = List.begin(); I != List.end(); I++) - { - string File = ListDir + URItoFileName(I->PackagesURI()); - - if (FileExists(File) == false) - continue; - - FileFd Pkg(File,FileFd::ReadOnly); - debListParser Parser(Pkg); - Progress.OverallProgress(CurrentSize,TotalSize,Pkg.Size(),"Reading Package Lists"); - if (_error->PendingError() == true) - return _error->Error("Problem opening %s",File.c_str()); - CurrentSize += Pkg.Size(); - - Progress.SubProgress(0,I->PackagesInfo()); - if (Gen.SelectFile(File) == false) - return _error->Error("Problem with SelectFile %s",File.c_str()); - - if (Gen.MergeList(Parser) == false) - return _error->Error("Problem with MergeList %s",File.c_str()); - - // Check the release file - string RFile = ListDir + URItoFileName(I->ReleaseURI()); - if (FileExists(RFile) == true) - { - FileFd Rel(RFile,FileFd::ReadOnly); - if (_error->PendingError() == true) - return false; - Parser.LoadReleaseInfo(Gen.GetCurFile(),Rel); - } - } - // Write the src cache Gen.GetCache().HeaderP->Dirty = false; if (SCacheF.Write(Map.Data(),Map.Size()) == false) @@ -721,3 +751,124 @@ bool pkgMakeStatusCache(pkgSourceList &List,OpProgress &Progress) return pkgMergeStatus(Progress,Gen,CurrentSize,TotalSize); } /*}}}*/ +// MakeStatusCacheMem - Returns a map for the status cache /*{{{*/ +// --------------------------------------------------------------------- +/* This creates a map object for the status cache. If the process has write + access to the caches then it is the same as MakeStatusCache, otherwise it + creates a memory block and puts the cache in there. */ +MMap *pkgMakeStatusCacheMem(pkgSourceList &List,OpProgress &Progress) +{ + /* If the cache file is writeable this is just a wrapper for + MakeStatusCache */ + string CacheFile = _config->FindFile("Dir::Cache::pkgcache"); + bool Writeable = access(CacheFile.c_str(),W_OK) == 0; + if (Writeable == true) + { + if (pkgMakeStatusCache(List,Progress) == false) + return 0; + + // Open the cache file + FileFd File(_config->FindFile("Dir::Cache::pkgcache"),FileFd::ReadOnly); + if (_error->PendingError() == true) + return 0; + + MMap *Map = new MMap(File,MMap::Public | MMap::ReadOnly); + if (_error->PendingError() == true) + { + delete Map; + return 0; + } + return Map; + } + + // Mostly from MakeStatusCache.. + Progress.OverallProgress(0,1,1,"Reading Package Lists"); + + bool SrcOk = pkgSrcCacheCheck(List); + bool PkgOk = SrcOk && pkgPkgCacheCheck(CacheFile); + + // Rebuild the source and package caches + if (SrcOk == false) + { + DynamicMMap *Map = new DynamicMMap(MMap::Public); + if (_error->PendingError() == true) + { + delete Map; + return 0; + } + + pkgCacheGenerator Gen(*Map,Progress); + unsigned long CurrentSize = 0; + unsigned long TotalSize = 0; + if (pkgGenerateSrcCache(List,Progress,Gen,CurrentSize,TotalSize) == false) + { + delete Map; + return 0; + } + + // Merge in the source caches + if (pkgMergeStatus(Progress,Gen,CurrentSize,TotalSize) == false) + { + delete Map; + return 0; + } + + return Map; + } + + if (PkgOk == true) + { + Progress.OverallProgress(1,1,1,"Reading Package Lists"); + + // Open the cache file + FileFd File(_config->FindFile("Dir::Cache::pkgcache"),FileFd::ReadOnly); + if (_error->PendingError() == true) + return 0; + + MMap *Map = new MMap(File,MMap::Public | MMap::ReadOnly); + if (_error->PendingError() == true) + { + delete Map; + return 0; + } + return Map; + } + + // We use the source cache to generate the package cache + string SCacheFile = _config->FindFile("Dir::Cache::srcpkgcache"); + FileFd SCacheF(SCacheFile,FileFd::ReadOnly); + DynamicMMap *Map = new DynamicMMap(MMap::Public); + if (_error->PendingError() == true) + { + delete Map; + return 0; + } + + // Preload the map with the source cache + if (SCacheF.Read((unsigned char *)Map->Data() + Map->RawAllocate(SCacheF.Size()), + SCacheF.Size()) == false) + { + delete Map; + return 0; + } + + pkgCacheGenerator Gen(*Map,Progress); + + // Compute the progress + unsigned long TotalSize = 0; + if (pkgAddSourcesSize(TotalSize) == false) + { + delete Map; + return 0; + } + + unsigned long CurrentSize = 0; + if (pkgMergeStatus(Progress,Gen,CurrentSize,TotalSize) == false) + { + delete Map; + return 0; + } + + return Map; +} + /*}}}*/