// Copyright 2021 The Dawn & Tint Authors
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are met:
//
// 1. Redistributions of source code must retain the above copyright notice, this
//    list of conditions and the following disclaimer.
//
// 2. Redistributions in binary form must reproduce the above copyright notice,
//    this list of conditions and the following disclaimer in the documentation
//    and/or other materials provided with the distribution.
//
// 3. Neither the name of the copyright holder nor the names of its
//    contributors may be used to endorse or promote products derived from
//    this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
// DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
// FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
// DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
// SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
// CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
// OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

#ifndef SRC_TINT_UTILS_MATH_HASH_H_
#define SRC_TINT_UTILS_MATH_HASH_H_

#include <stdint.h>
#include <cstdio>
#include <functional>
#include <string>
#include <tuple>
#include <utility>
#include <variant>
#include <vector>

#include "src/tint/utils/math/crc32.h"

namespace tint {

namespace detail {

template <typename T, typename = void>
struct HasHashCodeMember : std::false_type {};

template <typename T>
struct HasHashCodeMember<
    T,
    std::enable_if_t<std::is_member_function_pointer_v<decltype(&T::HashCode)>>> : std::true_type {
};

}  // namespace detail

/// The type of a hash code
using HashCode = uint32_t;

/// Forward declarations (see below)
template <typename... ARGS>
HashCode Hash(const ARGS&... values);

template <typename... ARGS>
HashCode HashCombine(HashCode hash, const ARGS&... values);

/// A STL-compatible hasher that does a more thorough job than most implementations of std::hash.
/// Hasher has been optimized for a better quality hash at the expense of increased computation
/// costs.
/// Hasher is specialized for various core Tint data types. The default implementation will use a
/// `HashCode HashCode()` method on the `T` type, and will fallback to `std::hash<T>` if
/// `T::HashCode` is missing.
template <typename T>
struct Hasher {
    /// @param value the value to hash
    /// @returns a hash of the value
    HashCode operator()(const T& value) const {
        if constexpr (detail::HasHashCodeMember<T>::value) {
            auto hash = value.HashCode();
            static_assert(std::is_same_v<decltype(hash), HashCode>,
                          "T::HashCode() must return HashCode");
            return hash;
        } else {
            return static_cast<HashCode>(std::hash<T>()(value));
        }
    }
};

/// Hasher specialization for pointers
template <typename T>
struct Hasher<T*> {
    /// @param ptr the pointer to hash
    /// @returns a hash of the pointer
    HashCode operator()(T* ptr) const {
        auto hash = reinterpret_cast<uintptr_t>(ptr);
#ifdef TINT_HASH_SEED
        hash ^= static_cast<uint32_t>(TINT_HASH_SEED);
#endif
        if constexpr (sizeof(hash) > 4) {
            return static_cast<HashCode>(hash >> 4 | hash >> 32);
        } else {
            return static_cast<HashCode>(hash >> 4);
        }
    }
};

/// Hasher specialization for std::vector
template <typename T>
struct Hasher<std::vector<T>> {
    /// @param vector the vector to hash
    /// @returns a hash of the vector
    HashCode operator()(const std::vector<T>& vector) const {
        auto hash = Hash(vector.size());
        for (auto& el : vector) {
            hash = HashCombine(hash, el);
        }
        return hash;
    }
};

/// Hasher specialization for std::tuple
template <typename... TYPES>
struct Hasher<std::tuple<TYPES...>> {
    /// @param tuple the tuple to hash
    /// @returns a hash of the tuple
    HashCode operator()(const std::tuple<TYPES...>& tuple) const {
        return std::apply(Hash<TYPES...>, tuple);
    }
};

/// Hasher specialization for std::pair
template <typename A, typename B>
struct Hasher<std::pair<A, B>> {
    /// @param tuple the tuple to hash
    /// @returns a hash of the tuple
    HashCode operator()(const std::pair<A, B>& tuple) const {
        return std::apply(Hash<A, B>, tuple);
    }
};

/// Hasher specialization for std::variant
template <typename... TYPES>
struct Hasher<std::variant<TYPES...>> {
    /// @param variant the variant to hash
    /// @returns a hash of the tuple
    HashCode operator()(const std::variant<TYPES...>& variant) const {
        return std::visit([](auto&& val) { return Hash(val); }, variant);
    }
};

/// Hasher specialization for std::string, which also supports hashing of const char* and
/// std::string_view without first constructing a std::string.
template <>
struct Hasher<std::string> {
    /// @param str the string to hash
    /// @returns a hash of the string
    HashCode operator()(const std::string& str) const {
        return static_cast<HashCode>(std::hash<std::string_view>()(std::string_view(str)));
    }

