Hacky fast closure copying mechanism

This commit is contained in:
Eelco Dolstra 2021-06-29 21:17:48 +02:00
parent bef40c2949
commit 3d9de41a5b
6 changed files with 55 additions and 1 deletions

View file

@ -12,6 +12,7 @@
#include "eval-cache.hh" #include "eval-cache.hh"
#include "url.hh" #include "url.hh"
#include "registry.hh" #include "registry.hh"
#include "remote-store.hh"
#include <regex> #include <regex>
#include <queue> #include <queue>
@ -378,6 +379,7 @@ DerivedPaths InstallableValue::toDerivedPaths()
DerivedPaths res; DerivedPaths res;
std::map<StorePath, std::set<std::string>> drvsToOutputs; std::map<StorePath, std::set<std::string>> drvsToOutputs;
RealisedPath::Set drvsToCopy;
// Group by derivation, helps with .all in particular // Group by derivation, helps with .all in particular
for (auto & drv : toDerivations()) { for (auto & drv : toDerivations()) {
@ -385,11 +387,38 @@ DerivedPaths InstallableValue::toDerivedPaths()
if (outputName == "") if (outputName == "")
throw Error("derivation '%s' lacks an 'outputName' attribute", state->store->printStorePath(drv.drvPath)); throw Error("derivation '%s' lacks an 'outputName' attribute", state->store->printStorePath(drv.drvPath));
drvsToOutputs[drv.drvPath].insert(outputName); drvsToOutputs[drv.drvPath].insert(outputName);
drvsToCopy.insert(drv.drvPath);
} }
for (auto & i : drvsToOutputs) for (auto & i : drvsToOutputs)
res.push_back(DerivedPath::Built { i.first, i.second }); res.push_back(DerivedPath::Built { i.first, i.second });
// FIXME: Temporary hack
if (state->store != state->buildStore) {
RealisedPath::Set closure;
RealisedPath::closure(*state->store, drvsToCopy, closure);
if (dynamic_cast<RemoteStore *>(&*state->buildStore)) {
StorePathSet closure2;
for (auto & p : closure)
closure2.insert(p.path());
auto valid = state->buildStore->queryValidPaths(closure2);
StorePathSet missing;
for (auto & p : closure2)
if (!valid.count(p)) missing.insert(p);
if (!missing.empty()) {
auto source = sinkToSource([&](Sink & sink) {
state->store->exportPaths(missing, sink);
});
state->buildStore->importPaths(*source, NoCheckSigs);
}
} else
copyPaths(state->store, state->buildStore, closure);
}
return res; return res;
} }

View file

@ -505,6 +505,17 @@ static void performOp(TunnelLogger * logger, ref<Store> store,
break; break;
} }
case wopImportPaths2: {
logger->startWork();
auto paths = store->importPaths(from,
trusted ? NoCheckSigs : CheckSigs);
logger->stopWork();
Strings paths2;
for (auto & i : paths) paths2.push_back(store->printStorePath(i));
to << paths2;
break;
}
case wopBuildPaths: { case wopBuildPaths: {
auto drvs = readDerivedPaths(*store, clientVersion, from); auto drvs = readDerivedPaths(*store, clientVersion, from);
BuildMode mode = bmNormal; BuildMode mode = bmNormal;

View file

@ -875,6 +875,16 @@ void RemoteStore::queryMissing(const std::vector<DerivedPath> & targets,
} }
StorePaths RemoteStore::importPaths(Source & source, CheckSigsFlag checkSigs)
{
auto conn(getConnection());
conn->to << wopImportPaths2;
source.drainInto(conn->to);
conn.processStderr();
return worker_proto::read(*this, conn->from, Phantom<StorePaths> {});
}
void RemoteStore::connect() void RemoteStore::connect()
{ {
auto conn(getConnection()); auto conn(getConnection());

View file

@ -112,6 +112,8 @@ public:
StorePathSet & willBuild, StorePathSet & willSubstitute, StorePathSet & unknown, StorePathSet & willBuild, StorePathSet & willSubstitute, StorePathSet & unknown,
uint64_t & downloadSize, uint64_t & narSize) override; uint64_t & downloadSize, uint64_t & narSize) override;
StorePaths importPaths(Source & source, CheckSigsFlag checkSigs) override;
void connect() override; void connect() override;
unsigned int getProtocol() override; unsigned int getProtocol() override;

View file

@ -676,7 +676,7 @@ public:
the Nix store. Optionally, the contents of the NARs are the Nix store. Optionally, the contents of the NARs are
preloaded into the specified FS accessor to speed up subsequent preloaded into the specified FS accessor to speed up subsequent
access. */ access. */
StorePaths importPaths(Source & source, CheckSigsFlag checkSigs = CheckSigs); virtual StorePaths importPaths(Source & source, CheckSigsFlag checkSigs = CheckSigs);
struct Stats struct Stats
{ {
@ -766,6 +766,7 @@ std::map<StorePath, StorePath> copyPaths(ref<Store> srcStore, ref<Store> dstStor
RepairFlag repair = NoRepair, RepairFlag repair = NoRepair,
CheckSigsFlag checkSigs = CheckSigs, CheckSigsFlag checkSigs = CheckSigs,
SubstituteFlag substitute = NoSubstitute); SubstituteFlag substitute = NoSubstitute);
std::map<StorePath, StorePath> copyPaths(ref<Store> srcStore, ref<Store> dstStore, std::map<StorePath, StorePath> copyPaths(ref<Store> srcStore, ref<Store> dstStore,
const StorePathSet & paths, const StorePathSet & paths,
RepairFlag repair = NoRepair, RepairFlag repair = NoRepair,

View file

@ -55,6 +55,7 @@ typedef enum {
wopQueryDerivationOutputMap = 41, wopQueryDerivationOutputMap = 41,
wopRegisterDrvOutput = 42, wopRegisterDrvOutput = 42,
wopQueryRealisation = 43, wopQueryRealisation = 43,
wopImportPaths2 = 44, // hack
} WorkerOp; } WorkerOp;