about summary refs log tree commit diff
diff options
context:
space:
mode:
authorEelco Dolstra <e.dolstra@tudelft.nl>2011-08-31T21·11+0000
committerEelco Dolstra <e.dolstra@tudelft.nl>2011-08-31T21·11+0000
commit93227ff65c73e726c4ceef0cdd9439e7a4301417 (patch)
treeba7b60ca132c373913dd4a1c42a900009aeb8a77
parent5bcdc7e3517e6d679cad1aaba41e4deb76d5a6e7 (diff)
* Eliminate all uses of the global variable ‘store’ from libstore.
  This should also fix:

    nix-instantiate: ./../boost/shared_ptr.hpp:254: T* boost::shared_ptr<T>::operator->() const [with T = nix::StoreAPI]: Assertion `px != 0' failed.

  which was caused by hashDerivationModulo() calling the ‘store’
  object (during store upgrades) before openStore() assigned it.

-rw-r--r--src/libexpr/primops.cc8
-rw-r--r--src/libmain/shared.cc4
-rw-r--r--src/libmain/shared.hh4
-rw-r--r--src/libstore/build.cc16
-rw-r--r--src/libstore/derivations.cc11
-rw-r--r--src/libstore/derivations.hh8
-rw-r--r--src/libstore/gc.cc48
-rw-r--r--src/libstore/local-store.cc2
-rw-r--r--src/libstore/misc.cc30
-rw-r--r--src/libstore/misc.hh6
-rw-r--r--src/libstore/store-api.hh6
-rw-r--r--src/nix-env/nix-env.cc8
-rw-r--r--src/nix-env/profiles.cc2
-rw-r--r--src/nix-instantiate/nix-instantiate.cc5
-rw-r--r--src/nix-store/nix-store.cc26
15 files changed, 95 insertions, 89 deletions
diff --git a/src/libexpr/primops.cc b/src/libexpr/primops.cc
index 9d226a327017..0e81f7b72fae 100644
--- a/src/libexpr/primops.cc
+++ b/src/libexpr/primops.cc
@@ -357,7 +357,7 @@ static void prim_derivationStrict(EvalState & state, Value * * args, Value & v)
            runs. */
         if (path.at(0) == '=') {
             path = string(path, 1);
-            PathSet refs; computeFSClosure(path, refs);
+            PathSet refs; computeFSClosure(*store, path, refs);
             foreach (PathSet::iterator, j, refs) {
                 drv.inputSrcs.insert(*j);
                 if (isDerivation(*j))
@@ -433,7 +433,7 @@ static void prim_derivationStrict(EvalState & state, Value * * args, Value & v)
 
         /* Use the masked derivation expression to compute the output
            path. */
-        Hash h = hashDerivationModulo(drv);
+        Hash h = hashDerivationModulo(*store, drv);
         
         foreach (DerivationOutputs::iterator, i, drv.outputs)
             if (i->second.path == "") {
@@ -444,7 +444,7 @@ static void prim_derivationStrict(EvalState & state, Value * * args, Value & v)
     }
 
     /* Write the resulting term into the Nix store directory. */
-    Path drvPath = writeDerivation(drv, drvName);
+    Path drvPath = writeDerivation(*store, drv, drvName);
 
     printMsg(lvlChatty, format("instantiated `%1%' -> `%2%'")
         % drvName % drvPath);
@@ -452,7 +452,7 @@ static void prim_derivationStrict(EvalState & state, Value * * args, Value & v)
     /* Optimisation, but required in read-only mode! because in that
        case we don't actually write store derivations, so we can't
        read them later. */
-    drvHashes[drvPath] = hashDerivationModulo(drv);
+    drvHashes[drvPath] = hashDerivationModulo(*store, drv);
 
     state.mkAttrs(v, 1 + drv.outputs.size());
     mkString(*state.allocAttr(v, state.sDrvPath), drvPath, singleton<PathSet>("=" + drvPath));
diff --git a/src/libmain/shared.cc b/src/libmain/shared.cc
index 43ec4bcdd482..f0035c358f1d 100644
--- a/src/libmain/shared.cc
+++ b/src/libmain/shared.cc
@@ -52,11 +52,11 @@ void printGCWarning()
 }
 
 
