hash: Add support for tuples

There is now builtin support for stdplus::hash<> and
stdplus::hashMulti(...) hashing std::tuple containers.

Change-Id: I0e0983c04d54302f00c811e5de0d949accee03d7
Signed-off-by: William A. Kennington III <wak@google.com>
diff --git a/include/meson.build b/include/meson.build
index 358bc32..fc304f3 100644
--- a/include/meson.build
+++ b/include/meson.build
@@ -7,6 +7,7 @@
   'stdplus/handle/copyable.hpp',
   'stdplus/handle/managed.hpp',
   'stdplus/hash.hpp',
+  'stdplus/hash/tuple.hpp',
   'stdplus/pinned.hpp',
   'stdplus/raw.hpp',
   'stdplus/signal.hpp',
diff --git a/include/stdplus/hash.hpp b/include/stdplus/hash.hpp
index 44cc6a6..f3aa8e6 100644
--- a/include/stdplus/hash.hpp
+++ b/include/stdplus/hash.hpp
@@ -1,5 +1,6 @@
 #pragma once
 #include <cstddef>
+#include <tuple>
 #include <utility>
 
 namespace std
@@ -65,4 +66,14 @@
 struct hash : std::hash<Key>
 {};
 
+template <typename... Ts>
+struct hash<std::tuple<Ts...>>
+{
+    constexpr std::size_t operator()(const std::tuple<Ts...>& ts) noexcept(
+        noexcept(hashMulti(std::declval<Ts>()...)))
+    {
+        return std::apply(hashMulti<Ts...>, ts);
+    }
+};
+
 } // namespace stdplus
diff --git a/include/stdplus/hash/tuple.hpp b/include/stdplus/hash/tuple.hpp
new file mode 100644
index 0000000..be7a45e
--- /dev/null
+++ b/include/stdplus/hash/tuple.hpp
@@ -0,0 +1,14 @@
+#pragma once
+#include <stdplus/hash.hpp>
+
+#include <tuple>
+
+template <typename... Ts>
+struct std::hash<std::tuple<Ts...>>
+{
+    constexpr auto operator()(const std::tuple<Ts...>& ts) const noexcept(
+        noexcept(stdplus::hashMulti(std::declval<std::tuple<Ts...>>())))
+    {
+        return stdplus::hashMulti(ts);
+    }
+};