HikoGUI
A low latency retained GUI
Loading...
Searching...
No Matches
counters.hpp
1// Copyright Take Vos 2019-2020.
2// Distributed under the Boost Software License, Version 1.0.
3// (See accompanying file LICENSE_1_0.txt or copy at https://www.boost.org/LICENSE_1_0.txt)
4
5#pragma once
6
7#include "wfree_unordered_map.hpp"
8#include "os_detect.hpp"
9#include "fixed_string.hpp"
10#include <span>
11#include <typeinfo>
12#include <typeindex>
13#include <string>
14
15namespace tt {
16
17constexpr int MAX_NR_COUNTERS = 1024;
18
20 std::atomic<int64_t> *counter;
21 int64_t previous_value;
22};
23
25
26// To reduce number of executed instruction this is a global variable.
27// The wfree_unordered_map does not need to be initialized.
28inline counter_map_type counter_map;
29
30template<basic_fixed_string Tag>
32 // Make sure non of the counters are false sharing cache-lines.
33 alignas(hardware_destructive_interference_size) inline static std::atomic<int64_t> counter = 0;
34
35 tt_no_inline void add_to_map() const noexcept
36 {
37 counter_map.insert(Tag, counter_map_value_type{&counter, 0});
38 }
39
40 int64_t increment() const noexcept
41 {
42 ttlet value = counter.fetch_add(1, std::memory_order_relaxed);
43
44 if (value == 0) {
45 [[unlikely]] add_to_map();
46 }
47
48 return value + 1;
49 }
50
51 [[nodiscard]] int64_t read() const noexcept
52 {
53 return counter.load(std::memory_order_relaxed);
54 }
55
56 // Don't implement readAndSet, a set to zero would cause the counters to be reinserted.
57};
58
59template<basic_fixed_string Tag>
60inline int64_t increment_counter() noexcept
61{
62 return counter_functor<Tag>{}.increment();
63}
64
65template<basic_fixed_string Tag>
66[[nodiscard]] inline int64_t read_counter() noexcept
67{
68 return counter_functor<Tag>{}.read();
69}
70
74[[nodiscard]] inline std::pair<int64_t, int64_t> read_counter(std::string tag) noexcept
75{
76 auto &item = counter_map[tag];
77
78 ttlet *const count_ptr = item.counter;
79 ttlet count = count_ptr != nullptr ? item.counter->load(std::memory_order_relaxed) : 0;
80 ttlet count_since_last_read = count - item.previous_value;
81 item.previous_value = count;
82 return {count, count_since_last_read};
83}
84
85} // namespace tt
Definition counters.hpp:19
Definition counters.hpp:31
Definition wfree_unordered_map.hpp:56
T count(T... args)
T fetch_add(T... args)
T load(T... args)