CMS 3D CMS Logo

StorageAccount.h
Go to the documentation of this file.
1 #ifndef STORAGE_FACTORY_STORAGE_ACCOUNT_H
2 #define STORAGE_FACTORY_STORAGE_ACCOUNT_H
3 
4 #include <cstdint>
5 #include <string>
6 #include <chrono>
7 #include <atomic>
8 #include <map>
9 #include <memory>
10 #include "oneapi/tbb/concurrent_unordered_map.h"
11 
12 namespace edm::storage {
14  public:
15  enum class Operation {
16  check,
17  close,
18  construct,
19  destruct,
20  flush,
21  open,
22  position,
23  prefetch,
24  read,
25  readActual,
26  readAsync,
29  readv,
30  resize,
31  seek,
32  stagein,
33  stat,
34  write,
37  writev
38  };
39 
40  struct Counter {
42  : attempts{0},
43  successes{0},
44  amount{0},
45  amount_square{0.},
46  vector_count{0},
47  vector_square{0},
48  timeTotal{0.},
49  timeMin{0.},
50  timeMax{0.} {}
51 
52  //NOTE: This is needed by oneapi::tbb::concurrent_unordered_map when it
53  // is constructing a new one. This would not give correct results
54  // if the object being passed were being updated, but that is not
55  // the case for operator[]
56  Counter(Counter const& iOther)
57  : attempts{iOther.attempts.load()},
58  successes{iOther.successes.load()},
59  amount{iOther.amount.load()},
60  amount_square{iOther.amount_square.load()},
61  vector_count{iOther.vector_count.load()},
62  vector_square{iOther.vector_square.load()},
63  timeTotal{iOther.timeTotal.load()},
64  timeMin{iOther.timeMin.load()},
65  timeMax{iOther.timeMax.load()} {}
66 
67  //Use atomics to allow concurrent read/write for intermediate
68  // output of the statics while running. The values obtained
69  // won't be completely consistent but should be good enough for
70  // monitoring. The values obtained once the program is shutting
71  // down should be completely consistent.
72 
73  std::atomic<uint64_t> attempts;
74  std::atomic<uint64_t> successes;
75  std::atomic<uint64_t> amount;
76  // NOTE: Significant risk exists for underflow in this value.
77  // However, the use cases are marginal so I let it pass.
78  std::atomic<double> amount_square;
79  std::atomic<int64_t> vector_count;
80  std::atomic<int64_t> vector_square;
81  std::atomic<double> timeTotal;
82  std::atomic<double> timeMin;
83  std::atomic<double> timeMax;
84 
85  static void addTo(std::atomic<double>& iAtomic, double iToAdd) {
86  double oldValue = iAtomic.load();
87  double newValue = oldValue + iToAdd;
88  while (not iAtomic.compare_exchange_weak(oldValue, newValue)) {
89  newValue = oldValue + iToAdd;
90  }
91  }
92  };
93 
94  class Stamp {
95  public:
97 
98  void tick(uint64_t amount = 0, int64_t tick = 0) const;
99 
100  protected:
102  std::chrono::time_point<std::chrono::high_resolution_clock> m_start;
103  };
104 
106  public:
107  StorageClassToken(StorageClassToken const&) = default;
108  StorageClassToken() = delete;
109  int value() const { return m_value; }
110 
111  friend class StorageAccount;
112 
113  private:
114  explicit StorageClassToken(int iValue) : m_value{iValue} {}
115 
116  int m_value;
117  };
118 
119  typedef oneapi::tbb::concurrent_unordered_map<int, Counter> OperationStats;
120  typedef oneapi::tbb::concurrent_unordered_map<int, OperationStats> StorageStats;
121 
122  static char const* operationName(Operation operation);
125 
126  static const StorageStats& summary(void);
127  static std::string summaryText(bool banner = false);
128  static void fillSummary(std::map<std::string, std::string>& summary);
129  static Counter& counter(StorageClassToken token, Operation operation);
130 
131  private:
133  };
134 } // namespace edm::storage
135 #endif // STORAGE_FACTORY_STORAGE_ACCOUNT_H
static std::string summaryText(bool banner=false)
static StorageClassToken tokenForStorageClassName(std::string const &iName)
oneapi::tbb::concurrent_unordered_map< int, OperationStats > StorageStats
static Counter & counter(StorageClassToken token, Operation operation)
void tick(uint64_t amount=0, int64_t tick=0) const
oneapi::tbb::concurrent_unordered_map< int, Counter > OperationStats
static void fillSummary(std::map< std::string, std::string > &summary)
std::chrono::time_point< std::chrono::high_resolution_clock > m_start
std::atomic< uint64_t > successes
static const std::string & nameForToken(StorageClassToken)
std::atomic< uint64_t > attempts
unsigned long long uint64_t
Definition: Time.h:13
static const StorageStats & summary(void)
std::atomic< int64_t > vector_square
static StorageStats m_stats
std::atomic< int64_t > vector_count
static char const * operationName(Operation operation)
static void addTo(std::atomic< double > &iAtomic, double iToAdd)