* Start move towards SHA-256 hashes instead of MD5.
* Start cleaning up unique store path generation (they weren't always
  unique; in particular the suffix ("-aterm-2.2", "-builder.sh") was
  not part of the hash, therefore changes to the suffix would cause
  multiple store objects with the same hash).
			
			
This commit is contained in:
		
							parent
							
								
									a7b94e87d7
								
							
						
					
					
						commit
						9530cc3170
					
				
					 9 changed files with 63 additions and 34 deletions
				
			
		|  | @ -59,7 +59,7 @@ static Path copyAtom(EvalState & state, const Path & srcPath) | |||
|     ne.closure.elems[dstPath] = elem; | ||||
| 
 | ||||
|     Hash drvHash = hashDerivation(state, ne); | ||||
|     Path drvPath = writeTerm(unparseStoreExpr(ne), ""); | ||||
|     Path drvPath = writeTerm(unparseStoreExpr(ne), "c"); | ||||
|     state.drvHashes.insert(make_pair(drvPath, drvHash)); | ||||
| 
 | ||||
|     state.drvRoots[drvPath] = ne.closure.roots; | ||||
|  | @ -251,20 +251,31 @@ static Expr primDerivation(EvalState & state, const ATermVector & _args) | |||
|                 % *i % drvName); | ||||
|         } | ||||
| 
 | ||||
|     /* Construct the "masked" derivation store expression, which is
 | ||||
|        the final one except that the list of output paths is set to | ||||
|        the set of output names, and the corresponding environment | ||||
|        variables have an empty value.  This ensures that changes in | ||||
|        the set of output names do get reflected in the hash. */ | ||||
|     ne.derivation.env["out"] = ""; | ||||
|     ne.derivation.outputs.insert("out"); | ||||
|          | ||||
|     /* Determine the output path by hashing the Nix expression with no
 | ||||
|        outputs to produce a unique but deterministic path name for | ||||
|        this derivation. */ | ||||
|     if (!outHashGiven) outHash = hashDerivation(state, ne); | ||||
|     Path outPath = canonPath(nixStore + "/" +  | ||||
|         ((string) outHash).c_str() + "-" + drvName); | ||||
|     Path outPath = makeStorePath("output:out", | ||||
|         outHash, drvName); | ||||
| 
 | ||||
|     /* Construct the final derivation store expression. */ | ||||
|     ne.derivation.env["out"] = outPath; | ||||
|     ne.derivation.outputs.clear(); | ||||
|     ne.derivation.outputs.insert(outPath); | ||||
| 
 | ||||
|     /* Write the resulting term into the Nix store directory. */ | ||||
|     Hash drvHash = outHashGiven | ||||
|         ? hashString((string) outHash + outPath, htMD5) | ||||
|         : hashDerivation(state, ne); | ||||
|     Path drvPath = writeTerm(unparseStoreExpr(ne), "-d-" + drvName); | ||||
|     Path drvPath = writeTerm(unparseStoreExpr(ne), "d-" + drvName); | ||||
| 
 | ||||
|     printMsg(lvlChatty, format("instantiated `%1%' -> `%2%'") | ||||
|         % drvName % drvPath); | ||||
|  |  | |||
|  | @ -69,10 +69,10 @@ static void initAndRun(int argc, char * * argv) | |||
|     } | ||||
|      | ||||
|     /* Setup Nix paths. */ | ||||
|     nixStore = getEnv("NIX_STORE_DIR", canonPath(NIX_STORE_DIR)); | ||||
|     nixDataDir = getEnv("NIX_DATA_DIR", canonPath(NIX_DATA_DIR)); | ||||
|     nixLogDir = getEnv("NIX_LOG_DIR", canonPath(NIX_LOG_DIR)); | ||||
|     nixStateDir = getEnv("NIX_STATE_DIR", canonPath(NIX_STATE_DIR)); | ||||
|     nixStore = canonPath(getEnv("NIX_STORE_DIR", NIX_STORE_DIR)); | ||||
|     nixDataDir = canonPath(getEnv("NIX_DATA_DIR", NIX_DATA_DIR)); | ||||
|     nixLogDir = canonPath(getEnv("NIX_LOG_DIR", NIX_LOG_DIR)); | ||||
|     nixStateDir = canonPath(getEnv("NIX_STATE_DIR", NIX_STATE_DIR)); | ||||
|     nixDBPath = getEnv("NIX_DB_DIR", nixStateDir + "/db"); | ||||
| 
 | ||||