    /// @param str the string to hash
    /// @returns a hash of the string
    HashCode operator()(const char* str) const {
        return static_cast<HashCode>(std::hash<std::string_view>()(std::string_view(str)));
    }

    /// @param str the string to hash
    /// @returns a hash of the string
    HashCode operator()(const std::string_view& str) const {
        return static_cast<HashCode>(std::hash<std::string_view>()(str));
    }
};

/// @param args the arguments to hash
/// @returns a hash of the variadic list of arguments.
///          The returned hash is dependent on the order of the arguments.
template <typename... ARGS>
HashCode Hash(const ARGS&... args) {
    if constexpr (sizeof...(ARGS) == 0) {
        return 0;
    } else if constexpr (sizeof...(ARGS) == 1) {
        using T = std::tuple_element_t<0, std::tuple<ARGS...>>;
        return Hasher<T>()(args...);
    } else {
        HashCode hash = 102931;  // seed with an arbitrary prime
        return HashCombine(hash, args...);
    }
}

/// @param hash the hash value to combine with
/// @param values the values to hash
/// @returns a hash of the variadic list of arguments.
///          The returned hash is dependent on the order of the arguments.
template <typename... ARGS>
HashCode HashCombine(HashCode hash, const ARGS&... values) {
#ifdef TINT_HASH_SEED
    constexpr uint32_t offset = 0x7f4a7c16 ^ static_cast<uint32_t>(TINT_HASH_SEED);
#else
    constexpr uint32_t offset = 0x7f4a7c16;
#endif

    ((hash ^= Hash(values) + (offset ^ (hash >> 2))), ...);
    return hash;
}

/// A STL-compatible equal_to implementation that specializes for types.
template <typename T>
struct EqualTo {
    /// @param lhs the left hand side value
    /// @param rhs the right hand side value
    /// @returns true if the two values are equal
    constexpr bool operator()(const T& lhs, const T& rhs) const {
        return std::equal_to<T>()(lhs, rhs);
    }
};

/// A specialization for EqualTo for std::string, which supports additional comparision with
/// std::string_view and const char*.
template <>
struct EqualTo<std::string> {
    /// @param lhs the left hand side value
    /// @param rhs the right hand side value
    /// @returns true if the two values are equal
    bool operator()(const std::string& lhs, const std::string& rhs) const { return lhs == rhs; }

    /// @param lhs the left hand side value
    /// @param rhs the right hand side value
    /// @returns true if the two values are equal
    bool operator()(const std::string& lhs, const char* rhs) const { return lhs == rhs; }

    /// @param lhs the left hand side value
    /// @param rhs the right hand side value
    /// @returns true if the two values are equal
    bool operator()(const std::string& lhs, std::string_view rhs) const { return lhs == rhs; }

    /// @param lhs the left hand side value
    /// @param rhs the right hand side value
    /// @returns true if the two values are equal
    bool operator()(const char* lhs, const std::string& rhs) const { return lhs == rhs; }

    /// @param lhs the left hand side value
    /// @param rhs the right hand side value
    /// @returns true if the two values are equal
    bool operator()(std::string_view lhs, const std::string& rhs) const { return lhs == rhs; }
};

/// Wrapper for a hashable type enabling the wrapped value to be used as a key
/// for an unordered_map or unordered_set.
template <typename T>
struct UnorderedKeyWrapper {
    /// The wrapped value
    T value;
    /// The hash of value
    HashCode hash;

    /// Constructor
    /// @param v the value to wrap
    explicit UnorderedKeyWrapper(const T& v) : value(v), hash(Hash(v)) {}

    /// Move constructor
    /// @param v the value to wrap
    explicit UnorderedKeyWrapper(T&& v) : value(std::move(v)), hash(Hash(value)) {}

    /// @returns true if this wrapper comes before other
    /// @param other the RHS of the operator
    bool operator<(const UnorderedKeyWrapper& other) const { return hash < other.hash; }

    /// @returns true if this wrapped value is equal to the other wrapped value
    /// @param other the RHS of the operator
    bool operator==(const UnorderedKeyWrapper& other) const { return value == other.value; }
};

}  // namespace tint

namespace std {

/// Custom std::hash specialization for tint::UnorderedKeyWrapper
template <typename T>
class hash<tint::UnorderedKeyWrapper<T>> {
  public:
    /// @param w the UnorderedKeyWrapper
    /// @return the hash value
    inline std::size_t operator()(const tint::UnorderedKeyWrapper<T>& w) const { return w.hash; }
};

}  // namespace std

#endif  // SRC_TINT_UTILS_MATH_HASH_H_
