aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorCarlo Nucera <carlo.nucera@protonmail.com>2020-06-01 18:53:31 -0400
committerCarlo Nucera <carlo.nucera@protonmail.com>2020-06-01 18:53:31 -0400
commitda39092a39bbcca80144041b5efc8428cc3b2e4a (patch)
tree3816bca4737a6a895d4a921c90f83abfb5d26263
parent0e9438b6d381a87946ddda8d4bdd06707f9b0a48 (diff)
WIP
-rw-r--r--src/libstore/file-hash.hh17
-rw-r--r--src/libstore/path.hh10
-rw-r--r--src/libstore/store-api.cc2
-rw-r--r--src/libstore/store-api.hh32
-rw-r--r--src/nix-store/nix-store.cc2
5 files changed, 47 insertions, 16 deletions
diff --git a/src/libstore/file-hash.hh b/src/libstore/file-hash.hh
index 94122db07..9d2b78688 100644
--- a/src/libstore/file-hash.hh
+++ b/src/libstore/file-hash.hh
@@ -1,5 +1,6 @@
#pragma once
+#include <variant>
#include "hash.hh"
namespace nix {
@@ -23,6 +24,22 @@ struct FileSystemHash {
std::string printMethodAlgo() const;
};
+/*
+ We've accumulated several types of content-addressed paths over the years;
+ fixed-output derivations support multiple hash algorithms and serialisation
+ methods (flat file vs NAR). Thus, ‘ca’ has one of the following forms:
+
+ * ‘text:sha256:<sha256 hash of file contents>’: For paths
+ computed by makeTextPath() / addTextToStore().
+
+ * ‘fixed:<r?>:<ht>:<h>’: For paths computed by
+ makeFixedOutputPath() / addToStore().
+*/
+typedef std::variant<
+ Hash, // for paths computed by makeTextPath() / addTextToStore
+ FileSystemHash // for path computed by makeFixedOutputPath
+> ContentAddress;
+
/* Compute the prefix to the hash algorithm which indicates how the files were
ingested. */
std::string makeFileIngestionPrefix(const FileIngestionMethod m);
diff --git a/src/libstore/path.hh b/src/libstore/path.hh
index 186976855..5268b3bbf 100644
--- a/src/libstore/path.hh
+++ b/src/libstore/path.hh
@@ -1,6 +1,7 @@
#pragma once
#include "rust-ffi.hh"
+#include "file-hash.hh"
namespace nix {
@@ -87,6 +88,15 @@ const size_t storePathHashLen = 32; // i.e. 160 bits
/* Extension of derivations in the Nix store. */
const std::string drvExtension = ".drv";
+std::string to_string(FileIngestionMethod m) {
+ switch(m) {
+ case FileIngestionMethod::Flat:
+ return "false";
+ case FileIngestionMethod::Recursive:
+ return "true";
+ }
+}
+
struct StorePathWithOutputs
{
StorePath path;
diff --git a/src/libstore/store-api.cc b/src/libstore/store-api.cc
index 3c72dc56f..0a36dcb2b 100644
--- a/src/libstore/store-api.cc
+++ b/src/libstore/store-api.cc
@@ -467,7 +467,7 @@ void Store::pathInfoToJSON(JSONPlaceholder & jsonOut, const StorePathSet & store
jsonRefs.elem(printStorePath(ref));
}
- if (info->ca != "")
+ if (info->ca)
jsonPath.attr("ca", info->ca);
std::pair<uint64_t, uint64_t> closureSizes;
diff --git a/src/libstore/store-api.hh b/src/libstore/store-api.hh
index d89e10c94..1f1c1e0eb 100644
--- a/src/libstore/store-api.hh
+++ b/src/libstore/store-api.hh
@@ -19,6 +19,7 @@
#include <memory>
#include <string>
#include <chrono>
+#include <variant>
namespace nix {
@@ -110,6 +111,19 @@ struct SubstitutablePathInfo
typedef std::map<StorePath, SubstitutablePathInfo> SubstitutablePathInfos;
+template<class... Ts> struct overloaded : Ts... { using Ts::operator()...; };
+template<class... Ts> overloaded(Ts...) -> overloaded<Ts...>;
+
+std::string renderContentAddress(ContentAddress ca) {
+ return std::visit(overloaded {
+ [](Hash hash) {
+ return "text:" + hash.to_string();
+ },
+ [](FileSystemHash fsh) {
+ return makeFixedOutputCA(fsh.method, fsh.hash);
+ }
+ }, ca);
+}
struct ValidPathInfo
{
@@ -139,21 +153,11 @@ struct ValidPathInfo
that a particular output path was produced by a derivation; the
path then implies the contents.)
- Ideally, the content-addressability assertion would just be a
- Boolean, and the store path would be computed from
- the name component, ‘narHash’ and ‘references’. However,
- 1) we've accumulated several types of content-addressed paths
- over the years; and 2) fixed-output derivations support
- multiple hash algorithms and serialisation methods (flat file
- vs NAR). Thus, ‘ca’ has one of the following forms:
-
- * ‘text:sha256:<sha256 hash of file contents>’: For paths
- computed by makeTextPath() / addTextToStore().
-
- * ‘fixed:<r?>:<ht>:<h>’: For paths computed by
- makeFixedOutputPath() / addToStore().
+ Ideally, the content-addressability assertion would just be a Boolean,
+ and the store path would be computed from the name component, ‘narHash’
+ and ‘references’. However, we support many types of content addresses.
*/
- std::string ca;
+ std::optional<ContentAddress> ca;
bool operator == (const ValidPathInfo & i) const
{
diff --git a/src/nix-store/nix-store.cc b/src/nix-store/nix-store.cc
index ace593cde..6f3a59002 100644
--- a/src/nix-store/nix-store.cc
+++ b/src/nix-store/nix-store.cc
@@ -856,7 +856,7 @@ static void opServe(Strings opFlags, Strings opArgs)
out << info->narSize // downloadSize
<< info->narSize;
if (GET_PROTOCOL_MINOR(clientVersion) >= 4)
- out << (info->narHash ? info->narHash.to_string() : "") << info->ca << info->sigs;
+ out << (info->narHash ? info->narHash.to_string() : "") << renderContentAddress(info->ca) << info->sigs;
} catch (InvalidPath &) {
}
}