|     /* Check that the store directory and its parent are not
 | ||||
|  |  | |||
|  | @ -1137,7 +1137,7 @@ void NormalisationGoal::createClosure() | |||
|     /* Write the normal form.  This does not have to occur in the
 | ||||
|        transaction below because writing terms is idem-potent. */ | ||||
|     ATerm nfTerm = unparseStoreExpr(nf); | ||||
|     Path nfPath = writeTerm(nfTerm, "-s"); | ||||
|     Path nfPath = writeTerm(nfTerm, "s"); | ||||
| 
 | ||||
|     /* Register each output path, and register the normal form.  This
 | ||||
|        is wrapped in one database transaction to ensure that if we | ||||
|  |  | |||
|  | @ -411,19 +411,34 @@ static void invalidatePath(const Path & path, Transaction & txn) | |||
| } | ||||
| 
 | ||||
| 
 | ||||
| Path makeStorePath(const string & type, | ||||
|     Hash & hash, const string & suffix) | ||||
| { | ||||
|     /* e.g., "source:sha256:1abc...:/nix/store:foo.tar.gz" */ | ||||
|     string s = type + ":sha256:" + (string) hash + ":" | ||||
|         + nixStore + ":" + suffix; | ||||
| 
 | ||||
|     Hash nameHash = hashString(s, htSHA256); | ||||
| 
 | ||||
|     printMsg(lvlError, format("name input: %1% -> %2%") % s % (string) nameHash); | ||||
| 
 | ||||
|     return nixStore + "/" + (string) nameHash + "-" + suffix; | ||||
| } | ||||
| 
 | ||||
| 
 | ||||
