소스 검색

deal better with (very) small apt::cache-start values

It is a bit academic to support values which aren't big enough to fit even
the hashtables without resizing, but cleaning up ensures that we do the
right thing (aka not segfaulting) even if something goes wrong in these
deep layers. You still can't have very very small values through…

Git-Dch: Ignore
David Kalnischkies 10 년 전
부모
커밋
a133f79c87
3개의 변경된 파일26개의 추가작업 그리고 17개의 파일을 삭제
  1. 1 1
      apt-pkg/cachefile.cc
  2. 24 16
      apt-pkg/pkgcachegen.cc
  3. 1 0
      apt-pkg/pkgcachegen.h

+ 1 - 1
apt-pkg/cachefile.cc

@@ -221,7 +221,7 @@ bool pkgCacheFile::AddIndexFile(pkgIndexFile * const File)		/*{{{*/
       {
       {
 	 {
 	 {
 	    pkgCacheGenerator Gen(dynmmap, nullptr);
 	    pkgCacheGenerator Gen(dynmmap, nullptr);
-	    if (File->Merge(Gen, nullptr) == false)
+	    if (Gen.Start() == false || File->Merge(Gen, nullptr) == false)
 	       return false;
 	       return false;
 	 }
 	 }
 	 Cache = new pkgCache(Map);
 	 Cache = new pkgCache(Map);

+ 24 - 16
apt-pkg/pkgcachegen.cc

@@ -57,6 +57,9 @@ using APT::StringView;
 pkgCacheGenerator::pkgCacheGenerator(DynamicMMap *pMap,OpProgress *Prog) :
 pkgCacheGenerator::pkgCacheGenerator(DynamicMMap *pMap,OpProgress *Prog) :
 		    Map(*pMap), Cache(pMap,false), Progress(Prog),
 		    Map(*pMap), Cache(pMap,false), Progress(Prog),
 		     CurrentRlsFile(NULL), CurrentFile(NULL), d(NULL)
 		     CurrentRlsFile(NULL), CurrentFile(NULL), d(NULL)
+{
+}
+bool pkgCacheGenerator::Start()
 {
 {
    if (Map.Size() == 0)
    if (Map.Size() == 0)
    {
    {
@@ -67,7 +70,9 @@ pkgCacheGenerator::pkgCacheGenerator(DynamicMMap *pMap,OpProgress *Prog) :
       bool const newError = _error->PendingError();
       bool const newError = _error->PendingError();
       _error->MergeWithStack();
       _error->MergeWithStack();
       if (newError)
       if (newError)
-	 return;
+	 return false;
+      if (Map.Size() <= 0)
+	 return false;
 
 
       Map.UsePools(*Cache.HeaderP->Pools,sizeof(Cache.HeaderP->Pools)/sizeof(Cache.HeaderP->Pools[0]));
       Map.UsePools(*Cache.HeaderP->Pools,sizeof(Cache.HeaderP->Pools)/sizeof(Cache.HeaderP->Pools[0]));
 
 
@@ -76,16 +81,15 @@ pkgCacheGenerator::pkgCacheGenerator(DynamicMMap *pMap,OpProgress *Prog) :
 
 
       // make room for the hashtables for packages and groups
       // make room for the hashtables for packages and groups
       if (Map.RawAllocate(2 * (Cache.HeaderP->GetHashTableSize() * sizeof(map_pointer_t))) == 0)
       if (Map.RawAllocate(2 * (Cache.HeaderP->GetHashTableSize() * sizeof(map_pointer_t))) == 0)
-	 return;
+	 return false;
 
 
       map_stringitem_t const idxVerSysName = WriteStringInMap(_system->VS->Label);
       map_stringitem_t const idxVerSysName = WriteStringInMap(_system->VS->Label);
       if (unlikely(idxVerSysName == 0))
       if (unlikely(idxVerSysName == 0))
-	 return;
-      Cache.HeaderP->VerSysName = idxVerSysName;
+	 return false;
       map_stringitem_t const idxArchitecture = StoreString(MIXED, _config->Find("APT::Architecture"));
       map_stringitem_t const idxArchitecture = StoreString(MIXED, _config->Find("APT::Architecture"));
       if (unlikely(idxArchitecture == 0))
       if (unlikely(idxArchitecture == 0))
-	 return;
-      Cache.HeaderP->Architecture = idxArchitecture;
+	 return false;
+      map_stringitem_t idxArchitectures;
 
 
       std::vector<std::string> archs = APT::Configuration::getArchitectures();
       std::vector<std::string> archs = APT::Configuration::getArchitectures();
       if (archs.size() > 1)
       if (archs.size() > 1)
@@ -94,13 +98,17 @@ pkgCacheGenerator::pkgCacheGenerator(DynamicMMap *pMap,OpProgress *Prog) :
 	 std::string list = *a;
 	 std::string list = *a;
 	 for (++a; a != archs.end(); ++a)
 	 for (++a; a != archs.end(); ++a)
 	    list.append(",").append(*a);
 	    list.append(",").append(*a);
-	 map_stringitem_t const idxArchitectures = WriteStringInMap(list);
+	 idxArchitectures = WriteStringInMap(list);
 	 if (unlikely(idxArchitectures == 0))
 	 if (unlikely(idxArchitectures == 0))
-	    return;
-	 Cache.HeaderP->SetArchitectures(idxArchitectures);
+	    return false;
       }
       }
       else
       else
-	 Cache.HeaderP->SetArchitectures(idxArchitecture);
+	 idxArchitectures = idxArchitecture;
+
+      Cache.HeaderP = (pkgCache::Header *)Map.Data();
+      Cache.HeaderP->VerSysName = idxVerSysName;
+      Cache.HeaderP->Architecture = idxArchitecture;
+      Cache.HeaderP->SetArchitectures(idxArchitectures);
 
 
       // Calculate the hash for the empty map, so ReMap does not fail
       // Calculate the hash for the empty map, so ReMap does not fail
       Cache.HeaderP->CacheFileSize = Cache.CacheHash();
       Cache.HeaderP->CacheFileSize = Cache.CacheHash();
@@ -112,14 +120,12 @@ pkgCacheGenerator::pkgCacheGenerator(DynamicMMap *pMap,OpProgress *Prog) :
       Cache.ReMap(); 
       Cache.ReMap(); 
       Map.UsePools(*Cache.HeaderP->Pools,sizeof(Cache.HeaderP->Pools)/sizeof(Cache.HeaderP->Pools[0]));
       Map.UsePools(*Cache.HeaderP->Pools,sizeof(Cache.HeaderP->Pools)/sizeof(Cache.HeaderP->Pools[0]));
       if (Cache.VS != _system->VS)
       if (Cache.VS != _system->VS)
-      {
-	 _error->Error(_("Cache has an incompatible versioning system"));
-	 return;
-      }
+	 return _error->Error(_("Cache has an incompatible versioning system"));
    }
    }
 
 
    Cache.HeaderP->Dirty = true;
    Cache.HeaderP->Dirty = true;
    Map.Sync(0,sizeof(pkgCache::Header));
    Map.Sync(0,sizeof(pkgCache::Header));
+   return true;
 }
 }
 									/*}}}*/
 									/*}}}*/
 // CacheGenerator::~pkgCacheGenerator - Destructor 			/*{{{*/
 // CacheGenerator::~pkgCacheGenerator - Destructor 			/*{{{*/
