// Copyright (c) Microsoft Corporation. All rights reserved. // Licensed under the Apache 2.0 License. #pragma once #include "ccf/ds/siphash.h" #define FMT_HEADER_ONLY #include #include namespace ccf { using ByteVector = llvm_vecsmall::SmallVector; } namespace std { template struct hash> { size_t operator()(const llvm_vecsmall::SmallVector& v) const { static constexpr ccf::siphash::SipKey k{ 0x7720796f726c694b, 0x2165726568207361}; return ccf::siphash::siphash<2, 4>(v.data(), v.size(), k); } }; } FMT_BEGIN_NAMESPACE template <> struct formatter { template constexpr auto parse(ParseContext& ctx) { return ctx.begin(); } template auto format(const ccf::ByteVector& e, FormatContext& ctx) const { // This is the same as std::isprint, but independent of the current locale. auto printable = [](uint8_t b) { return b >= 0x20 && b <= 0x7e; }; if (std::all_of(e.begin(), e.end(), printable)) { return format_to( ctx.out(), "", e.size(), std::string(e.begin(), e.end())); } else { return format_to( ctx.out(), "", e.size(), fmt::join(e, " ")); } } }; FMT_END_NAMESPACE