aboutsummaryrefslogtreecommitdiff
path: root/src/libstore/worker-protocol.hh
diff options
context:
space:
mode:
authorJohn Ericson <John.Ericson@Obsidian.Systems>2020-10-09 18:26:47 +0000
committerJohn Ericson <John.Ericson@Obsidian.Systems>2020-10-09 18:26:47 +0000
commit39de73550dd5579c2b3f14f7ce669d3f8ed85689 (patch)
tree79194a4ed21a04ebca269005d2e188532e460fab /src/libstore/worker-protocol.hh
parentcfe791a638a3fdf53a2608f885c407bafc238094 (diff)
parente845d19ae368cb9ee6371c4b2fdbdc86a110d893 (diff)
Merge remote-tracking branch 'upstream/master' into fix-and-ci-static-builds
Diffstat (limited to 'src/libstore/worker-protocol.hh')
-rw-r--r--src/libstore/worker-protocol.hh109
1 files changed, 55 insertions, 54 deletions
diff --git a/src/libstore/worker-protocol.hh b/src/libstore/worker-protocol.hh
index 13cf8d4ab..b3705578e 100644
--- a/src/libstore/worker-protocol.hh
+++ b/src/libstore/worker-protocol.hh
@@ -6,7 +6,7 @@ namespace nix {
#define WORKER_MAGIC_1 0x6e697863
#define WORKER_MAGIC_2 0x6478696f
-#define PROTOCOL_VERSION 0x118
+#define PROTOCOL_VERSION 0x11a
#define GET_PROTOCOL_MAJOR(x) ((x) & 0xff00)
#define GET_PROTOCOL_MINOR(x) ((x) & 0x00ff)
@@ -18,7 +18,7 @@ typedef enum {
wopQueryReferences = 5, // obsolete
wopQueryReferrers = 6,
wopAddToStore = 7,
- wopAddTextToStore = 8,
+ wopAddTextToStore = 8, // obsolete since 1.25, Nix 3.0. Use wopAddToStore
wopBuildPaths = 9,
wopEnsurePath = 10,
wopAddTempRoot = 11,
@@ -66,10 +66,6 @@ typedef enum {
class Store;
struct Source;
-template<class T> T readStorePaths(const Store & store, Source & from);
-
-void writeStorePaths(const Store & store, Sink & out, const StorePathSet & paths);
-
/* To guide overloading */
template<typename T>
struct Phantom {};
@@ -78,76 +74,81 @@ struct Phantom {};
namespace worker_proto {
/* FIXME maybe move more stuff inside here */
-StorePath read(const Store & store, Source & from, Phantom<StorePath> _);
-void write(const Store & store, Sink & out, const StorePath & storePath);
+#define MAKE_WORKER_PROTO(TEMPLATE, T) \
+ TEMPLATE T read(const Store & store, Source & from, Phantom< T > _); \
+ TEMPLATE void write(const Store & store, Sink & out, const T & str)
-template<typename T>
-std::map<std::string, T> read(const Store & store, Source & from, Phantom<std::map<std::string, T>> _);
-template<typename T>
-void write(const Store & store, Sink & out, const std::map<string, T> & resMap);
-template<typename T>
-std::optional<T> read(const Store & store, Source & from, Phantom<std::optional<T>> _);
-template<typename T>
-void write(const Store & store, Sink & out, const std::optional<T> & optVal);
+MAKE_WORKER_PROTO(, std::string);
+MAKE_WORKER_PROTO(, StorePath);
+MAKE_WORKER_PROTO(, ContentAddress);
-/* Specialization which uses and empty string for the empty case, taking
- advantage of the fact StorePaths always serialize to a non-empty string.
- This is done primarily for backwards compatability, so that StorePath <=
- std::optional<StorePath>, where <= is the compatability partial order.
+MAKE_WORKER_PROTO(template<typename T>, std::set<T>);
+
+#define X_ template<typename K, typename V>
+#define Y_ std::map<K, V>
+MAKE_WORKER_PROTO(X_, Y_);
+#undef X_
+#undef Y_
+
+/* These use the empty string for the null case, relying on the fact
+ that the underlying types never serialize to the empty string.
+
+ We do this instead of a generic std::optional<T> instance because
+ ordinal tags (0 or 1, here) are a bit of a compatability hazard. For
+ the same reason, we don't have a std::variant<T..> instances (ordinal
+ tags 0...n).
+
+ We could the generic instances and then these as specializations for
+ compatability, but that's proven a bit finnicky, and also makes the
+ worker protocol harder to implement in other languages where such
+ specializations may not be allowed.
*/
-template<>
-void write(const Store & store, Sink & out, const std::optional<StorePath> & optVal);
+MAKE_WORKER_PROTO(, std::optional<StorePath>);
+MAKE_WORKER_PROTO(, std::optional<ContentAddress>);
template<typename T>
-std::map<std::string, T> read(const Store & store, Source & from, Phantom<std::map<std::string, T>> _)
+std::set<T> read(const Store & store, Source & from, Phantom<std::set<T>> _)
{
- std::map<string, T> resMap;
- auto size = (size_t)readInt(from);
+ std::set<T> resSet;
+ auto size = readNum<size_t>(from);
while (size--) {
- auto thisKey = readString(from);
- resMap.insert_or_assign(std::move(thisKey), nix::worker_proto::read(store, from, Phantom<T> {}));
+ resSet.insert(read(store, from, Phantom<T> {}));
}
- return resMap;
+ return resSet;
}
template<typename T>
-void write(const Store & store, Sink & out, const std::map<string, T> & resMap)
+void write(const Store & store, Sink & out, const std::set<T> & resSet)
{
- out << resMap.size();
- for (auto & i : resMap) {
- out << i.first;
- nix::worker_proto::write(store, out, i.second);
+ out << resSet.size();
+ for (auto & key : resSet) {
+ write(store, out, key);
}
}
-template<typename T>
-std::optional<T> read(const Store & store, Source & from, Phantom<std::optional<T>> _)
+template<typename K, typename V>
+std::map<K, V> read(const Store & store, Source & from, Phantom<std::map<K, V>> _)
{
- auto tag = readNum<uint8_t>(from);
- switch (tag) {
- case 0:
- return std::nullopt;
- case 1:
- return nix::worker_proto::read(store, from, Phantom<T> {});
- default:
- throw Error("got an invalid tag bit for std::optional: %#04x", tag);
+ std::map<K, V> resMap;
+ auto size = readNum<size_t>(from);
+ while (size--) {
+ auto k = read(store, from, Phantom<K> {});
+ auto v = read(store, from, Phantom<V> {});
+ resMap.insert_or_assign(std::move(k), std::move(v));
}
+ return resMap;
}
-template<typename T>
-void write(const Store & store, Sink & out, const std::optional<T> & optVal)
+template<typename K, typename V>
+void write(const Store & store, Sink & out, const std::map<K, V> & resMap)
{
- out << (optVal ? 1 : 0);
- if (optVal)
- nix::worker_proto::write(store, out, *optVal);
+ out << resMap.size();
+ for (auto & i : resMap) {
+ write(store, out, i.first);
+ write(store, out, i.second);
+ }
}
-
}
-
-StorePathCAMap readStorePathCAMap(const Store & store, Source & from);
-
-void writeStorePathCAMap(const Store & store, Sink & out, const StorePathCAMap & paths);
-
}