Speed up GC by marking entire closures as live

This commit is contained in:
Eelco Dolstra 2021-10-14 14:13:57 +02:00
parent 0154fa30cf
commit 17e6ebcc90

View file

@ -654,12 +654,22 @@ void LocalStore::collectGarbage(const GCOptions & options, GCResults & results)
handle it again. */ handle it again. */
if (dead.count(*path)) continue; if (dead.count(*path)) continue;
auto markAlive = [&]()
{
alive.insert(*path);
alive.insert(start);
try {
StorePathSet closure;
computeFSClosure(*path, closure);
for (auto & p : closure)
alive.insert(p);
} catch (InvalidPath &) { }
};
/* If this is a root, bail out. */ /* If this is a root, bail out. */
if (roots.count(*path)) { if (roots.count(*path)) {
debug("cannot delete '%s' because it's a root", printStorePath(*path)); debug("cannot delete '%s' because it's a root", printStorePath(*path));
alive.insert(*path); return markAlive();
alive.insert(start);
return;
} }
if (options.action == GCOptions::gcDeleteSpecific if (options.action == GCOptions::gcDeleteSpecific
@ -671,9 +681,7 @@ void LocalStore::collectGarbage(const GCOptions & options, GCResults & results)
auto shared(_shared.lock()); auto shared(_shared.lock());
if (shared->tempRoots.count(hashPart)) { if (shared->tempRoots.count(hashPart)) {
debug("cannot delete '%s' because it's a temporary root", printStorePath(*path)); debug("cannot delete '%s' because it's a temporary root", printStorePath(*path));
alive.insert(*path); return markAlive();
alive.insert(start);
return;
} }
shared->pending = hashPart; shared->pending = hashPart;
} }