* Updated `nix-store --verify' to the new schema.
This commit is contained in:
		
							parent
							
								
									60feff82cf
								
							
						
					
					
						commit
						3d74274b37
					
				
					 6 changed files with 106 additions and 26 deletions
				
			
		|  | @ -806,7 +806,7 @@ DerivationGoal::HookReply DerivationGoal::tryBuildHook() | ||||||
|         { |         { | ||||||
|             s += *i; |             s += *i; | ||||||
|             PathSet references; |             PathSet references; | ||||||
|             queryReferences(*i, references); |             queryReferences(noTxn, *i, references); | ||||||
|             for (PathSet::iterator j = references.begin(); |             for (PathSet::iterator j = references.begin(); | ||||||
|                  j != references.end(); ++j) |                  j != references.end(); ++j) | ||||||
|             { |             { | ||||||
|  | @ -1326,7 +1326,7 @@ void SubstitutionGoal::init() | ||||||
| 
 | 
 | ||||||
|     /* To maintain the closure invairant, we first have to realise the
 |     /* To maintain the closure invairant, we first have to realise the
 | ||||||
|        paths referenced by this one. */ |        paths referenced by this one. */ | ||||||
|     queryReferences(storePath, references); |     queryReferences(noTxn, storePath, references); | ||||||
| 
 | 
 | ||||||
|     for (PathSet::iterator i = references.begin(); |     for (PathSet::iterator i = references.begin(); | ||||||
|          i != references.end(); ++i) |          i != references.end(); ++i) | ||||||
|  |  | ||||||
|  | @ -279,7 +279,7 @@ static void dfsVisit(const PathSet & paths, const Path & path, | ||||||
|      |      | ||||||
|     PathSet references; |     PathSet references; | ||||||
|     if (isValidPath(path)) |     if (isValidPath(path)) | ||||||
|         queryReferences(path, references); |         queryReferences(noTxn, path, references); | ||||||
|      |      | ||||||
|     for (PathSet::iterator i = references.begin(); |     for (PathSet::iterator i = references.begin(); | ||||||
|          i != references.end(); ++i) |          i != references.end(); ++i) | ||||||
|  |  | ||||||
|  | @ -19,9 +19,9 @@ void computeFSClosure(const Path & storePath, | ||||||
| 
 | 
 | ||||||
|     PathSet references; |     PathSet references; | ||||||
|     if (flipDirection) |     if (flipDirection) | ||||||
|         queryReferers(storePath, references); |         queryReferers(noTxn, storePath, references); | ||||||
|     else |     else | ||||||
|         queryReferences(storePath, references); |         queryReferences(noTxn, storePath, references); | ||||||
| 
 | 
 | ||||||
|     for (PathSet::iterator i = references.begin(); |     for (PathSet::iterator i = references.begin(); | ||||||
|          i != references.end(); ++i) |          i != references.end(); ++i) | ||||||
|  |  | ||||||
|  | @ -325,21 +325,23 @@ void setReferences(const Transaction & txn, const Path & storePath, | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| 
 | 
 | ||||||
| void queryReferences(const Path & storePath, PathSet & references) | void queryReferences(const Transaction & txn, | ||||||
|  |     const Path & storePath, PathSet & references) | ||||||
| { | { | ||||||
|     Paths references2; |     Paths references2; | ||||||
|     if (!isRealisablePath(noTxn, storePath)) |     if (!isRealisablePath(txn, storePath)) | ||||||
|         throw Error(format("path `%1%' is not valid") % storePath); |         throw Error(format("path `%1%' is not valid") % storePath); | ||||||
|     nixDB.queryStrings(noTxn, dbReferences, storePath, references2); |     nixDB.queryStrings(txn, dbReferences, storePath, references2); | ||||||
|     references.insert(references2.begin(), references2.end()); |     references.insert(references2.begin(), references2.end()); | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| 
 | 
 | ||||||