| Path addToStore(const Path & _srcPath) | ||||
| { | ||||
|     Path srcPath(absPath(_srcPath)); | ||||
|     debug(format("adding `%1%' to the store") % srcPath); | ||||
| 
 | ||||
|     Hash h(htMD5); | ||||
|     Hash h(htSHA256); | ||||
|     { | ||||
|         SwitchToOriginalUser sw; | ||||
|         h = hashPath(srcPath, htMD5); | ||||
|         h = hashPath(srcPath, htSHA256); | ||||
|     } | ||||
| 
 | ||||
|     string baseName = baseNameOf(srcPath); | ||||
|     Path dstPath = canonPath(nixStore + "/" + (string) h + "-" + baseName); | ||||
|     Path dstPath = makeStorePath("source", h, baseName); | ||||
| 
 | ||||
|     if (!readOnlyMode && !isValidPath(dstPath)) {  | ||||
| 
 | ||||
|  | @ -443,6 +458,11 @@ Path addToStore(const Path & _srcPath) | |||
|              | ||||
|             copyPath(srcPath, dstPath); | ||||
| 
 | ||||
|             Hash h2 = hashPath(dstPath, htSHA256); | ||||
|             if (h != h2) | ||||
|                 throw Error(format("contents of `%1%' changed while copying it to `%2%' (%3% -> %4%)") | ||||
|                     % srcPath % dstPath % (string) h % (string) h2); | ||||
| 
 | ||||
|             makePathReadOnly(dstPath); | ||||
|              | ||||
|             Transaction txn(nixDB); | ||||
|  | @ -457,11 +477,13 @@ Path addToStore(const Path & _srcPath) | |||
| } | ||||
| 
 | ||||
| 
 | ||||
| void addTextToStore(const Path & dstPath, const string & s) | ||||
| Path addTextToStore(const string & suffix, const string & s) | ||||
| { | ||||
|     assertStorePath(dstPath); | ||||
|     Hash hash = hashString(s, htSHA256); | ||||
| 
 | ||||
|     if (!isValidPath(dstPath)) { | ||||
|     Path dstPath = makeStorePath("text", hash, suffix); | ||||
|      | ||||
|     if (!readOnlyMode && !isValidPath(dstPath)) { | ||||
| 
 | ||||
|         PathSet lockPaths; | ||||
|         lockPaths.insert(dstPath); | ||||
|  | @ -482,6 +504,8 @@ void addTextToStore(const Path & dstPath, const string & s) | |||
| 
 | ||||
|         outputLock.setDeletion(true); | ||||
|     } | ||||
| 
 | ||||
|     return dstPath; | ||||
| } | ||||
| 
 | ||||
| 
 | ||||
|  |  | |||
|  | @ -81,14 +81,17 @@ void assertStorePath(const Path & path); | |||
| /* Checks whether a path is valid. */  | ||||
| bool isValidPath(const Path & path); | ||||
| 
 | ||||
| /* Constructs a unique store path name. */ | ||||
| Path makeStorePath(const string & type, | ||||
|     Hash & hash, const string & suffix); | ||||
|      | ||||
| /* Copy the contents of a path to the store and register the validity
 | ||||
|    the resulting path.  The resulting path is returned. */ | ||||
| Path addToStore(const Path & srcPath); | ||||
| 
 | ||||
| /* Like addToStore, but the path of the output is given, and the
 | ||||
|    contents written to the output path is a regular file containing | ||||
|    the given string. */ | ||||
| void addTextToStore(const Path & dstPath, const string & s); | ||||
| /* Like addToStore, but the contents written to the output path is a
 | ||||
|    regular file containing the given string. */ | ||||
| Path addTextToStore(const string & suffix, const string & s); | ||||
| 
 | ||||
| /* Delete a value from the nixStore directory. */ | ||||
| void deleteFromStore(const Path & path); | ||||
|  |  | |||
|  | @ -14,19 +14,9 @@ Hash hashTerm(ATerm t) | |||
| 
 | ||||
| Path writeTerm(ATerm t, const string & suffix) | ||||
| { | ||||
|     /* The id of a term is its hash. */ | ||||
|     Hash h = hashTerm(t); | ||||
| 
 | ||||
|     Path path = canonPath(nixStore + "/" +  | ||||
|         (string) h + suffix + ".store"); | ||||
| 
 | ||||
|     if (!readOnlyMode && !isValidPath(path)) { | ||||
|     char * s = ATwriteToString(t); | ||||
|         if (!s) throw Error(format("cannot write aterm to `%1%'") % path); | ||||
|         addTextToStore(path, string(s)); | ||||
|     } | ||||
|      | ||||
|     return path; | ||||
|     if (!s) throw Error("cannot print aterm"); | ||||
|     return addTextToStore(suffix + ".store", string(s)); | ||||
| } | ||||
| 
 | ||||
| 
 | ||||
|  |  | |||
|  | @ -22,6 +22,7 @@ Hash::Hash(HashType type) | |||
|     else if (type == htSHA1) hashSize = sha1HashSize; | ||||
|     else if (type == htSHA256) hashSize = sha256HashSize; | ||||
|     else throw Error("unknown hash type"); | ||||
|     assert(hashSize <= maxHashSize); | ||||
|     memset(hash, 0, hashSize); | ||||
| } | ||||
| 
 | ||||
|  |  | |||
|  | @ -18,7 +18,7 @@ const int sha256HashSize = 32; | |||
| 
 | ||||
| struct Hash | ||||
| { | ||||
|     static const unsigned int maxHashSize = 20; | ||||
|     static const unsigned int maxHashSize = 32; | ||||
|     unsigned int hashSize; | ||||
|     unsigned char hash[maxHashSize]; | ||||
| 
 | ||||
|  |  | |||
|  | @ -216,7 +216,7 @@ void createUserEnv(EvalState & state, const DrvInfos & drvs, | |||
| 
 | ||||
|     /* Also write a copy of the list of inputs to the store; we need
 | ||||
|        it for future modifications of the environment. */ | ||||
|     Path inputsFile = writeTerm(inputs2, "-env-inputs"); | ||||
|     Path inputsFile = writeTerm(inputs2, "env-inputs"); | ||||
| 
 | ||||
|     Expr topLevel = makeCall(envBuilder, makeAttrs(ATmakeList3( | ||||
|         makeBind(toATerm("system"), | ||||
|  |  | |||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue