2024-04-18 23:49:52 +03:00
|
|
|
#include "indirect-root-store.hh"
|
|
|
|
|
|
|
|
namespace nix {
|
|
|
|
|
|
|
|
void IndirectRootStore::makeSymlink(const Path & link, const Path & target)
|
|
|
|
{
|
|
|
|
/* Create directories up to `gcRoot'. */
|
|
|
|
createDirs(dirOf(link));
|
|
|
|
|
|
|
|
/* Create the new symlink. */
|
|
|
|
Path tempLink = fmt("%1%.tmp-%2%-%3%", link, getpid(), rand());
|
|
|
|
createSymlink(target, tempLink);
|
|
|
|
|
|
|
|
/* Atomically replace the old one. */
|
|
|
|
renameFile(tempLink, link);
|
|
|
|
}
|
|
|
|
|
|
|
|
Path IndirectRootStore::addPermRoot(const StorePath & storePath, const Path & _gcRoot)
|
|
|
|
{
|
|
|
|
Path gcRoot(canonPath(_gcRoot));
|
|
|
|
|
|
|
|
if (isInStore(gcRoot))
|
|
|
|
throw Error(
|
2024-05-03 04:41:24 +03:00
|
|
|
"creating a garbage collector root (%1%) in the Nix store is forbidden "
|
|
|
|
"(are you running nix-build inside the store?)",
|
|
|
|
gcRoot);
|
2024-04-18 23:49:52 +03:00
|
|
|
|
|
|
|
/* Register this root with the garbage collector, if it's
|
|
|
|
running. This should be superfluous since the caller should
|
|
|
|
have registered this root yet, but let's be on the safe
|
|
|
|
side. */
|
|
|
|
addTempRoot(storePath);
|
|
|
|
|
|
|
|
/* Don't clobber the link if it already exists and doesn't
|
|
|
|
point to the Nix store. */
|
|
|
|
if (pathExists(gcRoot) && (!isLink(gcRoot) || !isInStore(readLink(gcRoot))))
|
|
|
|
throw Error("cannot create symlink '%1%'; already exists", gcRoot);
|
|
|
|
makeSymlink(gcRoot, printStorePath(storePath));
|
|
|
|
addIndirectRoot(gcRoot);
|
|
|
|
|
|
|
|
return gcRoot;
|
|
|
|
}
|
|
|
|
|
|
|
|
}
|