-void printMissing(const PathSet & paths)
+void printMissing(StoreAPI & store, const PathSet & paths)
 {
     unsigned long long downloadSize, narSize;
     PathSet willBuild, willSubstitute, unknown;
-    queryMissing(paths, willBuild, willSubstitute, unknown, downloadSize, narSize);
+    queryMissing(store, paths, willBuild, willSubstitute, unknown, downloadSize, narSize);
 
     if (!willBuild.empty()) {
         printMsg(lvlInfo, format("these derivations will be built:"));
diff --git a/src/libmain/shared.hh b/src/libmain/shared.hh
index c99810c78a20..bd3d19531a80 100644
--- a/src/libmain/shared.hh
+++ b/src/libmain/shared.hh
@@ -24,11 +24,13 @@ namespace nix {
 
 MakeError(UsageError, nix::Error);
 
+class StoreAPI;
+
 /* Ugh.  No better place to put this. */
 Path makeRootName(const Path & gcRoot, int & counter);
 void printGCWarning();
 
-void printMissing(const PathSet & paths);
+void printMissing(StoreAPI & store, const PathSet & paths);
 
 template<class N> N getIntArg(const string & opt,
     Strings::iterator & i, const Strings::iterator & end)
diff --git a/src/libstore/build.cc b/src/libstore/build.cc
index 26f9fcc59820..d12f41d66941 100644
--- a/src/libstore/build.cc
+++ b/src/libstore/build.cc
@@ -934,7 +934,7 @@ void DerivationGoal::haveDerivation()
     assert(worker.store.isValidPath(drvPath));
 
     /* Get the derivation. */
-    drv = derivationFromPath(drvPath);
+    drv = derivationFromPath(worker.store, drvPath);
 
     foreach (DerivationOutputs::iterator, i, drv.outputs)
         worker.store.addTempRoot(i->second.path);
@@ -1030,10 +1030,10 @@ void DerivationGoal::inputsRealised()
            `*i' as input paths.  Only add the closures of output paths
            that are specified as inputs. */
         assert(worker.store.isValidPath(i->first));
-        Derivation inDrv = derivationFromPath(i->first);
+        Derivation inDrv = derivationFromPath(worker.store, i->first);
         foreach (StringSet::iterator, j, i->second)
             if (inDrv.outputs.find(*j) != inDrv.outputs.end())
-                computeFSClosure(inDrv.outputs[*j].path, inputPaths);
+                computeFSClosure(worker.store, inDrv.outputs[*j].path, inputPaths);
             else
                 throw Error(
                     format("derivation `%1%' requires non-existent output `%2%' from input derivation `%3%'")
@@ -1042,7 +1042,7 @@ void DerivationGoal::inputsRealised()
 
     /* Second, the input sources. */
     foreach (PathSet::iterator, i, drv.inputSrcs)
-        computeFSClosure(*i, inputPaths);
+        computeFSClosure(worker.store, *i, inputPaths);
 
     debug(format("added input paths %1%") % showPaths(inputPaths));
 
@@ -1399,7 +1399,7 @@ HookReply DerivationGoal::tryBuildHook()
        list it since the remote system *probably* already has it.) */
     PathSet allInputs;
     allInputs.insert(inputPaths.begin(), inputPaths.end());
-    computeFSClosure(drvPath, allInputs);
+    computeFSClosure(worker.store, drvPath, allInputs);
         
     string s;
     foreach (PathSet::iterator, i, allInputs) s += *i + " ";
@@ -1545,14 +1545,14 @@ void DerivationGoal::startBuilder()
            like passing all build-time dependencies of some path to a
            derivation that builds a NixOS DVD image. */
         PathSet paths, paths2;
-        computeFSClosure(storePath, paths);
+        computeFSClosure(worker.store, storePath, paths);
         paths2 = paths;
 
         foreach (PathSet::iterator, j, paths2) {
             if (isDerivation(*j)) {
-                Derivation drv = derivationFromPath(*j);
+                Derivation drv = derivationFromPath(worker.store, *j);
                 foreach (DerivationOutputs::iterator, k, drv.outputs)
-                    computeFSClosure(k->second.path, paths);
+                    computeFSClosure(worker.store, k->second.path, paths);
             }
         }
 
diff --git a/src/libstore/derivations.cc b/src/libstore/derivations.cc
index db9fc6b8a561..5a0f4ecc69e0 100644
--- a/src/libstore/derivations.cc
+++ b/src/libstore/derivations.cc
@@ -26,7 +26,8 @@ void DerivationOutput::parseHashInfo(bool & recursive, HashType & hashType, Hash
 }
 
 
-Path writeDerivation(const Derivation & drv, const string & name)
+Path writeDerivation(StoreAPI & store,
+    const Derivation & drv, const string & name)
 {
     PathSet references;
     references.insert(drv.inputSrcs.begin(), drv.inputSrcs.end());
@@ -39,7 +40,7 @@ Path writeDerivation(const Derivation & drv, const string & name)
     string contents = unparseDerivation(drv);
     return readOnlyMode
         ? computeStorePathForText(suffix, contents, references)
-        : store->addTextToStore(suffix, contents, references);
+        : store.addTextToStore(suffix, contents, references);
 }
 
 
@@ -221,7 +222,7 @@ DrvHashes drvHashes;
    paths have been replaced by the result of a recursive call to this
    function, and that for fixed-output derivations we return a hash of
    its output path. */
-Hash hashDerivationModulo(Derivation drv)
+Hash hashDerivationModulo(StoreAPI & store, Derivation drv)
 {
     /* Return a fixed hash for fixed-output derivations. */
     if (isFixedOutputDrv(drv)) {
@@ -238,8 +239,8 @@ Hash hashDerivationModulo(Derivation drv)
     foreach (DerivationInputs::const_iterator, i, drv.inputDrvs) {
         Hash h = drvHashes[i->first];
         if (h.type == htUnknown) {
-            Derivation drv2 = derivationFromPath(i->first);
-            h = hashDerivationModulo(drv2);
+            Derivation drv2 = derivationFromPath(store, i->first);
+            h = hashDerivationModulo(store, drv2);
             drvHashes[i->first] = h;
         }
         inputs2[printHash(h)] = i->second;
diff --git a/src/libstore/derivations.hh b/src/libstore/derivations.hh
index 4860f708c56f..27e471d885cc 100644
--- a/src/libstore/derivations.hh
+++ b/src/libstore/derivations.hh
@@ -53,8 +53,12 @@ struct Derivation
 };
 
 
+class StoreAPI;
+
+
 /* Write a derivation to the Nix store, and return its path. */
-Path writeDerivation(const Derivation & drv, const string & name);
+Path writeDerivation(StoreAPI & store,
+    const Derivation & drv, const string & name);
 
 /* Parse a derivation. */
 Derivation parseDerivation(const string & s);
@@ -69,7 +73,7 @@ bool isDerivation(const string & fileName);
 /* Return true iff this is a fixed-output derivation. */
 bool isFixedOutputDrv(const Derivation & drv);
 
-Hash hashDerivationModulo(Derivation drv);
+Hash hashDerivationModulo(StoreAPI & store, Derivation drv);
 
 /* Memoisation of hashDerivationModulo(). */
 typedef std::map<Path, Hash> DrvHashes;
diff --git a/src/libstore/gc.cc b/src/libstore/gc.cc
index b8395bfc4352..e79d93723b83 100644
--- a/src/libstore/gc.cc
+++ b/src/libstore/gc.cc
@@ -90,8 +90,8 @@ void LocalStore::addIndirectRoot(const Path & path)
 }
 
 
-Path addPermRoot(const Path & _storePath, const Path & _gcRoot,
-    bool indirect, bool allowOutsideRootsDir)
+Path addPermRoot(StoreAPI & store, const Path & _storePath,
+    const Path & _gcRoot, bool indirect, bool allowOutsideRootsDir)
 {
     Path storePath(canonPath(_storePath));
     Path gcRoot(canonPath(_gcRoot));
@@ -104,7 +104,7 @@ Path addPermRoot(const Path & _storePath, const Path & _gcRoot,
 
     if (indirect) {
         createSymlink(gcRoot, storePath, true);
-        store->addIndirectRoot(gcRoot);
+        store.addIndirectRoot(gcRoot);
     }
 
     else {
@@ -127,7 +127,7 @@ Path addPermRoot(const Path & _storePath, const Path & _gcRoot,
        check if the root is in a directory in or linked from the
        gcroots directory. */
     if (queryBoolSetting("gc-check-reachability", false)) {
-        Roots roots = store->findRoots();
+        Roots roots = store.findRoots();
         if (roots.find(gcRoot) == roots.end())
             printMsg(lvlError, 
                 format(
@@ -139,7 +139,7 @@ Path addPermRoot(const Path & _storePath, const Path & _gcRoot,
     /* Grab the global GC root, causing us to block while a GC is in
        progress.  This prevents the set of permanent roots from
        increasing while a GC is in progress. */
-    store->syncWithGC();
+    store.syncWithGC();
     
     return gcRoot;
 }
@@ -275,8 +275,8 @@ static void readTempRoots(PathSet & tempRoots, FDs & fds)
 }
 
 
-static void findRoots(const Path & path, bool recurseSymlinks,
-    bool deleteStale, Roots & roots)
+static void findRoots(StoreAPI & store, const Path & path,
+    bool recurseSymlinks, bool deleteStale, Roots & roots)
 {
     try {
         
@@ -289,7 +289,7 @@ static void findRoots(const Path & path, bool recurseSymlinks,
         if (S_ISDIR(st.st_mode)) {
             Strings names = readDirectory(path);
             foreach (Strings::iterator, i, names)
-                findRoots(path + "/" + *i, recurseSymlinks, deleteStale, roots);
+                findRoots(store, path + "/" + *i, recurseSymlinks, deleteStale, roots);
         }
 
         else if (S_ISLNK(st.st_mode)) {
@@ -299,7 +299,7 @@ static void findRoots(const Path & path, bool recurseSymlinks,
                 debug(format("found root `%1%' in `%2%'")
                     % target % path);
                 Path storePath = toStorePath(target);
-                if (store->isValidPath(storePath)) 
+                if (store.isValidPath(storePath)) 
                     roots[path] = storePath;
                 else
                     printMsg(lvlInfo, format("skipping invalid root from `%1%' to `%2%'")
@@ -308,7 +308,7 @@ static void findRoots(const Path & path, bool recurseSymlinks,
 
             else if (recurseSymlinks) {
                 if (pathExists(target))
-                    findRoots(target, false, deleteStale, roots);
+                    findRoots(store, target, false, deleteStale, roots);
                 else if (deleteStale) {
                     printMsg(lvlInfo, format("removing stale link from `%1%' to `%2%'") % path % target);
                     /* Note that we only delete when recursing, i.e.,
@@ -331,22 +331,22 @@ static void findRoots(const Path & path, bool recurseSymlinks,
 }
 
 
-static Roots findRoots(bool deleteStale)
+static Roots findRoots(StoreAPI & store, bool deleteStale)
 {
     Roots roots;
     Path rootsDir = canonPath((format("%1%/%2%") % nixStateDir % gcRootsDir).str());
-    findRoots(rootsDir, true, deleteStale, roots);
+    findRoots(store, rootsDir, true, deleteStale, roots);
     return roots;
 }
 
 
 Roots LocalStore::findRoots()
 {
-    return nix::findRoots(false);
+    return nix::findRoots(*this, false);
 }
 
 
-static void addAdditionalRoots(PathSet & roots)
+static void addAdditionalRoots(StoreAPI & store, PathSet & roots)
 {
     Path rootFinder = getEnv("NIX_ROOT_FINDER",
         nixLibexecDir + "/nix/find-runtime-roots.pl");
@@ -362,7 +362,7 @@ static void addAdditionalRoots(PathSet & roots)
     foreach (Strings::iterator, i, paths) {
         if (isInStore(*i)) {
             Path path = toStorePath(*i);
-            if (roots.find(path) == roots.end() && store->isValidPath(path)) {
+            if (roots.find(path) == roots.end() && store.isValidPath(path)) {
                 debug(format("got additional root `%1%'") % path);
                 roots.insert(path);
             }
@@ -371,32 +371,32 @@ static void addAdditionalRoots(PathSet & roots)
 }
 
 
-static void dfsVisit(const PathSet & paths, const Path & path,
-    PathSet & visited, Paths & sorted)
+static void dfsVisit(StoreAPI & store, const PathSet & paths,
+    const Path & path, PathSet & visited, Paths & sorted)
 {
     if (visited.find(path) != visited.end()) return;
     visited.insert(path);
     
     PathSet references;
-    if (store->isValidPath(path))
-        store->queryReferences(path, references);
+    if (store.isValidPath(path))
+        store.queryReferences(path, references);
     
     foreach (PathSet::iterator, i, references)
         /* Don't traverse into paths that don't exist.  That can
            happen due to substitutes for non-existent paths. */
         if (*i != path && paths.find(*i) != paths.end())
-            dfsVisit(paths, *i, visited, sorted);
+            dfsVisit(store, paths, *i, visited, sorted);
 
     sorted.push_front(path);
 }
 
 
-Paths topoSortPaths(const PathSet & paths)
+Paths topoSortPaths(StoreAPI & store, const PathSet & paths)
 {
     Paths sorted;
     PathSet visited;
     foreach (PathSet::const_iterator, i, paths)
-        dfsVisit(paths, *i, visited, sorted);
+        dfsVisit(store, paths, *i, visited, sorted);
     return sorted;
 }
 
@@ -582,7 +582,7 @@ void LocalStore::collectGarbage(const GCOptions & options, GCResults & results)
     /* Find the roots.  Since we've grabbed the GC lock, the set of
        permanent roots cannot increase now. */
     printMsg(lvlError, format("finding garbage collector roots..."));
-    Roots rootMap = options.ignoreLiveness ? Roots() : nix::findRoots(true);
+    Roots rootMap = options.ignoreLiveness ? Roots() : nix::findRoots(*this, true);
 
     foreach (Roots::iterator, i, rootMap) state.roots.insert(i->second);
 
@@ -591,7 +591,7 @@ void LocalStore::collectGarbage(const GCOptions & options, GCResults & results)
        to add running programs to the set of roots (to prevent them
        from being garbage collected). */
     if (!options.ignoreLiveness)
-        addAdditionalRoots(state.roots);
+        addAdditionalRoots(*this, state.roots);
 
     /* Read the temporary roots.  This acquires read locks on all
        per-process temporary root files.  So after this point no paths
diff --git a/src/libstore/local-store.cc b/src/libstore/local-store.cc
index 691069e2b8a0..6ad4c84c69ff 100644
--- a/src/libstore/local-store.cc
+++ b/src/libstore/local-store.cc
@@ -497,7 +497,7 @@ void LocalStore::checkDerivationOutputs(const Path & drvPath, const Derivation &
             drvCopy.env[i->first] = "";
         }
 
-        Hash h = hashDerivationModulo(drvCopy);
+        Hash h = hashDerivationModulo(*this, drvCopy);
         
         foreach (DerivationOutputs::const_iterator, i, drv.outputs) {
             Path outPath = makeOutputPath(i->first, h, drvName);
diff --git a/src/libstore/misc.cc b/src/libstore/misc.cc
index 01d6a97ae6fb..d4bbccd111ba 100644
--- a/src/libstore/misc.cc
+++ b/src/libstore/misc.cc
@@ -6,15 +6,15 @@
 namespace nix {
 
 
-Derivation derivationFromPath(const Path & drvPath)
+Derivation derivationFromPath(StoreAPI & store, const Path & drvPath)
 {
     assertStorePath(drvPath);
-    store->ensurePath(drvPath);
+    store.ensurePath(drvPath);
     return parseDerivation(readFile(drvPath));
 }
 
 
-void computeFSClosure(const Path & storePath,
+void computeFSClosure(StoreAPI & store, const Path & storePath,
     PathSet & paths, bool flipDirection, bool includeOutputs)
 {
     if (paths.find(storePath) != paths.end()) return;
@@ -22,19 +22,19 @@ void computeFSClosure(const Path & storePath,
 
     PathSet references;
     if (flipDirection)
-        store->queryReferrers(storePath, references);
+        store.queryReferrers(storePath, references);
     else
-        store->queryReferences(storePath, references);
+        store.queryReferences(storePath, references);
 
     if (includeOutputs && isDerivation(storePath)) {
-        PathSet outputs = store->queryDerivationOutputs(storePath);
+        PathSet outputs = store.queryDerivationOutputs(storePath);
         foreach (PathSet::iterator, i, outputs)
-            if (store->isValidPath(*i))
-                computeFSClosure(*i, paths, flipDirection, true);
+            if (store.isValidPath(*i))
+                computeFSClosure(store, *i, paths, flipDirection, true);
     }
 
     foreach (PathSet::iterator, i, references)
-        computeFSClosure(*i, paths, flipDirection, includeOutputs);
+        computeFSClosure(store, *i, paths, flipDirection, includeOutputs);
 }
 
 
@@ -46,7 +46,7 @@ Path findOutput(const Derivation & drv, string id)
 }
 
 
-void queryMissing(const PathSet & targets,
+void queryMissing(StoreAPI & store, const PathSet & targets,
     PathSet & willBuild, PathSet & willSubstitute, PathSet & unknown,
     unsigned long long & downloadSize, unsigned long long & narSize)
 {
@@ -61,15 +61,15 @@ void queryMissing(const PathSet & targets,
         done.insert(p);
 
         if (isDerivation(p)) {
-            if (!store->isValidPath(p)) {
+            if (!store.isValidPath(p)) {
                 unknown.insert(p);
                 continue;
             }
-            Derivation drv = derivationFromPath(p);
+            Derivation drv = derivationFromPath(store, p);
 
             bool mustBuild = false;
             foreach (DerivationOutputs::iterator, i, drv.outputs)
-                if (!store->isValidPath(i->second.path) && !store->hasSubstitutes(i->second.path))
+                if (!store.isValidPath(i->second.path) && !store.hasSubstitutes(i->second.path))
                     mustBuild = true;
 
             if (mustBuild) {
@@ -83,9 +83,9 @@ void queryMissing(const PathSet & targets,
         }
 
         else {
-            if (store->isValidPath(p)) continue;
+            if (store.isValidPath(p)) continue;
             SubstitutablePathInfo info;
-            if (store->querySubstitutablePathInfo(p, info)) {
+            if (store.querySubstitutablePathInfo(p, info)) {
                 willSubstitute.insert(p);
                 downloadSize += info.downloadSize;
                 narSize += info.narSize;
diff --git a/src/libstore/misc.hh b/src/libstore/misc.hh
index abef6237e7f6..850c12af4ebc 100644
--- a/src/libstore/misc.hh
+++ b/src/libstore/misc.hh
@@ -9,7 +9,7 @@ namespace nix {
 
 /* Read a derivation, after ensuring its existence through
    ensurePath(). */
-Derivation derivationFromPath(const Path & drvPath);
+Derivation derivationFromPath(StoreAPI & store, const Path & drvPath);
 
 /* Place in `paths' the set of all store paths in the file system
    closure of `storePath'; that is, all paths than can be directly or
@@ -18,7 +18,7 @@ Derivation derivationFromPath(const Path & drvPath);
    `storePath' is returned; that is, the closures under the
    `referrers' relation instead of the `references' relation is
    returned. */
-void computeFSClosure(const Path & storePath,
+void computeFSClosure(StoreAPI & store, const Path & storePath,
     PathSet & paths, bool flipDirection = false,
     bool includeOutputs = false);
 
@@ -29,7 +29,7 @@ Path findOutput(const Derivation & drv, string id);
 /* Given a set of paths that are to be built, return the set of
    derivations that will be built, and the set of output paths that
    will be substituted. */
-void queryMissing(const PathSet & targets,
+void queryMissing(StoreAPI & store, const PathSet & targets,
     PathSet & willBuild, PathSet & willSubstitute, PathSet & unknown,
     unsigned long long & downloadSize, unsigned long long & narSize);
 
diff --git a/src/libstore/store-api.hh b/src/libstore/store-api.hh
index 243a6324ccaa..b3e67436c6c3 100644
--- a/src/libstore/store-api.hh
+++ b/src/libstore/store-api.hh
@@ -314,13 +314,13 @@ void removeTempRoots();
 
 
 /* Register a permanent GC root. */
-Path addPermRoot(const Path & storePath, const Path & gcRoot,
-    bool indirect, bool allowOutsideRootsDir = false);
+Path addPermRoot(StoreAPI & store, const Path & storePath,
+    const Path & gcRoot, bool indirect, bool allowOutsideRootsDir = false);
 
 
 /* Sort a set of paths topologically under the references relation.
    If p refers to q, then p follows q in this list. */
-Paths topoSortPaths(const PathSet & paths);
+Paths topoSortPaths(StoreAPI & store, const PathSet & paths);
 
 
 /* For now, there is a single global store API object, but we'll
diff --git a/src/nix-env/nix-env.cc b/src/nix-env/nix-env.cc
index 731f91bba058..3dfecb2d7313 100644
--- a/src/nix-env/nix-env.cc
+++ b/src/nix-env/nix-env.cc
@@ -381,7 +381,7 @@ static void queryInstSources(EvalState & state,
 
                 if (isDerivation(path)) {
                     elem.setDrvPath(path);
-                    elem.setOutPath(findOutput(derivationFromPath(path), "out"));
+                    elem.setOutPath(findOutput(derivationFromPath(*store, path), "out"));
                     if (name.size() >= drvExtension.size() &&
                         string(name, name.size() - drvExtension.size()) == drvExtension)
                         name = string(name, 0, name.size() - drvExtension.size());
@@ -430,7 +430,7 @@ static void printMissing(EvalState & state, const DrvInfos & elems)
             targets.insert(i->queryOutPath(state));
     }
 
-    printMissing(targets);
+    printMissing(*store, targets);
 }
 
 
@@ -693,12 +693,12 @@ static void opSet(Globals & globals,
 
     if (drv.queryDrvPath(globals.state) != "") {
         PathSet paths = singleton<PathSet>(drv.queryDrvPath(globals.state));
-        printMissing(paths);
+        printMissing(*store, paths);
         if (globals.dryRun) return;
         store->buildDerivations(paths);
     }
     else {
-        printMissing(singleton<PathSet>(drv.queryOutPath(globals.state)));
+        printMissing(*store, singleton<PathSet>(drv.queryOutPath(globals.state)));
         if (globals.dryRun) return;
         store->ensurePath(drv.queryOutPath(globals.state));
     }
diff --git a/src/nix-env/profiles.cc b/src/nix-env/profiles.cc
index 60576f1ae74b..5cc0d9a1cd42 100644
--- a/src/nix-env/profiles.cc
+++ b/src/nix-env/profiles.cc
@@ -91,7 +91,7 @@ Path createGeneration(Path profile, Path outPath)
        user environment etc. we've just built. */
     Path generation;
     makeName(profile, num + 1, generation);
-    addPermRoot(outPath, generation, false, true);
+    addPermRoot(*store, outPath, generation, false, true);
 
     return generation;
 }
diff --git a/src/nix-instantiate/nix-instantiate.cc b/src/nix-instantiate/nix-instantiate.cc
index 05b9d54797e4..98eadbd69580 100644
--- a/src/nix-instantiate/nix-instantiate.cc
+++ b/src/nix-instantiate/nix-instantiate.cc
@@ -64,9 +64,8 @@ void processExpr(EvalState & state, const Strings & attrPaths,
                     if (gcRoot == "")
                         printGCWarning();
                     else
-                        drvPath = addPermRoot(drvPath,
-                            makeRootName(gcRoot, rootNr),
-                            indirectRoot);
+                        drvPath = addPermRoot(*store, drvPath,
+                            makeRootName(gcRoot, rootNr), indirectRoot);
                     std::cout << format("%1%\n") % drvPath;
                 }
             }
diff --git a/src/nix-store/nix-store.cc b/src/nix-store/nix-store.cc
index 49a705585ebf..00dab5f32670 100644
--- a/src/nix-store/nix-store.cc
+++ b/src/nix-store/nix-store.cc
@@ -58,14 +58,13 @@ static Path realisePath(const Path & path)
         PathSet paths;
         paths.insert(path);
         store->buildDerivations(paths);
-        Path outPath = findOutput(derivationFromPath(path), "out");
+        Path outPath = findOutput(derivationFromPath(*store, path), "out");
         
         if (gcRoot == "")
             printGCWarning();
         else
-            outPath = addPermRoot(outPath,
-                makeRootName(gcRoot, rootNr),
-                indirectRoot);
+            outPath = addPermRoot(*store, outPath,
+                makeRootName(gcRoot, rootNr), indirectRoot);
         
         return outPath;
     } else {
@@ -87,7 +86,7 @@ static void opRealise(Strings opFlags, Strings opArgs)
     foreach (Strings::iterator, i, opArgs)
         *i = followLinksToStorePath(*i);
             
-    printMissing(PathSet(opArgs.begin(), opArgs.end()));
+    printMissing(*store, PathSet(opArgs.begin(), opArgs.end()));
     
     if (dryRun) return;
     
@@ -170,7 +169,7 @@ static Path maybeUseOutput(const Path & storePath, bool useOutput, bool forceRea
 {
     if (forceRealise) realisePath(storePath);
     if (useOutput && isDerivation(storePath)) {
-        Derivation drv = derivationFromPath(storePath);
+        Derivation drv = derivationFromPath(*store, storePath);
         return findOutput(drv, "out");
     }
     else return storePath;
@@ -210,7 +209,7 @@ static void printTree(const Path & path,
        closure(B).  That is, if derivation A is an (possibly indirect)
        input of B, then A is printed first.  This has the effect of
        flattening the tree, preventing deeply nested structures.  */
-    Paths sorted = topoSortPaths(references);
+    Paths sorted = topoSortPaths(*store, references);
     reverse(sorted.begin(), sorted.end());
 
     for (Paths::iterator i = sorted.begin(); i != sorted.end(); ++i) {
@@ -265,7 +264,7 @@ static void opQuery(Strings opFlags, Strings opArgs)
             foreach (Strings::iterator, i, opArgs) {
                 *i = followLinksToStorePath(*i);
                 if (forceRealise) realisePath(*i);
-                Derivation drv = derivationFromPath(*i);
+                Derivation drv = derivationFromPath(*store, *i);
                 cout << format("%1%\n") % findOutput(drv, "out");
             }
             break;
@@ -278,12 +277,12 @@ static void opQuery(Strings opFlags, Strings opArgs)
             PathSet paths;
             foreach (Strings::iterator, i, opArgs) {
                 Path path = maybeUseOutput(followLinksToStorePath(*i), useOutput, forceRealise);
-                if (query == qRequisites) computeFSClosure(path, paths, false, includeOutputs);
+                if (query == qRequisites) computeFSClosure(*store, path, paths, false, includeOutputs);
                 else if (query == qReferences) store->queryReferences(path, paths);
                 else if (query == qReferrers) store->queryReferrers(path, paths);
-                else if (query == qReferrersClosure) computeFSClosure(path, paths, true);
+                else if (query == qReferrersClosure) computeFSClosure(*store, path, paths, true);
             }
-            Paths sorted = topoSortPaths(paths);
+            Paths sorted = topoSortPaths(*store, paths);
             for (Paths::reverse_iterator i = sorted.rbegin(); 
                  i != sorted.rend(); ++i)
                 cout << format("%s\n") % *i;
@@ -301,7 +300,7 @@ static void opQuery(Strings opFlags, Strings opArgs)
         case qBinding:
             foreach (Strings::iterator, i, opArgs) {
                 Path path = useDeriver(followLinksToStorePath(*i));
-                Derivation drv = derivationFromPath(path);
+                Derivation drv = derivationFromPath(*store, path);
                 StringPairs::iterator j = drv.env.find(bindingName);
                 if (j == drv.env.end())
                     throw Error(format("derivation `%1%' has no environment binding named `%2%'")
@@ -355,7 +354,8 @@ static void opQuery(Strings opFlags, Strings opArgs)
         case qRoots: {
             PathSet referrers;
             foreach (Strings::iterator, i, opArgs)
-                computeFSClosure(maybeUseOutput(followLinksToStorePath(*i), useOutput, forceRealise),
+                computeFSClosure(*store,
+                    maybeUseOutput(followLinksToStorePath(*i), useOutput, forceRealise),
                     referrers, true);
             Roots roots = store->findRoots();
             foreach (Roots::iterator, i, roots)