@@ -1607,7 +1613,7 @@ static bool loadBackMMapFromFile(std::unique_ptr<pkgCacheGenerator> &Gen,
    if (CacheF.Read((unsigned char *)Map->Data() + alloc, CacheF.Size()) == false)
    if (CacheF.Read((unsigned char *)Map->Data() + alloc, CacheF.Size()) == false)
       return false;
       return false;
    Gen.reset(new pkgCacheGenerator(Map.get(),Progress));
    Gen.reset(new pkgCacheGenerator(Map.get(),Progress));
-   return true;
+   return Gen->Start();
 }
 }
 bool pkgMakeStatusCache(pkgSourceList &List,OpProgress &Progress,
 bool pkgMakeStatusCache(pkgSourceList &List,OpProgress &Progress,
 			MMap **OutMap, bool AllowMem)
 			MMap **OutMap, bool AllowMem)
@@ -1713,6 +1719,8 @@ bool pkgCacheGenerator::MakeStatusCache(pkgSourceList &List,OpProgress *Progress
       if (Debug == true)
       if (Debug == true)
 	 std::clog << "srcpkgcache.bin is NOT valid - rebuild" << std::endl;
 	 std::clog << "srcpkgcache.bin is NOT valid - rebuild" << std::endl;
       Gen.reset(new pkgCacheGenerator(Map.get(),Progress));
       Gen.reset(new pkgCacheGenerator(Map.get(),Progress));
+      if (Gen->Start() == false)
+	 return false;
 
 
       TotalSize += ComputeSize(&List, Files.begin(),Files.end());
       TotalSize += ComputeSize(&List, Files.begin(),Files.end());
       if (BuildCache(*Gen, Progress, CurrentSize, TotalSize, &List,
       if (BuildCache(*Gen, Progress, CurrentSize, TotalSize, &List,
@@ -1790,7 +1798,7 @@ bool pkgCacheGenerator::MakeOnlyStatusCache(OpProgress *Progress,DynamicMMap **O
    if (Progress != NULL)
    if (Progress != NULL)
       Progress->OverallProgress(0,1,1,_("Reading package lists"));
       Progress->OverallProgress(0,1,1,_("Reading package lists"));
    pkgCacheGenerator Gen(Map.get(),Progress);
    pkgCacheGenerator Gen(Map.get(),Progress);
-   if (_error->PendingError() == true)
+   if (Gen.Start() == false || _error->PendingError() == true)
       return false;
       return false;
    if (BuildCache(Gen,Progress,CurrentSize,TotalSize, NULL,
    if (BuildCache(Gen,Progress,CurrentSize,TotalSize, NULL,
 		  Files.begin(), Files.end()) == false)
 		  Files.begin(), Files.end()) == false)

+ 1 - 0
apt-pkg/pkgcachegen.h

@@ -153,6 +153,7 @@ class APT_HIDDEN pkgCacheGenerator					/*{{{*/
    APT_PUBLIC static bool MakeOnlyStatusCache(OpProgress *Progress,DynamicMMap **OutMap);
    APT_PUBLIC static bool MakeOnlyStatusCache(OpProgress *Progress,DynamicMMap **OutMap);
 
 
    void ReMap(void const * const oldMap, void const * const newMap, size_t oldSize);
    void ReMap(void const * const oldMap, void const * const newMap, size_t oldSize);
+   bool Start();
 
 
    pkgCacheGenerator(DynamicMMap *Map,OpProgress *Progress);
    pkgCacheGenerator(DynamicMMap *Map,OpProgress *Progress);
    virtual ~pkgCacheGenerator();
    virtual ~pkgCacheGenerator();