2019-07-08 14:04:52 +00:00
|
|
|
/* EVMC: Ethereum Client-VM Connector API.
|
|
|
|
* Copyright 2018-2019 The EVMC Authors.
|
|
|
|
* Licensed under the Apache License, Version 2.0.
|
|
|
|
*/
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @file
|
|
|
|
* A collection of helpers (overloaded operators) for using EVMC types effectively in C++.
|
|
|
|
*
|
|
|
|
* @addtogroup helpers
|
|
|
|
* @{
|
|
|
|
*/
|
|
|
|
#pragma once
|
|
|
|
|
2019-11-07 10:34:12 +00:00
|
|
|
#include <evmc/evmc.hpp>
|
2019-07-08 14:04:52 +00:00
|
|
|
|
|
|
|
#include <cstring>
|
|
|
|
#include <functional>
|
|
|
|
|
2019-11-07 10:34:12 +00:00
|
|
|
using evmc::is_zero;
|
|
|
|
|
2019-07-08 14:04:52 +00:00
|
|
|
/// The comparator for std::map<evmc_address, ...>.
|
2019-11-07 10:34:12 +00:00
|
|
|
EVMC_DEPRECATED
|
2019-07-08 14:04:52 +00:00
|
|
|
inline bool operator<(const evmc_address& a, const evmc_address& b)
|
|
|
|
{
|
|
|
|
return std::memcmp(a.bytes, b.bytes, sizeof(a.bytes)) < 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
/// The comparator for std::map<evmc_bytes32, ...>.
|
2019-11-07 10:34:12 +00:00
|
|
|
EVMC_DEPRECATED
|
2019-07-08 14:04:52 +00:00
|
|
|
inline bool operator<(const evmc_bytes32& a, const evmc_bytes32& b)
|
|
|
|
{
|
|
|
|
return std::memcmp(a.bytes, b.bytes, sizeof(a.bytes)) < 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
/// The comparator for equality.
|
2019-11-07 10:34:12 +00:00
|
|
|
EVMC_DEPRECATED
|
2019-07-08 14:04:52 +00:00
|
|
|
inline bool operator==(const evmc_address& a, const evmc_address& b)
|
|
|
|
{
|
|
|
|
return std::memcmp(a.bytes, b.bytes, sizeof(a.bytes)) == 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
/// The comparator for equality.
|
2019-11-07 10:34:12 +00:00
|
|
|
EVMC_DEPRECATED
|
2019-07-08 14:04:52 +00:00
|
|
|
inline bool operator==(const evmc_bytes32& a, const evmc_bytes32& b)
|
|
|
|
{
|
|
|
|
return std::memcmp(a.bytes, b.bytes, sizeof(a.bytes)) == 0;
|
|
|
|
}
|
|
|
|
|
2019-11-07 10:34:12 +00:00
|
|
|
/// Parameters for the fnv1a hash function, specialized by the hash result size (size_t).
|
|
|
|
///
|
|
|
|
/// The values for the matching size are taken from
|
|
|
|
/// https://en.wikipedia.org/wiki/Fowler%E2%80%93Noll%E2%80%93Vo_hash_function#FNV_hash_parameters.
|
|
|
|
///
|
|
|
|
/// @tparam size The size of the hash result (size_t).
|
|
|
|
template <size_t size>
|
|
|
|
struct fnv1_params
|
2019-07-08 14:04:52 +00:00
|
|
|
{
|
2019-11-07 10:34:12 +00:00
|
|
|
};
|
2019-07-08 14:04:52 +00:00
|
|
|
|
2019-11-07 10:34:12 +00:00
|
|
|
/// Parameters for the fnv1a hash function, specialized for the hash result of 4 bytes.
|
|
|
|
template <>
|
|
|
|
struct fnv1_params<4>
|
2019-07-08 14:04:52 +00:00
|
|
|
{
|
2019-11-07 10:34:12 +00:00
|
|
|
static constexpr auto prime = 0x1000193; ///< The FNV prime.
|
|
|
|
static constexpr auto offset_basis = 0x811c9dc5; ///< The FNV offset basis.
|
|
|
|
};
|
|
|
|
|
|
|
|
/// Parameters for the fnv1a hash function, specialized for the hash result of 8 bytes.
|
|
|
|
template <>
|
|
|
|
struct fnv1_params<8>
|
|
|
|
{
|
|
|
|
static constexpr auto prime = 0x100000001b3; ///< The FNV prime.
|
|
|
|
static constexpr auto offset_basis = 0xcbf29ce484222325; ///< The FNV offset basis.
|
|
|
|
};
|
2019-07-08 14:04:52 +00:00
|
|
|
|
2019-11-07 10:34:12 +00:00
|
|
|
/// FNV1a hash function.
|
|
|
|
inline size_t fnv1a(const uint8_t* ptr, size_t len) noexcept
|
2019-07-08 14:04:52 +00:00
|
|
|
{
|
2019-11-07 10:34:12 +00:00
|
|
|
using params = fnv1_params<sizeof(size_t)>;
|
2019-07-08 14:04:52 +00:00
|
|
|
|
2019-11-07 10:34:12 +00:00
|
|
|
auto ret = size_t{params::offset_basis};
|
2019-07-08 14:04:52 +00:00
|
|
|
for (size_t i = 0; i < len; i++)
|
|
|
|
{
|
|
|
|
ret ^= ptr[i];
|
2019-11-07 10:34:12 +00:00
|
|
|
ret *= params::prime;
|
2019-07-08 14:04:52 +00:00
|
|
|
}
|
|
|
|
return ret;
|
|
|
|
}
|
|
|
|
|
|
|
|
namespace std
|
|
|
|
{
|
|
|
|
/// Hash operator template specialization for evmc_address needed for unordered containers.
|
|
|
|
template <>
|
2019-11-07 10:34:12 +00:00
|
|
|
struct EVMC_DEPRECATED hash<evmc_address>
|
2019-07-08 14:04:52 +00:00
|
|
|
{
|
|
|
|
/// Hash operator using FNV1a.
|
2019-11-07 10:34:12 +00:00
|
|
|
size_t operator()(const evmc_address& s) const noexcept
|
2019-07-08 14:04:52 +00:00
|
|
|
{
|
2019-11-07 10:34:12 +00:00
|
|
|
return fnv1a(s.bytes, sizeof(s.bytes));
|
2019-07-08 14:04:52 +00:00
|
|
|
}
|
|
|
|
};
|
|
|
|
|
|
|
|
/// Hash operator template needed for std::unordered_set and others using hashes.
|
|
|
|
template <>
|
2019-11-07 10:34:12 +00:00
|
|
|
struct EVMC_DEPRECATED hash<evmc_bytes32>
|
2019-07-08 14:04:52 +00:00
|
|
|
{
|
|
|
|
/// Hash operator using FNV1a.
|
2019-11-07 10:34:12 +00:00
|
|
|
size_t operator()(const evmc_bytes32& s) const noexcept
|
2019-07-08 14:04:52 +00:00
|
|
|
{
|
2019-11-07 10:34:12 +00:00
|
|
|
return fnv1a(s.bytes, sizeof(s.bytes));
|
2019-07-08 14:04:52 +00:00
|
|
|
}
|
|
|
|
};
|
|
|
|
} // namespace std
|
|
|
|
|
|
|
|
/** @} */
|