| void queryReferers(const Path & storePath, PathSet & referers) | void queryReferers(const Transaction & txn, | ||||||
|  |     const Path & storePath, PathSet & referers) | ||||||
| { | { | ||||||
|     if (!isRealisablePath(noTxn, storePath)) |     if (!isRealisablePath(txn, storePath)) | ||||||
|         throw Error(format("path `%1%' is not valid") % storePath); |         throw Error(format("path `%1%' is not valid") % storePath); | ||||||
|     PathSet referers2 = getReferers(noTxn, storePath); |     PathSet referers2 = getReferers(txn, storePath); | ||||||
|     referers.insert(referers2.begin(), referers2.end()); |     referers.insert(referers2.begin(), referers2.end()); | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | @ -358,7 +360,7 @@ void setDeriver(const Transaction & txn, const Path & storePath, | ||||||
| 
 | 
 | ||||||
| Path queryDeriver(const Transaction & txn, const Path & storePath) | Path queryDeriver(const Transaction & txn, const Path & storePath) | ||||||
| { | { | ||||||
|     if (!isRealisablePath(noTxn, storePath)) |     if (!isRealisablePath(txn, storePath)) | ||||||
|         throw Error(format("path `%1%' is not valid") % storePath); |         throw Error(format("path `%1%' is not valid") % storePath); | ||||||
|     Path deriver; |     Path deriver; | ||||||
|     if (nixDB.queryString(txn, dbDerivers, storePath, deriver)) |     if (nixDB.queryString(txn, dbDerivers, storePath, deriver)) | ||||||
|  | @ -641,13 +643,8 @@ void verifyStore() | ||||||
|             validPaths.insert(path); |             validPaths.insert(path); | ||||||
|     } |     } | ||||||
| 
 | 
 | ||||||
|     /* !!! the code below does not allow transitive substitutes.
 |     /* "Usable" paths are those that are valid or have a
 | ||||||
|        I.e., if B is a substitute of A, then B must be a valid path. |        substitute. */ | ||||||
|        B cannot itself be invalid but have a substitute. */ |  | ||||||
| 
 |  | ||||||
|     /* "Usable" paths are those that are valid or have a substitute.
 |  | ||||||
|        These are the paths that are allowed to appear in the |  | ||||||
|        right-hand side of a sute mapping. */ |  | ||||||
|     PathSet usablePaths(validPaths); |     PathSet usablePaths(validPaths); | ||||||
| 
 | 
 | ||||||
|     /* Check that the values of the substitute mappings are valid
 |     /* Check that the values of the substitute mappings are valid
 | ||||||
|  | @ -656,11 +653,92 @@ void verifyStore() | ||||||
|     nixDB.enumTable(txn, dbSubstitutes, subKeys); |     nixDB.enumTable(txn, dbSubstitutes, subKeys); | ||||||
|     for (Paths::iterator i = subKeys.begin(); i != subKeys.end(); ++i) { |     for (Paths::iterator i = subKeys.begin(); i != subKeys.end(); ++i) { | ||||||
|         Substitutes subs = readSubstitutes(txn, *i); |         Substitutes subs = readSubstitutes(txn, *i); | ||||||
| 	if (subs.size() > 0) |         if (!isStorePath(*i)) { | ||||||
| 	    usablePaths.insert(*i); |             printMsg(lvlError, format("found substitutes for non-store path `%1%'") % *i); | ||||||
|         else |  | ||||||
|             nixDB.delPair(txn, dbSubstitutes, *i); |             nixDB.delPair(txn, dbSubstitutes, *i); | ||||||
|         } |         } | ||||||
|  |         else if (subs.size() == 0) | ||||||
|  |             nixDB.delPair(txn, dbSubstitutes, *i); | ||||||
|  |         else | ||||||
|  | 	    usablePaths.insert(*i); | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     /* Check the cleanup invariant: only usable paths can have
 | ||||||
|  |        `references', `referers', or `derivers' entries. */ | ||||||
|  | 
 | ||||||
|  |     /* Check the `derivers' table. */ | ||||||
|  |     Paths deriversKeys; | ||||||
|  |     nixDB.enumTable(txn, dbDerivers, deriversKeys); | ||||||
|  |     for (Paths::iterator i = deriversKeys.begin(); | ||||||
|  |          i != deriversKeys.end(); ++i) | ||||||
|  |     { | ||||||
|  |         if (usablePaths.find(*i) == usablePaths.end()) { | ||||||
|  |             printMsg(lvlError, format("found deriver entry for unusable path `%1%'") | ||||||
|  |                 % *i); | ||||||
|  |             nixDB.delPair(txn, dbDerivers, *i); | ||||||
|  |         } | ||||||
|  |         else { | ||||||
|  |             Path deriver = queryDeriver(txn, *i); | ||||||
|  |             if (!isStorePath(deriver)) { | ||||||
|  |                 printMsg(lvlError, format("found corrupt deriver `%1%' for `%2%'") | ||||||
|  |                     % deriver % *i); | ||||||
|  |                 nixDB.delPair(txn, dbDerivers, *i); | ||||||
|  |             } | ||||||
|  |         } | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     /* Check the `references' table. */ | ||||||
|  |     Paths referencesKeys; | ||||||
|  |     nixDB.enumTable(txn, dbReferences, referencesKeys); | ||||||
|  |     for (Paths::iterator i = referencesKeys.begin(); | ||||||
|  |          i != referencesKeys.end(); ++i) | ||||||
|  |     { | ||||||
|  |         if (usablePaths.find(*i) == usablePaths.end()) { | ||||||
|  |             printMsg(lvlError, format("found references entry for unusable path `%1%'") | ||||||
|  |                 % *i); | ||||||
|  |             nixDB.delPair(txn, dbReferences, *i); | ||||||
|  |         } | ||||||
|  |         else { | ||||||
|  |             PathSet references; | ||||||
|  |             queryReferences(txn, *i, references); | ||||||
|  |             for (PathSet::iterator j = references.begin(); | ||||||
|  |                  j != references.end(); ++j) | ||||||
|  |             { | ||||||
|  |                 PathSet referers = getReferers(txn, *j); | ||||||
|  |                 if (referers.find(*i) == referers.end()) { | ||||||
|  |                     printMsg(lvlError, format("missing referer mapping from `%1%' to `%2%'") | ||||||
|  |                         % *j % *i); | ||||||
|  |                 } | ||||||
|  |             } | ||||||
|  |         } | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     /* Check the `referers' table. */ | ||||||
|  |     Paths referersKeys; | ||||||
|  |     nixDB.enumTable(txn, dbReferers, referersKeys); | ||||||
|  |     for (Paths::iterator i = referersKeys.begin(); | ||||||
|  |          i != referersKeys.end(); ++i) | ||||||
|  |     { | ||||||
|  |         if (usablePaths.find(*i) == usablePaths.end()) { | ||||||
|  |             printMsg(lvlError, format("found referers entry for unusable path `%1%'") | ||||||
|  |                 % *i); | ||||||
|  |             nixDB.delPair(txn, dbReferers, *i); | ||||||
|  |         } | ||||||
|  |         else { | ||||||
|  |             PathSet referers; | ||||||
|  |             queryReferers(txn, *i, referers); | ||||||
|  |             for (PathSet::iterator j = referers.begin(); | ||||||
|  |                  j != referers.end(); ++j) | ||||||
|  |             { | ||||||
|  |                 Paths references; | ||||||
|  |                 nixDB.queryStrings(txn, dbReferences, *j, references); | ||||||
|  |                 if (find(references.begin(), references.end(), *i) == references.end()) { | ||||||
|  |                     printMsg(lvlError, format("missing reference mapping from `%1%' to `%2%'") | ||||||
|  |                         % *j % *i); | ||||||
|  |                 } | ||||||
|  |             } | ||||||
|  |         } | ||||||
|  |     } | ||||||
| 
 | 
 | ||||||
|     txn.commit(); |     txn.commit(); | ||||||
| } | } | ||||||
|  |  | ||||||
|  | @ -90,11 +90,13 @@ void setReferences(const Transaction & txn, const Path & storePath, | ||||||
| 
 | 
 | ||||||
| /* Queries the set of outgoing FS references for a store path.  The
 | /* Queries the set of outgoing FS references for a store path.  The
 | ||||||
|    result is not cleared. */ |    result is not cleared. */ | ||||||
| void queryReferences(const Path & storePath, PathSet & references); | void queryReferences(const Transaction & txn, | ||||||
|  |     const Path & storePath, PathSet & references); | ||||||
| 
 | 
 | ||||||
| /* Queries the set of incoming FS references for a store path.  The
 | /* Queries the set of incoming FS references for a store path.  The
 | ||||||
|    result is not cleared. */ |    result is not cleared. */ | ||||||
| void queryReferers(const Path & storePath, PathSet & referers); | void queryReferers(const Transaction & txn, | ||||||
|  |     const Path & storePath, PathSet & referers); | ||||||
| 
 | 
 | ||||||
| /* Sets the deriver of a store path.  Use with care! */ | /* Sets the deriver of a store path.  Use with care! */ | ||||||
| void setDeriver(const Transaction & txn, const Path & storePath, | void setDeriver(const Transaction & txn, const Path & storePath, | ||||||
|  |  | ||||||
|  | @ -215,8 +215,8 @@ static void opQuery(Strings opFlags, Strings opArgs) | ||||||
|                 Path path = maybeUseOutput(*i, useOutput, forceRealise); |                 Path path = maybeUseOutput(*i, useOutput, forceRealise); | ||||||
|                 if (query == qRequisites) |                 if (query == qRequisites) | ||||||
|                     storePathRequisites(path, includeOutputs, paths); |                     storePathRequisites(path, includeOutputs, paths); | ||||||
|                 else if (query == qReferences) queryReferences(path, paths); |                 else if (query == qReferences) queryReferences(noTxn, path, paths); | ||||||
|                 else if (query == qReferers) queryReferers(path,  paths); |                 else if (query == qReferers) queryReferers(noTxn, path,  paths); | ||||||
|                 else if (query == qReferersClosure) computeFSClosure(path, paths, true); |                 else if (query == qReferersClosure) computeFSClosure(path, paths, true); | ||||||
|             } |             } | ||||||
|             printPathSet(paths); |             printPathSet(paths); | ||||||
|  |  | ||||||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue