mirror of
https://github.com/NixOS/nix.git
synced 2025-11-26 04:00:59 +01:00
Before adding dbValidStatePaths
This commit is contained in:
parent
0e41b191bf
commit
51fad07fbd
13 changed files with 167 additions and 144 deletions
|
|
@ -1194,7 +1194,7 @@ DerivationGoal::HookReply DerivationGoal::tryBuildHook()
|
||||||
*probably* already has it.) */
|
*probably* already has it.) */
|
||||||
PathSet allInputs;
|
PathSet allInputs;
|
||||||
allInputs.insert(inputPaths.begin(), inputPaths.end());
|
allInputs.insert(inputPaths.begin(), inputPaths.end());
|
||||||
computeFSClosure(drvPath, allInputs);
|
computeFSClosure(drvPath, allInputs, false); //TODO !!!!!!!!!!!!!!!!!!!!!!!!!!! WE (MAY) ALSO NEED TO COPY STATE
|
||||||
|
|
||||||
string s;
|
string s;
|
||||||
for (PathSet::iterator i = allInputs.begin();
|
for (PathSet::iterator i = allInputs.begin();
|
||||||
|
|
@ -1316,7 +1316,7 @@ bool DerivationGoal::prepareBuild()
|
||||||
for (StringSet::iterator j = i->second.begin();
|
for (StringSet::iterator j = i->second.begin();
|
||||||
j != i->second.end(); ++j)
|
j != i->second.end(); ++j)
|
||||||
if (inDrv.outputs.find(*j) != inDrv.outputs.end())
|
if (inDrv.outputs.find(*j) != inDrv.outputs.end())
|
||||||
computeFSClosure(inDrv.outputs[*j].path, inputPaths);
|
computeFSClosure(inDrv.outputs[*j].path, inputPaths, false); //TODO !!!!!!!!!!!!!!!!!!!!!!!!!!! WE (MAY) ALSO NEED TO COPY STATE
|
||||||
else
|
else
|
||||||
throw BuildError(
|
throw BuildError(
|
||||||
format("derivation `%1%' requires non-existent output `%2%' from input derivation `%3%'")
|
format("derivation `%1%' requires non-existent output `%2%' from input derivation `%3%'")
|
||||||
|
|
@ -1326,7 +1326,7 @@ bool DerivationGoal::prepareBuild()
|
||||||
/* Second, the input sources. */
|
/* Second, the input sources. */
|
||||||
for (PathSet::iterator i = drv.inputSrcs.begin();
|
for (PathSet::iterator i = drv.inputSrcs.begin();
|
||||||
i != drv.inputSrcs.end(); ++i)
|
i != drv.inputSrcs.end(); ++i)
|
||||||
computeFSClosure(*i, inputPaths);
|
computeFSClosure(*i, inputPaths, false); //TODO !!!!!!!!!!!!!!!!!!!!!!!!!!! WE (MAY) ALSO NEED TO COPY STATE
|
||||||
|
|
||||||
debug(format("added input paths %1%") % showPaths(inputPaths));
|
debug(format("added input paths %1%") % showPaths(inputPaths));
|
||||||
|
|
||||||
|
|
@ -1451,7 +1451,7 @@ void DerivationGoal::startBuilder()
|
||||||
|
|
||||||
/* Write closure info to `fileName'. */
|
/* Write closure info to `fileName'. */
|
||||||
PathSet refs;
|
PathSet refs;
|
||||||
computeFSClosure(storePath, refs);
|
computeFSClosure(storePath, refs, false); //TODO !!!!!!!!!!!!!!!!!!!!!!!!!!! WE (MAY) ALSO NEED TO COPY STATE
|
||||||
/* !!! in secure Nix, the writing should be done on the
|
/* !!! in secure Nix, the writing should be done on the
|
||||||
build uid for security (maybe). */
|
build uid for security (maybe). */
|
||||||
writeStringToFile(tmpDir + "/" + fileName,
|
writeStringToFile(tmpDir + "/" + fileName,
|
||||||
|
|
|
||||||
|
|
@ -469,7 +469,7 @@ void LocalStore::collectGarbage(GCAction action, const PathSet & pathsToDelete,
|
||||||
roots under the `references' relation. */
|
roots under the `references' relation. */
|
||||||
PathSet livePaths;
|
PathSet livePaths;
|
||||||
for (PathSet::const_iterator i = roots.begin(); i != roots.end(); ++i)
|
for (PathSet::const_iterator i = roots.begin(); i != roots.end(); ++i)
|
||||||
computeFSClosure(canonPath(*i), livePaths);
|
computeFSClosure(canonPath(*i), livePaths, false); //TODO !!!!!!!!!!!!!!!!!!!!!!!!!!! WE (MAY) ALSO NEED TO DELETE STATE??
|
||||||
|
|
||||||
if (gcKeepDerivations) {
|
if (gcKeepDerivations) {
|
||||||
for (PathSet::iterator i = livePaths.begin();
|
for (PathSet::iterator i = livePaths.begin();
|
||||||
|
|
@ -480,7 +480,7 @@ void LocalStore::collectGarbage(GCAction action, const PathSet & pathsToDelete,
|
||||||
turned off). */
|
turned off). */
|
||||||
Path deriver = queryDeriver(noTxn, *i);
|
Path deriver = queryDeriver(noTxn, *i);
|
||||||
if (deriver != "" && store->isValidPath(deriver))
|
if (deriver != "" && store->isValidPath(deriver))
|
||||||
computeFSClosure(deriver, livePaths);
|
computeFSClosure(deriver, livePaths, false); //TODO !!!!!!!!!!!!!!!!!!!!!!!!!!! WE (MAY) ALSO NEED TO KEEP STATE
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -493,7 +493,7 @@ void LocalStore::collectGarbage(GCAction action, const PathSet & pathsToDelete,
|
||||||
for (DerivationOutputs::iterator j = drv.outputs.begin();
|
for (DerivationOutputs::iterator j = drv.outputs.begin();
|
||||||
j != drv.outputs.end(); ++j)
|
j != drv.outputs.end(); ++j)
|
||||||
if (store->isValidPath(j->second.path))
|
if (store->isValidPath(j->second.path))
|
||||||
computeFSClosure(j->second.path, livePaths);
|
computeFSClosure(j->second.path, livePaths, false); //TODO !!!!!!!!!!!!!!!!!!!!!!!!!!! WE (MAY) ALSO NEED TO KEEP STATE
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -518,7 +518,7 @@ void LocalStore::collectGarbage(GCAction action, const PathSet & pathsToDelete,
|
||||||
PathSet tempRootsClosed;
|
PathSet tempRootsClosed;
|
||||||
for (PathSet::iterator i = tempRoots.begin(); i != tempRoots.end(); ++i)
|
for (PathSet::iterator i = tempRoots.begin(); i != tempRoots.end(); ++i)
|
||||||
if (store->isValidPath(*i))
|
if (store->isValidPath(*i))
|
||||||
computeFSClosure(*i, tempRootsClosed);
|
computeFSClosure(*i, tempRootsClosed, false); //TODO !!!!!!!!!!!!!!!!!!!!!!!!!!! WE (MAY) ALSO NEED TO .... STATE
|
||||||
else
|
else
|
||||||
tempRootsClosed.insert(*i);
|
tempRootsClosed.insert(*i);
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -320,8 +320,7 @@ static Substitutes readSubstitutes(const Transaction & txn,
|
||||||
|
|
||||||
static bool isRealisablePath(const Transaction & txn, const Path & path)
|
static bool isRealisablePath(const Transaction & txn, const Path & path)
|
||||||
{
|
{
|
||||||
return isValidPathTxn(txn, path)
|
return isValidPathTxn(txn, path) || readSubstitutes(txn, path).size() > 0;
|
||||||
|| readSubstitutes(txn, path).size() > 0;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -545,7 +544,7 @@ bool LocalStore::isStateDrvPath(const Path & isStateDrv)
|
||||||
}
|
}
|
||||||
|
|
||||||
//TODO Add and ..
|
//TODO Add and ..
|
||||||
bool isStateDrvTxn(const Transaction & txn, Derivation drv)
|
bool isStateDrvTxn(const Transaction & txn, const Derivation & drv)
|
||||||
{
|
{
|
||||||
if (drv.stateOutputs.size() != 0)
|
if (drv.stateOutputs.size() != 0)
|
||||||
return true;
|
return true;
|
||||||
|
|
@ -553,7 +552,7 @@ bool isStateDrvTxn(const Transaction & txn, Derivation drv)
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool LocalStore::isStateDrv(Derivation drv)
|
bool LocalStore::isStateDrv(const Derivation & drv)
|
||||||
{
|
{
|
||||||
return nix::isStateDrvTxn(noTxn, drv);
|
return nix::isStateDrvTxn(noTxn, drv);
|
||||||
}
|
}
|
||||||
|
|
@ -886,7 +885,7 @@ Path LocalStore::addTextToStore(const string & suffix, const string & s,
|
||||||
{
|
{
|
||||||
Path dstPath = computeStorePathForText(suffix, s, references);
|
Path dstPath = computeStorePathForText(suffix, s, references);
|
||||||
|
|
||||||
printMsg(lvlError, format("addTextToStore: %1%") % dstPath);
|
//printMsg(lvlError, format("addTextToStore: %1%") % dstPath);
|
||||||
|
|
||||||
addTempRoot(dstPath);
|
addTempRoot(dstPath);
|
||||||
|
|
||||||
|
|
@ -1043,7 +1042,7 @@ Path LocalStore::importPath(bool requireSignature, Source & source)
|
||||||
|
|
||||||
PathSet references = readStorePaths(hashAndReadSource);
|
PathSet references = readStorePaths(hashAndReadSource);
|
||||||
|
|
||||||
//TODO TODO !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
|
//TODO TODO also ..??!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
|
||||||
PathSet stateReferences;
|
PathSet stateReferences;
|
||||||
|
|
||||||
Path deriver = readString(hashAndReadSource);
|
Path deriver = readString(hashAndReadSource);
|
||||||
|
|
@ -1137,7 +1136,7 @@ void deleteFromStore(const Path & _path, unsigned long long & bytesFreed)
|
||||||
invalidatePath(txn, path);
|
invalidatePath(txn, path);
|
||||||
|
|
||||||
//TODO !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
|
//TODO !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
|
||||||
//Also delete stateReferrers?????
|
//Also delete/invalidate stateReferrers?????
|
||||||
}
|
}
|
||||||
txn.commit();
|
txn.commit();
|
||||||
|
|
||||||
|
|
@ -1228,9 +1227,8 @@ void verifyStore(bool checkContents)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
//TODO also check state references and refererres
|
|
||||||
|
|
||||||
/* Check the `references' table. */
|
/* Check the `references' table. */
|
||||||
|
//TODO TODO Do the exact same thing for dbStateReferrers
|
||||||
printMsg(lvlInfo, "checking the references table");
|
printMsg(lvlInfo, "checking the references table");
|
||||||
Paths referencesKeys;
|
Paths referencesKeys;
|
||||||
nixDB.enumTable(txn, dbReferences, referencesKeys);
|
nixDB.enumTable(txn, dbReferences, referencesKeys);
|
||||||
|
|
@ -1264,6 +1262,7 @@ void verifyStore(bool checkContents)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Check the `referrers' table. */
|
/* Check the `referrers' table. */
|
||||||
|
//TODO TODO Do the exact same thing for dbStateReferrers, but merge! it into this one....
|
||||||
printMsg(lvlInfo, "checking the referrers table");
|
printMsg(lvlInfo, "checking the referrers table");
|
||||||
Strings referrers;
|
Strings referrers;
|
||||||
nixDB.enumTable(txn, dbReferrers, referrers);
|
nixDB.enumTable(txn, dbReferrers, referrers);
|
||||||
|
|
@ -1294,10 +1293,9 @@ void verifyStore(bool checkContents)
|
||||||
else {
|
else {
|
||||||
PathSet references;
|
PathSet references;
|
||||||
queryReferences(txn, from, references);
|
queryReferences(txn, from, references);
|
||||||
|
|
||||||
PathSet stateReferences;
|
PathSet stateReferences; //already a stateReferrers here!
|
||||||
queryStateReferences(txn, from, stateReferences);
|
queryStateReferences(txn, from, stateReferences);
|
||||||
//TODO TODO !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
|
|
||||||
|
|
||||||
if (find(references.begin(), references.end(), to) == references.end()) {
|
if (find(references.begin(), references.end(), to) == references.end()) {
|
||||||
printMsg(lvlError, format("adding missing referrer mapping from `%1%' to `%2%'") % from % to);
|
printMsg(lvlError, format("adding missing referrer mapping from `%1%' to `%2%'") % from % to);
|
||||||
|
|
@ -1309,7 +1307,7 @@ void verifyStore(bool checkContents)
|
||||||
}
|
}
|
||||||
|
|
||||||
//TODO Check stateinfo and statecounters table
|
//TODO Check stateinfo and statecounters table
|
||||||
|
|
||||||
|
|
||||||
txn.commit();
|
txn.commit();
|
||||||
}
|
}
|
||||||
|
|
@ -1412,29 +1410,43 @@ PathSet mergeNewDerivationIntoList(const Path & storepath, const Path & newdrv,
|
||||||
return newdrvs;
|
return newdrvs;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* We register in this database which _component_ paths are state paths
|
/* Place in `paths' the set of paths that are required to `realise'
|
||||||
* This does not mean these paths are already valid!, you should look in derivivers for that
|
the given store path, i.e., all paths necessary for valid
|
||||||
*/
|
deployment of the path. For a derivation, this is the union of
|
||||||
/*
|
requisites of the inputs, plus the derivation; for other store
|
||||||
void registerMaybeStatePath(const Path & drvPath)
|
paths, it is the set of paths in the FS closure of the path. If
|
||||||
{
|
`includeOutputs' is true, include the requisites of the output
|
||||||
if(!isStateDrv(drvPath))
|
paths of derivations as well.
|
||||||
return;
|
|
||||||
|
|
||||||
printMsg(lvlError, format("derivation aaa: %1% ") % drvPath);
|
Note that this function can be used to implement three different
|
||||||
|
deployment policies:
|
||||||
|
|
||||||
|
- Source deployment (when called on a derivation).
|
||||||
Derivation drv = derivationFromPath(drvPath);
|
- Binary deployment (when called on an output path).
|
||||||
Path storePath = drv.outputs["out"].path;
|
- Source/binary deployment (when called on a derivation with
|
||||||
|
`includeOutputs' set to true).
|
||||||
nixDB.setString(noTxn, dbStateInfo, storePath, ""); //update the dbinfo db. (maybe TODO)
|
|
||||||
}
|
|
||||||
|
|
||||||
void LocalStore::registerMaybeStatePath(const Path & drvPath)
|
|
||||||
{
|
|
||||||
nix::registerMaybeStatePath(drvPath);
|
|
||||||
}
|
|
||||||
*/
|
*/
|
||||||
|
void storePathRequisites(const Path & storePath, const bool includeOutputs, PathSet & paths, const bool & withState)
|
||||||
|
{
|
||||||
|
computeFSClosure(storePath, paths, withState);
|
||||||
|
|
||||||
|
if (includeOutputs) {
|
||||||
|
for (PathSet::iterator i = paths.begin();
|
||||||
|
i != paths.end(); ++i)
|
||||||
|
if (isDerivation(*i)) {
|
||||||
|
Derivation drv = derivationFromPath(*i);
|
||||||
|
for (DerivationOutputs::iterator j = drv.outputs.begin();
|
||||||
|
j != drv.outputs.end(); ++j)
|
||||||
|
if (store->isValidPath(j->second.path))
|
||||||
|
computeFSClosure(j->second.path, paths, withState);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void LocalStore::storePathRequisites(const Path & storePath, const bool includeOutputs, PathSet & paths, const bool & withState)
|
||||||
|
{
|
||||||
|
return nix::storePathRequisites(storePath, includeOutputs, paths, withState);
|
||||||
|
}
|
||||||
|
|
||||||
/* Upgrade from schema 1 (Nix <= 0.7) to schema 2 (Nix >= 0.8). */
|
/* Upgrade from schema 1 (Nix <= 0.7) to schema 2 (Nix >= 0.8). */
|
||||||
static void upgradeStore07()
|
static void upgradeStore07()
|
||||||
|
|
|
||||||
|
|
@ -88,7 +88,9 @@ public:
|
||||||
|
|
||||||
bool isStateDrvPath(const Path & drvpath);
|
bool isStateDrvPath(const Path & drvpath);
|
||||||
|
|
||||||
bool isStateDrv(Derivation drv);
|
bool isStateDrv(const Derivation & drv);
|
||||||
|
|
||||||
|
void storePathRequisites(const Path & storePath, const bool includeOutputs, PathSet & paths, const bool & withState);
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
@ -197,7 +199,7 @@ bool isStateComponentTxn(const Transaction & txn, const Path & path);
|
||||||
|
|
||||||
bool isStateDrvPathTxn(const Transaction & txn, const Path & drvPath);
|
bool isStateDrvPathTxn(const Transaction & txn, const Path & drvPath);
|
||||||
|
|
||||||
bool isStateDrvTxn(const Transaction & txn, Derivation drv);
|
bool isStateDrvTxn(const Transaction & txn, const Derivation & drv);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -18,6 +18,7 @@ Derivation derivationFromPath(const Path & drvPath)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
void computeFSClosure(const Path & storePath,
|
void computeFSClosure(const Path & storePath,
|
||||||
PathSet & paths, bool flipDirection)
|
PathSet & paths, bool flipDirection)
|
||||||
{
|
{
|
||||||
|
|
@ -30,10 +31,40 @@ void computeFSClosure(const Path & storePath,
|
||||||
else
|
else
|
||||||
store->queryReferences(storePath, references);
|
store->queryReferences(storePath, references);
|
||||||
|
|
||||||
for (PathSet::iterator i = references.begin();
|
for (PathSet::iterator i = references.begin(); i != references.end(); ++i)
|
||||||
i != references.end(); ++i)
|
|
||||||
computeFSClosure(*i, paths, flipDirection);
|
computeFSClosure(*i, paths, flipDirection);
|
||||||
}
|
}
|
||||||
|
*/
|
||||||
|
|
||||||
|
void computeFSClosure(const Path & path, PathSet & paths, const bool & withState, bool flipDirection)
|
||||||
|
{
|
||||||
|
if (paths.find(path) != paths.end()) return;
|
||||||
|
|
||||||
|
paths.insert(path);
|
||||||
|
|
||||||
|
PathSet references;
|
||||||
|
PathSet stateReferences;
|
||||||
|
|
||||||
|
if (flipDirection){
|
||||||
|
store->queryReferrers(path, references);
|
||||||
|
if(withState)
|
||||||
|
store->queryStateReferrers(path, stateReferences);
|
||||||
|
}
|
||||||
|
else{
|
||||||
|
store->queryReferences(path, references);
|
||||||
|
if(withState)
|
||||||
|
store->queryStateReferences(path, stateReferences);
|
||||||
|
}
|
||||||
|
|
||||||
|
PathSet allReferences;
|
||||||
|
if(withState)
|
||||||
|
allReferences = mergePathSets(references, stateReferences);
|
||||||
|
else
|
||||||
|
allReferences = references;
|
||||||
|
|
||||||
|
for (PathSet::iterator i = allReferences.begin(); i != allReferences.end(); ++i)
|
||||||
|
computeFSClosure(*i, paths, withState, flipDirection);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
Path findOutput(const Derivation & drv, string id)
|
Path findOutput(const Derivation & drv, string id)
|
||||||
|
|
|
||||||
|
|
@ -19,7 +19,7 @@ Derivation derivationFromPath(const Path & drvPath);
|
||||||
`referrers' relation instead of the `references' relation is
|
`referrers' relation instead of the `references' relation is
|
||||||
returned. */
|
returned. */
|
||||||
void computeFSClosure(const Path & storePath,
|
void computeFSClosure(const Path & storePath,
|
||||||
PathSet & paths, bool flipDirection = false);
|
PathSet & paths, const bool & withState, bool flipDirection = false);
|
||||||
|
|
||||||
/* Return the path corresponding to the output identifier `id' in the
|
/* Return the path corresponding to the output identifier `id' in the
|
||||||
given derivation. */
|
given derivation. */
|
||||||
|
|
|
||||||
|
|
@ -421,9 +421,15 @@ bool RemoteStore::isStateDrvPath(const Path & drvpath)
|
||||||
}
|
}
|
||||||
|
|
||||||
//TODO
|
//TODO
|
||||||
bool RemoteStore::isStateDrv(Derivation drv)
|
bool RemoteStore::isStateDrv(const Derivation & drv)
|
||||||
{
|
{
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//TODO
|
||||||
|
void RemoteStore::storePathRequisites(const Path & storePath, const bool includeOutputs, PathSet & paths, const bool & withState)
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -76,7 +76,9 @@ public:
|
||||||
|
|
||||||
bool isStateDrvPath(const Path & drvpath);
|
bool isStateDrvPath(const Path & drvpath);
|
||||||
|
|
||||||
bool isStateDrv(Derivation drv);
|
bool isStateDrv(const Derivation & drv);
|
||||||
|
|
||||||
|
void storePathRequisites(const Path & storePath, const bool includeOutputs, PathSet & paths, const bool & withState);
|
||||||
|
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
|
|
||||||
|
|
@ -203,7 +203,9 @@ public:
|
||||||
virtual bool isStateDrvPath(const Path & drvpath) = 0;
|
virtual bool isStateDrvPath(const Path & drvpath) = 0;
|
||||||
|
|
||||||
/* TODO */
|
/* TODO */
|
||||||
virtual bool isStateDrv(Derivation drv) = 0;
|
virtual bool isStateDrv(const Derivation & drv) = 0;
|
||||||
|
|
||||||
|
virtual void storePathRequisites(const Path & storePath, const bool includeOutputs, PathSet & paths, const bool & withState) = 0;
|
||||||
|
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -377,7 +377,6 @@ static void queryInstSources(EvalState & state,
|
||||||
if (isDerivation(*i)) {
|
if (isDerivation(*i)) {
|
||||||
elem.setDrvPath(*i);
|
elem.setDrvPath(*i);
|
||||||
elem.setOutPath(findOutput(derivationFromPath(*i), "out"));
|
elem.setOutPath(findOutput(derivationFromPath(*i), "out"));
|
||||||
|
|
||||||
//TODO !!!!!!!!!!!!!!!!!!!! setStatePath??
|
//TODO !!!!!!!!!!!!!!!!!!!! setStatePath??
|
||||||
|
|
||||||
if (name.size() >= drvExtension.size() &&
|
if (name.size() >= drvExtension.size() &&
|
||||||
|
|
|
||||||
|
|
@ -22,11 +22,12 @@ typedef void (* Operation) (Strings opFlags, Strings opArgs);
|
||||||
/************************* Build time Functions ******************************/
|
/************************* Build time Functions ******************************/
|
||||||
|
|
||||||
|
|
||||||
//a
|
|
||||||
/************************* Build time Functions ******************************/
|
/************************* Build time Functions ******************************/
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
/************************* Run time Functions ******************************/
|
||||||
|
|
||||||
void printHelp()
|
void printHelp()
|
||||||
{
|
{
|
||||||
|
|
@ -35,7 +36,7 @@ void printHelp()
|
||||||
|
|
||||||
|
|
||||||
//
|
//
|
||||||
Derivation getDerivation_andCheckArgs_(Strings opFlags, Strings opArgs, Path & componentPath, Path & statePath, string & stateIdentifier, string & binary, string & derivationPath,
|
Derivation getDerivation_andCheckArgs_(Strings opFlags, Strings opArgs, Path & componentPath, Path & statePath, string & stateIdentifier, string & binary, string & derivationPath, bool isStatePath,
|
||||||
bool getDerivers, PathSet & derivers, string & username) //optional
|
bool getDerivers, PathSet & derivers, string & username) //optional
|
||||||
{
|
{
|
||||||
if (!opFlags.empty()) throw UsageError("unknown flag");
|
if (!opFlags.empty()) throw UsageError("unknown flag");
|
||||||
|
|
@ -53,7 +54,8 @@ Derivation getDerivation_andCheckArgs_(Strings opFlags, Strings opArgs, Path & c
|
||||||
if(componentPath == "/nix/store")
|
if(componentPath == "/nix/store")
|
||||||
throw UsageError("You must specify the full! binary path");
|
throw UsageError("You must specify the full! binary path");
|
||||||
|
|
||||||
//TODO CHECK IF PATH IS STATEPATH
|
//Check if path is statepath
|
||||||
|
isStatePath = store->isStateComponent(componentPath);
|
||||||
|
|
||||||
if(opArgs.size() > 1){
|
if(opArgs.size() > 1){
|
||||||
opArgs.pop_front();
|
opArgs.pop_front();
|
||||||
|
|
@ -63,14 +65,16 @@ Derivation getDerivation_andCheckArgs_(Strings opFlags, Strings opArgs, Path & c
|
||||||
if(username == "")
|
if(username == "")
|
||||||
username = getCallingUserName();
|
username = getCallingUserName();
|
||||||
|
|
||||||
printMsg(lvlTalkative, format("%1% - %2% - %3% - %4%") % componentPath % stateIdentifier % binary % username);
|
//printMsg(lvlError, format("%1% - %2% - %3% - %4%") % componentPath % stateIdentifier % binary % username);
|
||||||
|
|
||||||
derivers = queryDerivers(noTxn, componentPath, stateIdentifier, username);
|
derivers = queryDerivers(noTxn, componentPath, stateIdentifier, username);
|
||||||
|
|
||||||
if(getDerivers == true)
|
if(getDerivers == true)
|
||||||
return Derivation();
|
return Derivation();
|
||||||
|
else if(derivers.size() == 0)
|
||||||
|
throw UsageError(format("There are no derivers with this combination of identifier '%1%' and username '%2%'") % stateIdentifier % username);
|
||||||
else if(derivers.size() != 1)
|
else if(derivers.size() != 1)
|
||||||
throw UsageError("There is more than one deriver....");
|
throw UsageError(format("There is more than one deriver with identifier '%1%' and username '%2%'") % stateIdentifier % username);
|
||||||
|
|
||||||
Derivation drv;
|
Derivation drv;
|
||||||
for (PathSet::iterator i = derivers.begin(); i != derivers.end(); ++i){ //ugly workaround for drvs[0].
|
for (PathSet::iterator i = derivers.begin(); i != derivers.end(); ++i){ //ugly workaround for drvs[0].
|
||||||
|
|
@ -84,11 +88,11 @@ Derivation getDerivation_andCheckArgs_(Strings opFlags, Strings opArgs, Path & c
|
||||||
}
|
}
|
||||||
|
|
||||||
//Wrapper
|
//Wrapper
|
||||||
Derivation getDerivation_andCheckArgs(Strings opFlags, Strings opArgs, Path & componentPath, Path & statePath, string & stateIdentifier, string & binary, string & derivationPath)
|
Derivation getDerivation_andCheckArgs(Strings opFlags, Strings opArgs, Path & componentPath, Path & statePath, string & stateIdentifier, string & binary, string & derivationPath, bool & isStatePath)
|
||||||
{
|
{
|
||||||
PathSet empty;
|
PathSet empty;
|
||||||
string empty2;
|
string empty2;
|
||||||
return getDerivation_andCheckArgs_(opFlags, opArgs, componentPath, statePath, stateIdentifier, binary, derivationPath, false, empty, empty2);
|
return getDerivation_andCheckArgs_(opFlags, opArgs, componentPath, statePath, stateIdentifier, binary, derivationPath, isStatePath, false, empty, empty2);
|
||||||
}
|
}
|
||||||
|
|
||||||
//
|
//
|
||||||
|
|
@ -107,10 +111,14 @@ static void opShowDerivations(Strings opFlags, Strings opArgs)
|
||||||
string binary;
|
string binary;
|
||||||
PathSet derivers;
|
PathSet derivers;
|
||||||
string derivationPath;
|
string derivationPath;
|
||||||
Derivation drv = getDerivation_andCheckArgs_(opFlags, opArgs, componentPath, statePath, stateIdentifier, binary, derivationPath, true, derivers, username);
|
bool isStatePath;
|
||||||
|
Derivation drv = getDerivation_andCheckArgs_(opFlags, opArgs, componentPath, statePath, stateIdentifier, binary, derivationPath, true, isStatePath, derivers, username);
|
||||||
|
|
||||||
|
if(!isStatePath)
|
||||||
|
throw UsageError(format("This path '%1%' is not a state path") % componentPath);
|
||||||
|
|
||||||
for (PathSet::iterator i = derivers.begin(); i != derivers.end(); ++i)
|
for (PathSet::iterator i = derivers.begin(); i != derivers.end(); ++i)
|
||||||
printMsg(lvlTalkative, format("%1%") % (*i));
|
printMsg(lvlError, format("%1%") % (*i));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -122,8 +130,13 @@ static void opShowStatePath(Strings opFlags, Strings opArgs)
|
||||||
string stateIdentifier;
|
string stateIdentifier;
|
||||||
string binary;
|
string binary;
|
||||||
string derivationPath;
|
string derivationPath;
|
||||||
Derivation drv = getDerivation_andCheckArgs(opFlags, opArgs, componentPath, statePath, stateIdentifier, binary, derivationPath);
|
bool isStatePath;
|
||||||
printMsg(lvlTalkative, format("%1%") % statePath);
|
Derivation drv = getDerivation_andCheckArgs(opFlags, opArgs, componentPath, statePath, stateIdentifier, binary, derivationPath, isStatePath);
|
||||||
|
|
||||||
|
if(!isStatePath)
|
||||||
|
throw UsageError(format("This path '%1%' is not a state path") % componentPath);
|
||||||
|
|
||||||
|
printMsg(lvlError, format("%1%") % statePath);
|
||||||
}
|
}
|
||||||
|
|
||||||
//Prints the root path that contains the repoisitorys of the state of a component - indetiefier combination
|
//Prints the root path that contains the repoisitorys of the state of a component - indetiefier combination
|
||||||
|
|
@ -134,19 +147,34 @@ static void opShowStateReposRootPath(Strings opFlags, Strings opArgs)
|
||||||
string stateIdentifier;
|
string stateIdentifier;
|
||||||
string binary;
|
string binary;
|
||||||
string derivationPath;
|
string derivationPath;
|
||||||
Derivation drv = getDerivation_andCheckArgs(opFlags, opArgs, componentPath, statePath, stateIdentifier, binary, derivationPath);
|
bool isStatePath;
|
||||||
string drvName = drv.env.find("name")->second;
|
Derivation drv = getDerivation_andCheckArgs(opFlags, opArgs, componentPath, statePath, stateIdentifier, binary, derivationPath, isStatePath);
|
||||||
|
|
||||||
|
if(!isStatePath)
|
||||||
|
throw UsageError(format("This path '%1%' is not a state path") % componentPath);
|
||||||
|
|
||||||
//Get the a repository for this state location
|
//Get the a repository for this state location
|
||||||
|
string drvName = drv.env.find("name")->second;
|
||||||
string repos = makeStateReposPath("stateOutput:staterepospath", statePath, "/", drvName, stateIdentifier); //this is a copy from store-state.cc
|
string repos = makeStateReposPath("stateOutput:staterepospath", statePath, "/", drvName, stateIdentifier); //this is a copy from store-state.cc
|
||||||
|
|
||||||
//TODO Strip off
|
printMsg(lvlError, format("%1%") % repos);
|
||||||
//repos = repos.substr(0, repos.length() - .... );
|
|
||||||
|
|
||||||
printMsg(lvlTalkative, format("%1%") % repos);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
PathSet getReferencesClosureWithState(const Path & storepath)
|
||||||
|
{
|
||||||
|
PathSet paths;
|
||||||
|
store->storePathRequisites(storepath, false, paths, true);
|
||||||
|
|
||||||
|
for (PathSet::iterator i = paths.begin(); i != paths.end(); ++i)
|
||||||
|
{
|
||||||
|
printMsg(lvlError, format("REFCLOSURE %1%") % *i);
|
||||||
|
}
|
||||||
|
|
||||||
|
//return drvs ! (combo of component + state | component path)
|
||||||
|
//return single state paths
|
||||||
|
}
|
||||||
|
|
||||||
//TODO
|
//TODO
|
||||||
static void recheckrefsinstaterecursive()
|
static void recheckrefsinstaterecursive()
|
||||||
{
|
{
|
||||||
|
|
@ -167,7 +195,8 @@ static void opRunComponent(Strings opFlags, Strings opArgs)
|
||||||
string stateIdentifier;
|
string stateIdentifier;
|
||||||
string binary;
|
string binary;
|
||||||
string derivationPath;
|
string derivationPath;
|
||||||
Derivation drv = getDerivation_andCheckArgs(opFlags, opArgs, componentPath, statePath, stateIdentifier, binary, derivationPath);
|
bool isStatePath;
|
||||||
|
Derivation drv = getDerivation_andCheckArgs(opFlags, opArgs, componentPath, statePath, stateIdentifier, binary, derivationPath, isStatePath);
|
||||||
DerivationStateOutputDirs stateOutputDirs = drv.stateOutputDirs;
|
DerivationStateOutputDirs stateOutputDirs = drv.stateOutputDirs;
|
||||||
DerivationStateOutputs stateOutputs = drv.stateOutputs;
|
DerivationStateOutputs stateOutputs = drv.stateOutputs;
|
||||||
DerivationOutputs outputs = drv.outputs;
|
DerivationOutputs outputs = drv.outputs;
|
||||||
|
|
@ -302,39 +331,6 @@ static void opRunComponent(Strings opFlags, Strings opArgs)
|
||||||
"commit-script");
|
"commit-script");
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
|
||||||
PathSet getStateReferencesClosure_(const Path & drvpath, PathSet & drvPaths, const PathSet & paths)
|
|
||||||
{
|
|
||||||
Derivation drv = derivationFromPath(drvpath);
|
|
||||||
Path outPath = drv.outputs["out"].path;
|
|
||||||
|
|
||||||
for (DerivationInputs::iterator i = drv.inputDrvs.begin(); i != drv.inputDrvs.end(); ++i){
|
|
||||||
|
|
||||||
Path checkDrvPath = i->first;
|
|
||||||
printMsg(lvlTalkative, format("DRVPS: `%1%'") % checkDrvPath);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
PathSet getStateReferencesClosure(const Path & drvpath)
|
|
||||||
{
|
|
||||||
PathSet empty;
|
|
||||||
PathSet paths;
|
|
||||||
Derivation drv = derivationFromPath(drvpath);
|
|
||||||
Path outPath = drv.outputs["out"].path;
|
|
||||||
computeFSClosure(outPath, paths);
|
|
||||||
PathSet drvRefs = getStateReferencesClosure_(drvpath, empty, paths);
|
|
||||||
|
|
||||||
for (PathSet::iterator i = paths.begin(); i != paths.end(); ++i)
|
|
||||||
{
|
|
||||||
printMsg(lvlTalkative, format("Referen2ces: `%1%'") % *i);
|
|
||||||
}
|
|
||||||
|
|
||||||
return drvRefs;
|
|
||||||
}
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void run(Strings args)
|
void run(Strings args)
|
||||||
|
|
@ -362,14 +358,15 @@ void run(Strings args)
|
||||||
store->addStateDeriver("/nix/store/0a151npn1aps8w75kpz2zm1yl3v11kbr-hellostateworld-1.0.drv", "/nix/store/k4v52ql98x2m09sb5pz7w1lrd4hamsm0-hellostateworld-1.0");
|
store->addStateDeriver("/nix/store/0a151npn1aps8w75kpz2zm1yl3v11kbr-hellostateworld-1.0.drv", "/nix/store/k4v52ql98x2m09sb5pz7w1lrd4hamsm0-hellostateworld-1.0");
|
||||||
store->addStateDeriver("/nix/store/2hpx60ibdfv2pslg4rjvp177frijamvi-hellostateworld-1.0.drv", "/nix/store/k4v52ql98x2m09sb5pz7w1lrd4hamsm0-hellostateworld-1.0");
|
store->addStateDeriver("/nix/store/2hpx60ibdfv2pslg4rjvp177frijamvi-hellostateworld-1.0.drv", "/nix/store/k4v52ql98x2m09sb5pz7w1lrd4hamsm0-hellostateworld-1.0");
|
||||||
return;
|
return;
|
||||||
*/
|
|
||||||
|
|
||||||
store = openStore();
|
store = openStore();
|
||||||
printMsg(lvlError, format("1: %1%") % bool2string( store->isStateComponent("/nix/store/7xkw5fkz5yw7dpx0pc6l12bh9a56135c-hellostateworld-1.0") ) );
|
printMsg(lvlError, format("1: %1%") % bool2string( store->isStateComponent("/nix/store/7xkw5fkz5yw7dpx0pc6l12bh9a56135c-hellostateworld-1.0") ) );
|
||||||
printMsg(lvlError, format("2: %1%") % bool2string( store->isStateComponent("/nix/store/05441jm8xmsidqm43ivk0micckf0mr2m-nvidiaDrivers") ) );
|
printMsg(lvlError, format("2: %1%") % bool2string( store->isStateComponent("/nix/store/05441jm8xmsidqm43ivk0micckf0mr2m-nvidiaDrivers") ) );
|
||||||
printMsg(lvlError, format("3: %1%") % bool2string( store->isStateDrvPath("/nix/store/2hpx60ibdfv2pslg4rjvp177frijamvi-hellostateworld-1.0.drv") ) );
|
printMsg(lvlError, format("3: %1%") % bool2string( store->isStateDrvPath("/nix/store/2hpx60ibdfv2pslg4rjvp177frijamvi-hellostateworld-1.0.drv") ) );
|
||||||
return;
|
return;
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
/* test */
|
/* test */
|
||||||
|
|
||||||
for (Strings::iterator i = args.begin(); i != args.end(); ) {
|
for (Strings::iterator i = args.begin(); i != args.end(); ) {
|
||||||
|
|
|
||||||
|
|
@ -31,11 +31,13 @@ Query flags:
|
||||||
|
|
||||||
--outputs: query the output paths of a Nix derivation (default)
|
--outputs: query the output paths of a Nix derivation (default)
|
||||||
--requisites / -R: print all paths necessary to realise a path
|
--requisites / -R: print all paths necessary to realise a path
|
||||||
|
--requisites-withstate: same as --requisites but now also including state paths
|
||||||
--references: print all paths referenced by the given path
|
--references: print all paths referenced by the given path
|
||||||
--references-state: print all state paths referenced by the given path
|
--references-state: print all state paths referenced by the given path
|
||||||
--referrers: print all paths directly refering to the given path
|
--referrers: print all paths directly refering to the given path
|
||||||
--referrers-state: print all state paths directly refering to the given path
|
--referrers-state: print all state paths directly refering to the given path
|
||||||
--referrers-closure: print all paths (in)directly refering to the given path
|
--referrers-closure: print all paths (in)directly refering to the given path
|
||||||
|
--referrers-closure-withstate: same as --referrers-closure but now also including state paths
|
||||||
--tree: print a tree showing the dependency graph of the given paths
|
--tree: print a tree showing the dependency graph of the given paths
|
||||||
--graph: print a dot graph rooted at given paths
|
--graph: print a dot graph rooted at given paths
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -163,41 +163,6 @@ static void opPrintFixedPath(Strings opFlags, Strings opArgs)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/* Place in `paths' the set of paths that are required to `realise'
|
|
||||||
the given store path, i.e., all paths necessary for valid
|
|
||||||
deployment of the path. For a derivation, this is the union of
|
|
||||||
requisites of the inputs, plus the derivation; for other store
|
|
||||||
paths, it is the set of paths in the FS closure of the path. If
|
|
||||||
`includeOutputs' is true, include the requisites of the output
|
|
||||||
paths of derivations as well.
|
|
||||||
|
|
||||||
Note that this function can be used to implement three different
|
|
||||||
deployment policies:
|
|
||||||
|
|
||||||
- Source deployment (when called on a derivation).
|
|
||||||
- Binary deployment (when called on an output path).
|
|
||||||
- Source/binary deployment (when called on a derivation with
|
|
||||||
`includeOutputs' set to true).
|
|
||||||
*/
|
|
||||||
static void storePathRequisites(const Path & storePath,
|
|
||||||
bool includeOutputs, PathSet & paths)
|
|
||||||
{
|
|
||||||
computeFSClosure(storePath, paths);
|
|
||||||
|
|
||||||
if (includeOutputs) {
|
|
||||||
for (PathSet::iterator i = paths.begin();
|
|
||||||
i != paths.end(); ++i)
|
|
||||||
if (isDerivation(*i)) {
|
|
||||||
Derivation drv = derivationFromPath(*i);
|
|
||||||
for (DerivationOutputs::iterator j = drv.outputs.begin();
|
|
||||||
j != drv.outputs.end(); ++j)
|
|
||||||
if (store->isValidPath(j->second.path))
|
|
||||||
computeFSClosure(j->second.path, paths);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
static Path maybeUseOutput(const Path & storePath, bool useOutput, bool forceRealise)
|
static Path maybeUseOutput(const Path & storePath, bool useOutput, bool forceRealise)
|
||||||
{
|
{
|
||||||
if (forceRealise) realisePath(storePath);
|
if (forceRealise) realisePath(storePath);
|
||||||
|
|
@ -257,8 +222,8 @@ static void printTree(const Path & path,
|
||||||
/* Perform various sorts of queries. */
|
/* Perform various sorts of queries. */
|
||||||
static void opQuery(Strings opFlags, Strings opArgs)
|
static void opQuery(Strings opFlags, Strings opArgs)
|
||||||
{
|
{
|
||||||
enum { qOutputs, qRequisites, qReferences, qStateReferences, qReferrers, qStateReferrers
|
enum { qOutputs, qRequisites, qRequisitesWithState, qReferences, qStateReferences, qReferrers, qStateReferrers
|
||||||
, qReferrersClosure, qDeriver, qBinding, qHash
|
, qReferrersClosure, qReferrersClosureWithState, qDeriver, qBinding, qHash
|
||||||
, qTree, qGraph, qResolve } query = qOutputs;
|
, qTree, qGraph, qResolve } query = qOutputs;
|
||||||
bool useOutput = false;
|
bool useOutput = false;
|
||||||
bool includeOutputs = false;
|
bool includeOutputs = false;
|
||||||
|
|
@ -269,11 +234,13 @@ static void opQuery(Strings opFlags, Strings opArgs)
|
||||||
i != opFlags.end(); ++i)
|
i != opFlags.end(); ++i)
|
||||||
if (*i == "--outputs") query = qOutputs;
|
if (*i == "--outputs") query = qOutputs;
|
||||||
else if (*i == "--requisites" || *i == "-R") query = qRequisites;
|
else if (*i == "--requisites" || *i == "-R") query = qRequisites;
|
||||||
|
else if (*i == "--requisites-withstate") query = qRequisitesWithState;
|
||||||
else if (*i == "--references") query = qReferences;
|
else if (*i == "--references") query = qReferences;
|
||||||
else if (*i == "--references-state") query = qStateReferences;
|
else if (*i == "--references-state") query = qStateReferences;
|
||||||
else if (*i == "--referrers" || *i == "--referers") query = qReferrers;
|
else if (*i == "--referrers" || *i == "--referers") query = qReferrers;
|
||||||
else if (*i == "--referrers-state" || *i == "--referers-state") query = qStateReferrers;
|
else if (*i == "--referrers-state" || *i == "--referers-state") query = qStateReferrers;
|
||||||
else if (*i == "--referrers-closure" || *i == "--referers-closure") query = qReferrersClosure;
|
else if (*i == "--referrers-closure" || *i == "--referers-closure") query = qReferrersClosure;
|
||||||
|
else if (*i == "--referrers-closure-withstate" || *i == "--referers-closure-withstate") query = qReferrersClosureWithState;
|
||||||
else if (*i == "--deriver" || *i == "-d") query = qDeriver;
|
else if (*i == "--deriver" || *i == "-d") query = qDeriver;
|
||||||
else if (*i == "--binding" || *i == "-b") {
|
else if (*i == "--binding" || *i == "-b") {
|
||||||
if (opArgs.size() == 0)
|
if (opArgs.size() == 0)
|
||||||
|
|
@ -306,23 +273,26 @@ static void opQuery(Strings opFlags, Strings opArgs)
|
||||||
}
|
}
|
||||||
|
|
||||||
case qRequisites:
|
case qRequisites:
|
||||||
|
case qRequisitesWithState:
|
||||||
case qReferences:
|
case qReferences:
|
||||||
case qStateReferences:
|
case qStateReferences:
|
||||||
case qReferrers:
|
case qReferrers:
|
||||||
case qStateReferrers:
|
case qStateReferrers:
|
||||||
case qReferrersClosure: {
|
case qReferrersClosure:
|
||||||
|
case qReferrersClosureWithState: {
|
||||||
PathSet paths;
|
PathSet paths;
|
||||||
for (Strings::iterator i = opArgs.begin();
|
for (Strings::iterator i = opArgs.begin();
|
||||||
i != opArgs.end(); ++i)
|
i != opArgs.end(); ++i)
|
||||||
{
|
{
|
||||||
Path path = maybeUseOutput(fixPath(*i), useOutput, forceRealise);
|
Path path = maybeUseOutput(fixPath(*i), useOutput, forceRealise);
|
||||||
if (query == qRequisites)
|
if (query == qRequisites) store->storePathRequisites(path, includeOutputs, paths, false);
|
||||||
storePathRequisites(path, includeOutputs, paths);
|
else if (query == qRequisitesWithState) store->storePathRequisites(path, includeOutputs, paths, true);
|
||||||
else if (query == qReferences) store->queryReferences(path, paths);
|
else if (query == qReferences) store->queryReferences(path, paths);
|
||||||
else if (query == qStateReferences) store->queryStateReferences(path, paths);
|
else if (query == qStateReferences) store->queryStateReferences(path, paths);
|
||||||
else if (query == qReferrers) store->queryReferrers(path, paths);
|
else if (query == qReferrers) store->queryReferrers(path, paths);
|
||||||
else if (query == qStateReferrers) store->queryStateReferrers(path, paths);
|
else if (query == qStateReferrers) store->queryStateReferrers(path, paths);
|
||||||
else if (query == qReferrersClosure) computeFSClosure(path, paths, true);
|
else if (query == qReferrersClosure) computeFSClosure(path, paths, false, true);
|
||||||
|
else if (query == qReferrersClosureWithState) computeFSClosure(path, paths, true, true);
|
||||||
}
|
}
|
||||||
Paths sorted = topoSortPaths(paths);
|
Paths sorted = topoSortPaths(paths);
|
||||||
for (Paths::reverse_iterator i = sorted.rbegin();
|
for (Paths::reverse_iterator i = sorted.rbegin();
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue