libdpf/include/dpf/experiment_note.hpp

53 lines
1.4 KiB
C++
Raw Normal View History

/// @file dpf/experiment_note.hpp
/// @brief Lightweight seed registry hook (no Asio / PRG includes).
#ifndef LIBDPF_INCLUDE_DPF_EXPERIMENT_NOTE_HPP__
#define LIBDPF_INCLUDE_DPF_EXPERIMENT_NOTE_HPP__
#include <cstddef>
#include <cstdint>
#include <type_traits>
#include "hedley/hedley.h"
namespace dpf
{
namespace detail
{
/// @brief Optional sink installed by `experiment` (TLS).
struct experiment_seed_sink
{
virtual ~experiment_seed_sink() = default;
virtual void note(const char * name, const std::uint8_t * bytes,
std::size_t n) = 0;
};
inline thread_local experiment_seed_sink * experiment_seed_sink_tls = nullptr;
} // namespace detail
/// @brief Record a named seed when an `experiment` is installed on this thread.
HEDLEY_ALWAYS_INLINE
void note_experiment_seed(const char * name, const void * bytes,
std::size_t n) noexcept
{
if (detail::experiment_seed_sink_tls == nullptr || bytes == nullptr
|| n == 0 || name == nullptr)
return;
detail::experiment_seed_sink_tls->note(name,
static_cast<const std::uint8_t *>(bytes), n);
}
template <typename T>
HEDLEY_ALWAYS_INLINE
void note_experiment_seed(const char * name, const T & seed) noexcept
{
static_assert(std::is_trivially_copyable_v<T>,
"note_experiment_seed requires a trivially copyable seed");
note_experiment_seed(name, &seed, sizeof(seed));
}
} // namespace dpf
#endif // LIBDPF_INCLUDE_DPF_EXPERIMENT_NOTE_HPP__